Page 1 of 1

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Wed Jul 27, 2011 8:04 pm
by robpat
Stdlib.moveLayerContentByIndex(doc, idx, dx, dy) moves the selected layers regardless of the value of idx.

The code I used.
Code: Select all#include "/r/xtools/xlib/stdlib.js"
Stdlib.moveLayerContentByIndex(app.activeDocument, 1, 100, 200);


Any fix for this?
Thanks.

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Thu Jul 28, 2011 1:35 pm
by xbytor
Looks like a bug in PS, at least in PSCS5. I'll check older versions to see if this behaved correctly in earlier revs.
Either that, or doing this in PS is not actually possible.

The simplest solution is to use Layer.translate or Stdlib.moveLayerContent with a Layer object reference instead of an index.

You may also be able to work up a version that uses the Name (if unique) or Id of the layer if you are trying to
avoid using Layer objects.

-X

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Fri Jul 29, 2011 5:43 pm
by robpat
Thanks for your advice.
Yes, I am trying to avoid using Layer objects.
I use Action Manager Index heavily in my code.
layer Id is not my choice unless there is a way to convert index to layer Id.

Now I come up with this workaround.
Code: Select allfunction makeActiveByIndex(idx) {
   var desc = new ActionDescriptor();
   var ref = new ActionReference();
   ref.putIndex(cTID("Lyr "), idx);
   desc.putReference(cTID("null"), ref);
   desc.putBoolean(cTID("MkVs"), false);
   executeAction(cTID("slct"), desc, DialogModes.NO);
}

function moveActiveLayerContent(dx, dy) {
   var desc = new ActionDescriptor();
   var lref = new ActionReference();
   lref.putEnumerated(cTID("Lyr "), cTID("Ordn"), cTID("Trgt"));
   desc.putReference(cTID("null"), lref);
   var pdesc = new ActionDescriptor();
   pdesc.putUnitDouble(cTID('Hrzn'), cTID('#Pxl'), dx);
   pdesc.putUnitDouble(cTID('Vrtc'), cTID('#Pxl'), dy);
   desc.putObject(cTID('T   '), cTID('Ofst'), pdesc);
   executeAction(cTID('move'), desc, DialogModes.NO);
}

makeActiveByIndex(1);
moveActiveLayerContent(100, 200);

makeActiveByIndex is rather slow though.

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Fri Jul 29, 2011 6:31 pm
by xbytor
layer Id is not my choice unless there is a way to convert index to layer Id.

Use the index to get the layer's descriptor. The layer id is in there. There should be functions for this in stdlib.js.

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Fri Jul 29, 2011 6:47 pm
by Mike Hale
robpat wrote:makeActiveByIndex is rather slow though.

The question is how does the speed of makeActiveByIndex compare with other ways to select a layer. I think you will find that it is much faster than any of the DOM methods. Replacing the cTID calls with the ID numbers will speed up the function a little at the expense of making it even harder to read.

One advantage of using ID is that it does not change when you move, add, or delete layers.

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Fri Jul 29, 2011 6:58 pm
by xbytor
The question is how does the speed of makeActiveByIndex compare with other ways to select a layer.

Selecting the layer is slow regardless of how you do it :)

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Sat Jul 30, 2011 12:25 pm
by robpat
xbytor wrote:Use the index to get the layer's descriptor. The layer id is in there. There should be functions for this in stdlib.js.
Here is my modified code.
Code: Select allfunction getLayerIDByIndex(index) {
   var ref = new ActionReference();
   ref.putProperty(cTID("Prpr"), cTID("LyrI"));
   ref.putIndex(cTID("Lyr "), index);
   return executeActionGet(ref).getInteger(cTID("LyrI"));
}

function moveLayerContentByLayerID(layerID, dx, dy) {
   var desc = new ActionDescriptor();
   var lref = new ActionReference();
   lref.putIdentifier(cTID("Lyr "), layerID);
   desc.putReference(cTID("null"), lref);
   var pdesc = new ActionDescriptor();
   pdesc.putUnitDouble(cTID('Hrzn'), cTID('#Pxl'), dx);
   pdesc.putUnitDouble(cTID('Vrtc'), cTID('#Pxl'), dy);
   desc.putObject(cTID('T   '), cTID('Ofst'), pdesc);
   executeAction(cTID('move'), desc, DialogModes.NO);
}

moveLayerContentByLayerID(getLayerIDByIndex(1), 100, 200);

Using layer Id cannot solve this problem.
moveLayerContentByLayerID also moves the selected layers instead of the layer specified by layerID.

Mike Hale wrote:The question is how does the speed of makeActiveByIndex compare with other ways to select a layer. I think you will find that it is much faster than any of the DOM methods. Replacing the cTID calls with the ID numbers will speed up the function a little at the expense of making it even harder to read.

One advantage of using ID is that it does not change when you move, add, or delete layers.
makeActiveByIndex is faster than setting doc.activeLayer, but I would prefer not to select the layer before moving it.

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Sat Jul 30, 2011 2:39 pm
by xbytor
I would prefer not to select the layer before moving it.

It would appear that this is one if those features that can only be invoked on an active layer, unfortunately. I don't know of any other way to attack the problem.

Stdlib.moveLayerContentByIndex doesn't work as expected

Posted: Sat Jul 30, 2011 5:09 pm
by robpat
Okay, I'll just go with my workaround.
Thank you for your suggestions.