Exit
  • Global community
    • Language:
      • Deutsch
      • English
      • Español
      • Français
      • Português
  • 日本語コミュニティ
  • 한국 커뮤니티
0

Call "Update Markers from Source".

Engaged ,
Aug 15, 2016 Aug 15, 2016

Is there a way to call "Update Markers from Source" command from a script?

Capture.PNG

TOPICS
Scripting
1.8K
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

Natively via ExtendScript properties, I don't think you can, but if you go the Menu Command ID route then perhaps. I always add the word of caution of the unstable nature of the command id way, but if you read my article here you can get the pdf that lists the update markers menu id.

UpdateMarkersFromSource = 2539

http://www.provideocoalition.com/after-effects-menu-command-ids/

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Engaged ,
Aug 15, 2016 Aug 15, 2016

David, thank you for the advice. I've been using this technique to create comp markers, thanks to one of your videos. For some reason ID=2539 doesn't seem to work. Calling

alert(app.findMenuCommandId("Update Markers from Source (replaces all markers)"));

shows 2539, so the ID is correct. Also, I'm making sure that the right layer is selected. Any idea what I'm missing?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

The menu commands get called from the app level, since it is app.executeCommand(). Since you have to access that contextual menu by right clicking an actual Marker, and not just selecting a layer, this may fall into the "unstable" category. Markers don't have a selection attribute unfortunately, so I'm not sure it will be possible to get this particular command to properly work.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

Actually, now that I look at your initial request more. You actual should be able to loop through a comp, gathering the comp marker times, and then create new markers on the precomp layer based on those same time locations. It's not as simple as just saying "Update", but it should be doable.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

Correction, forgot we still don't have direct access to Comp Markers.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

All though, there is the Expression cheat. I'm messing with it right now. You can get the CompMarkers via Expression. So adding a TextLayer, Expressioning the SourceText to read the CompMarker data, then translate that to scriptable time cues for your layer that needs Marker Source Update.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

Ok so this is very sloppy at the moment, and I just quickly tested it, but if you added a text layer then expressioned the SourceText to read:

var m = thisComp.marker.numKeys;

for(var i=1; i<=m; i++){

  if(thisComp.marker.key(i).time == time){

  true;

  break;

  }else{

  false;

  }

};

Then ran this code to retrieve the times from that layer:

var comp = app.project.item(1);

var frmDur = comp.frameDuration;

var compDur = comp.duration;

var frames = compDur/frmDur;

var prop = comp.layer("<empty text layer>").property("ADBE Text Properties").property("ADBE Text Document");

var times = new Array();

var isTrue;

for(var f=0; f<frames; f++){

  isTrue = prop.valueAtTime(frmDur*f, false);

  if(isTrue == "true"){

  times.push(frmDur*f);

  }

}

alert(times);

You should end up with an array of times that could be tossed into a setValuesAtTimes() method for your main layer to add the markers.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 15, 2016 Aug 15, 2016

David, you could avoid looping over all frames in the comp by building the array right inside the expression:

p = thisComp.marker;

M = p.numKeys;

a = [];

for (m=1; m<=M; m++) a.push(p.key(m).time);

M===0 ? "NO_KEYS" : a.toString();

then retrieve it by

var keyTimes = prop.valueAtTime(0, false);

if (keyTimes==="NO_KEYS"){

     keyTimes = [];

else{

     keyTimes = keyTimes.split();

     for (var k=0; k<keyTimes.length; k++){keyTimes = + keyTimes;}; // need convert string entry to number entry

     };

It should be considerably faster for a long comp.

Xavier.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Advocate ,
Aug 16, 2016 Aug 16, 2016
LATEST

Good point Xavier.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines