Creating and moving an artLayer inside "active" layerSet
Re: Creating and moving an artLayer inside "active" layerSet
Actually, there might be a misunderstanding here, you've already fixed the 27th of September the background layer position movement inside the layer Set (which needs only to happen once per activeDocument - as I'll duplicate the folder for each storyboard panel -).
This was already perfect and took only 2 lines of code I understood
The other issue is with my StoryCaveCam.jsx script which creates the layer with the green stroke, it works but creates the artLayer named CAM only in the top layerSet (SQ_00_SH_xxx...).
To explain how my template works, each layerSet SQ_00_SH_000_010, 020, 030, etc. will have drawings for each storyboard panel, so here's an example of what I want to do with these scripts, it'll make the project clearer :
As you can see, my current "action" creates the CAM layer on top of the Drawing layer which was the activeLayer.
If I were to use my script StoryCaveCam.jsx it would create that same layer but only in the top layerSet because the index is set to [0] even when I'm inside a bottom layerSet, like my old example where I'm initially in xxx_000 but CAM appears in xxx_010 :
If there was a built-in variable called "activeLayerSet" I believe this issue would be sorted right away, but ... :/
I hope this clarifies my issue, thanks again for your help man !
This was already perfect and took only 2 lines of code I understood
The other issue is with my StoryCaveCam.jsx script which creates the layer with the green stroke, it works but creates the artLayer named CAM only in the top layerSet (SQ_00_SH_xxx...).
To explain how my template works, each layerSet SQ_00_SH_000_010, 020, 030, etc. will have drawings for each storyboard panel, so here's an example of what I want to do with these scripts, it'll make the project clearer :
As you can see, my current "action" creates the CAM layer on top of the Drawing layer which was the activeLayer.
If I were to use my script StoryCaveCam.jsx it would create that same layer but only in the top layerSet because the index is set to [0] even when I'm inside a bottom layerSet, like my old example where I'm initially in xxx_000 but CAM appears in xxx_010 :
If there was a built-in variable called "activeLayerSet" I believe this issue would be sorted right away, but ... :/
I hope this clarifies my issue, thanks again for your help man !
Re: Creating and moving an artLayer inside "active" layerSet
I checked once again the post from 28 September and found I was wrong, I mean I misunderstood you. I still thought you want to move background layer to bottom of active subset, but without strict pointing it. So I wrote then another script which detected activce layer of its set and moved there background. As you see, difference was that you didn't need anymore to write where exactly background had to be moved, but a script checked it itself.
Now I know background layer issue is closed and now we're talking about creating CAM layer in a specific set - active one, without pointing it by a script - I mean a script will find it checking what layer(Set) is currently active.
Before you read my answer please reply to my question as you didn't do it before. Did that script I wrote worked for you (that with my screenshots "before" and "after" result)? So using even that simple example, moved a background inside a set where some layer was seleced as active one?
And here's a code I think you wanted about creating a CAM layer. If that is not again that you wanted then no problem, I hope we finally find the solution, as I think writing proper script is no problem for me, but only understanding what you want to exactly do... that may seem flustrating someone explains something to me quite well and though I could realize it I can't catch his mind
I won't create a new code. I'll use that "addition" preceding background layer part and then write 4 lines where in the 2nd eval of 3rd line I exploit PS scripting glith, so I do something what shouldn't happen if there were no bugs in Adobe Ps scrtipting environment. 2nd eval of 3rd line has to step back history state which was created by 1st eval of 3rd line, but to be honest if not a bug then 1st eval of 3rd line would create not two but just one step, so the excpected result only and nothing before it:
Now I know background layer issue is closed and now we're talking about creating CAM layer in a specific set - active one, without pointing it by a script - I mean a script will find it checking what layer(Set) is currently active.
Before you read my answer please reply to my question as you didn't do it before. Did that script I wrote worked for you (that with my screenshots "before" and "after" result)? So using even that simple example, moved a background inside a set where some layer was seleced as active one?
And here's a code I think you wanted about creating a CAM layer. If that is not again that you wanted then no problem, I hope we finally find the solution, as I think writing proper script is no problem for me, but only understanding what you want to exactly do... that may seem flustrating someone explains something to me quite well and though I could realize it I can't catch his mind
I won't create a new code. I'll use that "addition" preceding background layer part and then write 4 lines where in the 2nd eval of 3rd line I exploit PS scripting glith, so I do something what shouldn't happen if there were no bugs in Adobe Ps scrtipting environment. 2nd eval of 3rd line has to step back history state which was created by 1st eval of 3rd line, but to be honest if not a bug then 1st eval of 3rd line would create not two but just one step, so the excpected result only and nothing before it:
Code: Select all
aL = (aD = 'activeDocument') +'.activeLayer', bol = true, arr = []
while(bol) aL += '.parent', String(AL = eval(aL)).slice(1, 9) != 'LayerSet' ? bol = !bol : arr.push(AL.name)
aDl = aD + l = '.layers', n = arr.length - 1;
(function set() {
for(i = 0; i < (evl = eval(aDl)).length; i++) {
if (evl[i].name == arr[n]) {
aDl += '[i]' + l, n--, aD += l + '[' + i + ']'
if (n > -1) set(); break
}
}
})()
L = eval("(aL = activeDocument.activeLayer).kind == 'LayerKind.NORMAL' ?\
((lay = aL.parent.layers).length == 1 ? 1 : (lay[0] == aL ? 1 : 2)) : 2")
lyr = eval(aD).artLayers.add(), eval('doc.activeHistoryState =\
(hS = (doc = activeDocument).historyStates)[hS.length - L]'), lyr.name = 'CAM'
Re: Creating and moving an artLayer inside "active" layerSet
Hi Kukurykus,
To answer you question, this code still doesn't work even while selecting a layer or the group :
In ExtendScript Toolkit, I get the last line (btm.move ... all.Locked=1) selected in orange.
But, to answer your second question, the code you wrote to create the CAM layer works perfectly and everything is in order
A thousand thanks again, I'll update the script asap.
BTW, would you know the method to delete the last 5 historyStates ?
I've tried with :
delete(app.activeDocument.historyStates[4]);
delete(app.activeDocument.historyStates.length-4);
It doesn't show any errors but nothing happens.
The only one that works is the "purge" method I already use in the template, but clears it all :/
Thanks again !
To answer you question, this code still doesn't work even while selecting a layer or the group :
Code: Select all
aL = (aD = 'activeDocument') +'.activeLayer', bol = true, arr = []
while(bol) aL += '.parent', String(AL = eval(aL)).slice(1, 9) != 'LayerSet' ? bol = !bol : arr.push(AL.name)
aDl = aD + l = '.layers', n = arr.length - 1;
(function set() {
for(i = 0; i < (evl = eval(aDl)).length; i++) {
if (evl[i].name == arr[n]) {
aDl += '[i]' + l, n--, aD += l + '[' + i + ']'
if (n > -1) set(); break
}
}
})()
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) nme = btm.name, btm.isBackgroundLayer = 0
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
But, to answer your second question, the code you wrote to create the CAM layer works perfectly and everything is in order
A thousand thanks again, I'll update the script asap.
BTW, would you know the method to delete the last 5 historyStates ?
I've tried with :
delete(app.activeDocument.historyStates[4]);
delete(app.activeDocument.historyStates.length-4);
It doesn't show any errors but nothing happens.
The only one that works is the "purge" method I already use in the template, but clears it all :/
Thanks again !
Re: Creating and moving an artLayer inside "active" layerSet
I wonder why that code doesn't work for you. Maybe it's because you use PS CC while I still CS. Anyway fisrt part (that both codes have ie. with background moving and CAM creating) is identical.
It seems something brokes the code in their second part. We can investigate it some easy way. Those 2 additional lines:
worked fine as separate code (that before a little change I made to connect it to a part background code and now CAM's uses). This code originally looked so:
then I added next part in front of these 2 lines while in sole 2 lines I did 2 changes, I changed a rank of nme = btm.name, btm.isBackgroundLayer = 0 for btm.isBackgroundLayer = 0; nme = btm.name adding semicolon between. Second change was changing lyr[0] in 2 spots for aD, where additionally I bound aD to eval(aD):
1) Now when we know this all please let's see where exactly error happens in last line (that became orange for you):
open PS, ctrl-n (new document, where only background for test is sufficient), open ESTK, set PS mode, paste a code you did before that alerted error and replace last 2 lines for these ones:
2) When you do it please tell me did last or one before last line line get orange highlighted, also when you do this test, do another one but with 2 alerts:
I know it's not necessary for you now, but it may help me and maybe later you to understand what happens when you will write something similar...
(ah, and just for clarity. Like CAM layer had to be created in (sub)set which (layer) was activated / selected), this code has to move last layer (changed from background if needed) to (sub)set which (layer) was activated / selected. In this (ctrl-n etc) example only background changed to layer and locked again).
3) History States Deletion:
It seems something brokes the code in their second part. We can investigate it some easy way. Those 2 additional lines:
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) nme = btm.name, btm.isBackgroundLayer = 0
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) nme = btm.name, btm.isBackgroundLayer = 0
btm.move(lyr[0], ElementPlacement.PLACEATEND); (bGl = (bGn = lyr[0].layers)[bGn.length - 1]).name = nme, bGl.allLocked =1
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) btm.isBackgroundLayer = 0; nme = btm.name
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
1) Now when we know this all please let's see where exactly error happens in last line (that became orange for you):
open PS, ctrl-n (new document, where only background for test is sufficient), open ESTK, set PS mode, paste a code you did before that alerted error and replace last 2 lines for these ones:
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) btm.isBackgroundLayer = 0; nme = btm.name
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);
(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
Code: Select all
alert(aD)
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) btm.isBackgroundLayer = 0; nme = btm.name
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);
alert(aD)
alert(eval(aD))
(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
(ah, and just for clarity. Like CAM layer had to be created in (sub)set which (layer) was activated / selected), this code has to move last layer (changed from background if needed) to (sub)set which (layer) was activated / selected. In this (ctrl-n etc) example only background changed to layer and locked again).
3) History States Deletion:
Code: Select all
function cTT(v) {return charIDToTypeID(v)}; function sTT(v) {return stringIDToTypeID(v)}}
function HstS(v) {// UNDOING HISTORY STATES:
(ref = new ActionReference()).putOffset(cTT('HstS'), 1 - v);
(dsc = new ActionDescriptor()).putReference(cTT('null'), ref)
executeAction(cTT('slct'), dsc, DialogModes.NO);
}
function HSD() {// DELETION OF CURRENT AND FOLLOWING HISTORY STATES:
(ref = new ActionReference()).putProperty(cTT('HstS'), cTT('CrnH'));
(dsc = new ActionDescriptor()).putReference(cTT('null'), ref)
executeAction(cTT('Dlt '), dsc, DialogModes.NO)
}
HstS(5), HSD()
Re: Creating and moving an artLayer inside "active" layerSet
Hi Kukurykus,
No problem, let's do some troubleshooting.
The reason I believe it didn't work at first (apart from the version difference between CS and CC) is that I was trying to use your script using my StoryCaveTemplate.jsx file with the background layer that was already fixed and inside the layerSet at launch.
So I just stared from scratch with a new document like you suggested :
1)
When I use this code :
The last line is orange and the JS console says "Result: 1", nothing happens on Photoshop.
On this code :
It works, no orange line, the Background layer transforms into Layer 0 (locked)
the same thing happens with this code (it works too):
2)
When I use this code :
I first have the alerts, once in ExtendScript Toolkit that says "activeDocument" and twice in Photoshop that says "[Document Untitled -1]" and then the last line becomes orange, the backgroundLayer becomes Layer 0 (no lock).
then...
I tried that same code above on my template document, I've manually put the BackgroundLayer outside the layerSet for a test then ran the code, had the same three alerts (with different names), then it put the BackgroundLayer inside the layerSet at the bottom but had the last line in orange.
3) History State Deletion
I've added the code to the StoryCaveCam.jsx script, I ran it and nothing happen except that I just deleted the extra bracket that the editor found : Even after that the Result is "undefined" in the console, but i just realized I made a mistake, as I should modify the script to cut the layer, delete the history then paste it in order to work.
I'll send you an update on that asap !
Thanks again Kukurykus.
K.
No problem, let's do some troubleshooting.
The reason I believe it didn't work at first (apart from the version difference between CS and CC) is that I was trying to use your script using my StoryCaveTemplate.jsx file with the background layer that was already fixed and inside the layerSet at launch.
So I just stared from scratch with a new document like you suggested :
1)
When I use this code :
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) nme = btm.name, btm.isBackgroundLayer = 0
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
On this code :
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) btm.isBackgroundLayer = 0; nme = btm.name
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
the same thing happens with this code (it works too):
Code: Select all
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) btm.isBackgroundLayer = 0; nme = btm.name
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);
(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
When I use this code :
Code: Select all
alert(aD)
if ((btm = (lyr = activeDocument.layers)[lyr.length - 1]).isBackgroundLayer) btm.isBackgroundLayer = 0; nme = btm.name
btm.move(aD = eval(aD), ElementPlacement.PLACEATEND);
alert(aD)
alert(eval(aD))
(bGl = (bGn = aD.layers)[bGn.length-1]).name = nme, bGl.allLocked=1
then...
I tried that same code above on my template document, I've manually put the BackgroundLayer outside the layerSet for a test then ran the code, had the same three alerts (with different names), then it put the BackgroundLayer inside the layerSet at the bottom but had the last line in orange.
3) History State Deletion
I've added the code to the StoryCaveCam.jsx script, I ran it and nothing happen except that I just deleted the extra bracket that the editor found : Even after that the Result is "undefined" in the console, but i just realized I made a mistake, as I should modify the script to cut the layer, delete the history then paste it in order to work.
I'll send you an update on that asap !
Thanks again Kukurykus.
K.
Re: Creating and moving an artLayer inside "active" layerSet
1) I thought so you didn't include fixed part, it's why didn't work.
2) now when you found what was wrong in point 1, a code from point 2 will work too. It doesn't because I forgot to replace semicolon. When you start new 'sentence' with round bracket character then mostly everything in preceeding part need to be ended with semicolon. For example when it's ended with curly bracket then you don't need to use semicolon (but I'm not sure it's so in every case). So to make that test working you have to put semicolon after third alert expression, while that from before second alert may be removed, but nothing happens if it stays where it was put.
3) yes, I didn't remove additional bracket character after 2nd function. Originally I pasted both functions but that second wasn't needed to following code so I removed it. Then I thought maybe one day you'll need it so I pasted it again, but did mistake putting one bracket too many. If you want to check that code works simply do 5 custom things in photoshop like pressing ctrl j x 5 and then use that code, so it select -5 (it may be any other number you enter to HstS() function) history state going back from current one and then 2nd function will delete this current history state with all (already grey ones) followed.
2) now when you found what was wrong in point 1, a code from point 2 will work too. It doesn't because I forgot to replace semicolon. When you start new 'sentence' with round bracket character then mostly everything in preceeding part need to be ended with semicolon. For example when it's ended with curly bracket then you don't need to use semicolon (but I'm not sure it's so in every case). So to make that test working you have to put semicolon after third alert expression, while that from before second alert may be removed, but nothing happens if it stays where it was put.
3) yes, I didn't remove additional bracket character after 2nd function. Originally I pasted both functions but that second wasn't needed to following code so I removed it. Then I thought maybe one day you'll need it so I pasted it again, but did mistake putting one bracket too many. If you want to check that code works simply do 5 custom things in photoshop like pressing ctrl j x 5 and then use that code, so it select -5 (it may be any other number you enter to HstS() function) history state going back from current one and then 2nd function will delete this current history state with all (already grey ones) followed.
Re: Creating and moving an artLayer inside "active" layerSet
1) indeed
2) That's also what I'm trying to figure out with JavaScript syntax, in the examples I'm learning from the book Eloquent Javascript (I'm still in the beginning), the author doesn't always add curly brackets and semicolon, I need to get this right.
3) And yes it worked when I tried, thanks a lot man !
Somehow I tried to copy the CAM layer and couldn't make the code to work, here's the best I could get, but still have too many steps in the history
(ps: I put the values of the variables from the reference script in there so you don't have to import them, it works by itself if the document is 1920 by 1364) :
It's not really a big issue to be honest, I had to put 3 steps to delete in the history to make it work so if there's no better solution to copy and paste the CAM layer with less history steps, then let's forget about it
2) That's also what I'm trying to figure out with JavaScript syntax, in the examples I'm learning from the book Eloquent Javascript (I'm still in the beginning), the author doesn't always add curly brackets and semicolon, I need to get this right.
3) And yes it worked when I tried, thanks a lot man !
Somehow I tried to copy the CAM layer and couldn't make the code to work, here's the best I could get, but still have too many steps in the history
(ps: I put the values of the variables from the reference script in there so you don't have to import them, it works by itself if the document is 1920 by 1364) :
Code: Select all
//Set Document
var docRef = activeDocument
aL = (aD = 'activeDocument') +'.activeLayer', bol = true, arr = []
while(bol) aL += '.parent', String(AL = eval(aL)).slice(1, 9) != 'LayerSet' ? bol = !bol : arr.push(AL.name)
aDl = aD + l = '.layers', n = arr.length - 1;
(function set() {
for(i = 0; i < (evl = eval(aDl)).length; i++) {
if (evl[i].name == arr[n]) {
aDl += '[i]' + l, n--, aD += l + '[' + i + ']'
if (n > -1) set(); break
}
}
})()
//Create Camera layer
L = eval("(aL = activeDocument.activeLayer).kind == 'LayerKind.NORMAL' ?\
((lay = aL.parent.layers).length == 1 ? 1 : (lay[0] == aL ? 1 : 2)) : 2")
lyr = eval(aD).artLayers.add(), eval('doc.activeHistoryState =\
(hS = (doc = activeDocument).historyStates)[hS.length - L]'), lyr.name = "CAM"
//Set Selection
var shapeRef = [
[0,0],
[0,1364 - 284],
[1920,1364 - 284],
[1920,0]
]
docRef.selection.select(shapeRef)
//Set Stroke Color
strokeColor = new SolidColor //Default color for the camera line
strokeColor.rgb.red = 0
strokeColor.rgb.green = 165
strokeColor.rgb.blue = 63
activeDocument.selection.stroke (strokeColor, 10, StrokeLocation.INSIDE, ColorBlendMode.NORMAL, 100, false)
docRef.selection.cut()
docRef.selection.deselect()
function cTT(v) {return charIDToTypeID(v)}; function sTT(v) {return stringIDToTypeID(v)}
function HstS(v) {// UNDOING HISTORY STATES:
(ref = new ActionReference()).putOffset(cTT('HstS'), 1 - v);
(dsc = new ActionDescriptor()).putReference(cTT('null'), ref)
executeAction(cTT('slct'), dsc, DialogModes.NO);
}
function HSD() {// DELETION OF CURRENT AND FOLLOWING HISTORY STATES:
(ref = new ActionReference()).putProperty(cTT('HstS'), cTT('CrnH'));
(dsc = new ActionDescriptor()).putReference(cTT('null'), ref)
executeAction(cTT('Dlt '), dsc, DialogModes.NO)
}
HstS(3), HSD()
var idpast = charIDToTypeID( "past" );
var desc557 = new ActionDescriptor();
var idinPlace = stringIDToTypeID( "inPlace" );
desc557.putBoolean( idinPlace, true );
var idAntA = charIDToTypeID( "AntA" );
var idAnnt = charIDToTypeID( "Annt" );
var idAnno = charIDToTypeID( "Anno" );
desc557.putEnumerated( idAntA, idAnnt, idAnno );
executeAction( idpast, desc557, DialogModes.NO );
Re: Creating and moving an artLayer inside "active" layerSet
I don't get what you want to do. I created new document 1920 x 1324 and played your script...
You created stroked selection, cut it, then deleted last history states to paste cut layer. You could get the same result if you stopped your script right after creating stroked selection. I don't understand why you had to delete those history states to paste earlier copied / cut layer at the end, so get the same you had meantime?
Maybe you wanted simply (literally, like you wrote) copy that created layer without cutting it (so removing, but keeping in memory)? Then you should replace cut with copy, ie. using activeDocument.selection.copy, or you asked about something else I didn't understand again? You may also use activeDocument.activeLayer.duplicate() instead of activeDocument.selection.copy (and then pasting ir) to finish your script in this line again without loosing your original CAM layer.
You created stroked selection, cut it, then deleted last history states to paste cut layer. You could get the same result if you stopped your script right after creating stroked selection. I don't understand why you had to delete those history states to paste earlier copied / cut layer at the end, so get the same you had meantime?
Maybe you wanted simply (literally, like you wrote) copy that created layer without cutting it (so removing, but keeping in memory)? Then you should replace cut with copy, ie. using activeDocument.selection.copy, or you asked about something else I didn't understand again? You may also use activeDocument.activeLayer.duplicate() instead of activeDocument.selection.copy (and then pasting ir) to finish your script in this line again without loosing your original CAM layer.
Re: Creating and moving an artLayer inside "active" layerSet
True, it's not clear and a bit messy...
At first the script stopped after the stroked selection in early versions, and it was fine.
But then I wanted to create that CAM layer with just one history state, so it doesn't clutter the cache (I often work with +50 layerSets on several psd files).
I just did the same thing with docRef.camLayer.duplicate() at the end of the script while removing the "paste in place" function but doesn't work, I added this line......in order to identify the CAM layer I want to duplicate, but it doesn't work properly, it creates the layer but without the stroke and ends in orange.
It worked with copy() but then it has just as many states in the history.
At first the script stopped after the stroked selection in early versions, and it was fine.
But then I wanted to create that CAM layer with just one history state, so it doesn't clutter the cache (I often work with +50 layerSets on several psd files).
I just did the same thing with docRef.camLayer.duplicate() at the end of the script while removing the "paste in place" function but doesn't work, I added this line...
Code: Select all
var camLayer = docRef.activeLayer
It worked with copy() but then it has just as many states in the history.
Re: Creating and moving an artLayer inside "active" layerSet
So in case of one .pds document with some layerSets all works fine, but when you have many opened(?) documents where each has some layerSets that information of copied CAM layer you put to memory is in some degree lost?
Well I never worked with so many documents, especially with so many layerSets, but maybe I can help. You only need to specify some case of minimal opened documents (or there is only one at once?) and folders it contains etc so I can reproduce it and see how it (doesn't) work(s). Otherwise it's hard to me to find solution for something I can't see.
Well I never worked with so many documents, especially with so many layerSets, but maybe I can help. You only need to specify some case of minimal opened documents (or there is only one at once?) and folders it contains etc so I can reproduce it and see how it (doesn't) work(s). Otherwise it's hard to me to find solution for something I can't see.