morningShow

Back to All Results

Motion Vectorization

Input video: morningShow

Output SVG motion program code

Output SVG motion program

SVG motion program code (uncorrected tracking)

SVG motion program (uncorrected tracking)

Motion Program Transformation

Appearance Adjustment

Simple appearance adjustment

Input SVG motion program

MPTransformer(P, args):
  // OBJECT SELECTOR: Select all red objects.
  selObjs = objSelector(P, propQuery, "color", "red", [0, P.endFrm])
  // OBJECT TRANSFORMER: Replace with red stars.
  changeAppearanceObjTransformer(selObjs, “redStar.png”, [0, P.endFrm])

  // OBJECT SELECTOR: Select all black objects.
  selObjs = objSelector(P, propQuery, "color", "black", [0, P.endFrm])
  // OBJECT TRANSFORMER: Replace with red stars.
  changeAppearanceObjTransformer(selObjs, “redStar.png”, [0, P.endFrm])

  // OBJECT SELECTOR: Select all yellow objects.
  selObjs = objSelector(P, propQuery, "color", "yellow", [0, P.endFrm])
  // OBJECT TRANSFORMER: Replace with blue stars.
  changeAppearanceObjTransformer(selObjs, “blueStar.png”, [0, P.endFrm])

  // OBJECT SELECTOR: Select all orange objects.
  selObjs = objSelector(P, propQuery, "color", "orange", [0, P.endFrm])
  // OBJECT TRANSFORMER: Replace with white stars.
  changeAppearanceObjTransformer(selObjs, “whiteStar.png”, [0, P.endFrm])

Motion program transformer code. Here we change all the red and black circles to red stars, the yellow circles to blue stars, and the orange circles to white stars, using changeAppearanceObjTransformer.

Output SVG motion program

Input SVG motion program

MPTransformer(P, args):
  // Change the background.
  changeAppearance("bg", args.background)

  // Keep track of unchanged objects because we will replace them later.
  unchangedObjs = objSelector(P, propQuery, "position", [[0, 1], [0, 2/9]], [0, P.endFrm])

  // Replace the second row with Canal St stations.
  selObjs = objSelector(P, propQuery, "position", [[0, 1], [1/9, 2/9]], [0, P.endFrm])
  changeAppearanceObjTransformer(selObjs, args.canalStImgs, [0, P.endFrm])
  unchangedObjs.remove(selObjs)

  // Replace the fourth row with NJ transit and 123 trains.
  selObjs = objSelector(P, propQuery, "position", [[0, 1], [1/3 , 4/9]], [0, P.endFrm])
  changeAppearanceObjTransformer(selObjs[:3], args.oneTwoThree, [0, P.endFrm])
  changeAppearanceObjTransformer(selObjs[3:], args.njTransit, [0, P.endFrm])
  unchangedObjs.remove(selObjs)

  // Replace the eighth row with Penn Station and ACE trains.
  selObjs = objSelector(P, propQuery, "position", [[0, 1], [7/9, 8/9]], [0, P.endFrm])
  changeAppearanceObjTransformer(selObjs[:5], args.ace, [0, P.endFrm])
  changeAppearanceObjTransformer(selObjs[5:], args.pennStation, [0, P.endFrm])
  unchangedObjs.remove(selObjs)

  // Replace the black circle with a pink circle.
  blackCircle = propQuery(obj, "color", “black”, [0, P.endFrm])
  changeAppearanceObjTransformer(blackCircle, “pinkCircle.png”, [0, P.endFrm])
  unchangedObjs.remove(blackCircle)

  // Select some random objects to replace with green or yellow taxis.
  // randInt(a, b) chooses a random integer in [a, b].
  numTaxis = randInt(0, len(unchangedObjs))
  taxiImgs = chooseRandom(numTaxis, args.taxiImgs, replace=True)
  taxis = chooseRandom(numTaxis, unchangedObjs, replace=False)
  changeAppearanceObjTransformer(taxis, taxiImgs, [0, P.endFrm])
  unchangedObjs.remove(taxis)

  // Select a random object to replace with pedestrian signs.
  signs = chooseRandom(1, unchangedObjs, replace=True)
  changeAppearanceObjTransformer(signs, args.walkImg, [0, P.endFrm/4])
  changeAppearanceObjTransformer(signs, args.stopImg, [P.endFrm/4, P.endFrm/2])
  changeAppearanceObjTransformer(signs, args.walkImg, [P.endFrm/2, 3 * P.endFrm/4])
  changeAppearanceObjTransformer(signs, args.stopImg, [3 * P.endFrm/4, P.endFrm])

  // Replace the remaining objects with random colored circles.
  pplCircles = chooseRandom(len(unchangedObjs), args.pplCircles, replace=True)
  changeAppearanceObjTransformer(unchangedObjs, pplCircles, [0, P.endFrm])

Motion program transformer code. Here we create a subway station graphic by swapping out rows of circles for station lines and names. The remaining unchanged objects are randomly changed to different colored circle and green and yellow taxis. The appearance changes are done with changeAppearanceObjTransformer.

Output SVG motion program

Input SVG motion program

MPTransformer(P, args):
  // Change the background.
  changeAppearance("bg", args.background)

  // Keep track of all objects we have transformed.
  remainingObjs = objSelector(P, propQuery, "all", None, [0, P.endFrm])

  // Select all objects in first two rows.
  selObjs = objSelector(P, propQuery, "position", [[0, 1], [0, 2/9]], [0, P.endFrm])
  // Replace them with random Argentina team colors.
  // chooseRandom(N, choices) chooses N elements from an array of choices, the flag replace 
  // indicates whether we replace choices.
  argentinaColors = chooseRandom(len(selObjs), [“lightblue.png”, “white.png”, “gold.png”], replace=True)
  changeAppearanceObjTransformer(selObjs, argentinaColors, [0, P.endFrm])
  remainingObjs.remove(selObjs)

  // Do the same with the French team colors at the bottom two rows.
  selObjs = objSelector(P, propQuery, "position", [[0, 1], [7/9, 1]], [0, P.endFrm])
  argentinaColors = chooseRandom(len(selObjs), [“darkBlue.png”, “white.png”, “red.png”], replace=True)
  changeAppearanceObjTransformer(selObjs, franceColors, [0, P.endFrm])
  remainingObjs.remove(selObjs)

  // Replace the black circle with Argentina player.
  argentinaPlayer1 = objSelector(P, propQuery, "color", “black”, [0, P.endFrm])
  changeAppearanceObjTransformer(argentinaPlayer1, “argentina.png”, [0, P.endFrm])
  remainingObjs.remove(argentinaPlayer1)

  // The soccer ball is the first object that the black circle collides with. 
  // The collisions are sorted by time.
  collisions = eventQuery(argentinaPlayer1, "collisionFrames", [0, P.endFrm])
  soccerBall = collision[0].obj
  changeAppearanceObjTransformer(soccerBall, “soccerball.png”, [0, P.endFrm])
  remainingObjs.remove(soccerBall)

  // Replace the second object that the soccer ball collides with the other Argentina player.
  collisions = eventQuery(blackCircle, "collisionFrames", [0, P.endFrm])
  argentinaPlayer2 = collision[1].obj
  changeAppearanceObjTransformer(argentinaPlayer2, “argentina.png”, [0, P.endFrm])
  remainingObjs.remove(argentinaPlayer2)

  // Replace the object directly to the left of the soccer ball with a France player 
  // and add up and down oscillation.
  selObjs = objSelector(obj, propQuery, "position", [[0, soccerBall.x], 
                        [soccerBall.y - 0.05, soccerBall.y + 0.05]], [0, 1])
  // sortByX(objs) sorts the objs by increasing x coordinate
  francePlayer1 = sortByX(selObjs)[0]
  changeAppearanceObjTransformer(francePlayer1, “france.png”, [0, P.endFrm])
  function sinY(t, [y]):
      return y[t] + 0.05 * sin(t)
  adjLocalMotion(francePlayer1, shiftY, offset, [0, P.endFrm])
  remainingObjs.remove(francePlayer1)

  // Replace an object in the fourth row from the bottom with a France player.
  selObjs = objSelector(P, propQuery, "position", [[0, 1], [5/9, 2/3]], [0, P.endFrm])
  francePlayer2 = selObjs[0]
  changeAppearanceObjTransformer(francePlayer2, “france.png”, [0, P.endFrm])
  adjLocalMotion(francePlayer2, shiftY, offset, [0, P.endFrm])
  remainingObjs.remove(francePlayer2)

  // Remove all remaining unselected objects.
  removeObjs(remainingObjs)

Motion program transformer code. Here we generate a world cup graphic with changeAppearanceObjTransformer. We swap out rows of objects with different colored squares by querying the y-position of the input SVG objects. Positions in addition to collisions were used to determine which objects to swap out in the soccer field.

Output SVG motion program