Copy link to clipboard
Copied
I have a PS file that has about 30 photos all arranged in little columns and rows. Each photo has text associated with it, a name and a date. Every photo and every bit of text is on it's own layer. Is there a way for Photoshop to take all these layers and just scramble them up/randomly distribute them?
I've seen stuff about Random Fill, but I don't think that's what I want. And I've seen stuff about creating your own paintbrush, but I don't think that's what I want either. I want whatever the Photoshop equivalent is of nicely lining up a bunch of stuff on the bottom of a box, putting the lid on, and then shaking it. Is that even possible?
Copy link to clipboard
Copied
Can you post screenshot with some examples?
If I can understand what you want to do then only script can help you. I will tag few scripters @c.pfaffenbichler @Stephen_A_Marsh @r-bin @jazz-y
Copy link to clipboard
Copied
Yes! I'm sorry, here is a screenshot. I'm still fairly new to Photoshop so I'm not sure if this is sufficient, so please let me know if you need me to screenshot anything else!
Copy link to clipboard
Copied
Oops, I posted too soon.
But what I basically want is all those photos and text layers to just get randomly scattered an image. Imagine that each layer, whether it's a text or image layer, were all printed out on individual pieces of paper, and I just took them all threw them on the ground. They'd just be randomly and messily distributed across an area. That's what I want my final image to look like.
Copy link to clipboard
Copied
For a start, you can try these:
https://www.reddit.com/r/photoshop/comments/5kajgh/how_to_shuffle_layers/
Info on saving and using scripts:
https://prepression.blogspot.com/2017/11/downloading-and-installing-adobe-scripts.html
Copy link to clipboard
Copied
Would you consider building this project in InDesign or must it be in Photoshop?
Copy link to clipboard
Copied
Honestly, I'm not sure. I've never used InDesign, and I'm still fairly new to Photoshop! If you have some very beginner friendly tutorials on how I could do this, I'd be happy to give it a shot!
Copy link to clipboard
Copied
Could you please post screenshots with the pertinent Panels (Toolbar, Layers, Options Bar, …) visible?
If the Layers with name and date should stick with the Layer with the image how can they unequivocally be collated?
Copy link to clipboard
Copied
Sure! I'm still pretty new to Photoshop, so I don't know if this is what you need, so please let me know if you need screen shots of anything else!
And I'm not sure what you mean, but I don't want the names and dates to stick with their images. Imagine if every single layer, whether it's an image or text, were printed out on individual pieces of paper, and I just threw them on the ground. That's what I want. I just want all the layers to be scattered randomly across the image I want to create.
Copy link to clipboard
Copied
This is good candidate for data driven graphics. If you can not get job done with some script take a look at variables and data sets which can be formated to place "random" images or images at different layer positions with corresponding captions.
Copy link to clipboard
Copied
This might cause problems with Adjustment Layers, but in your example there don’t seem to be any.
// randomly place layers;
// 2023, use it at your own risk;
if (app.documents.length > 0) {
var originalRulerUnits = app.preferences.rulerUnits;
app.preferences.rulerUnits = Units.PIXELS;
var myDocument = activeDocument;
var theLayers = collectLayersBounds ();
var docWidth = myDocument.width;
var docHeight = myDocument.height;
var docCenter = [docWidth/2, docHeight/2];
for (var m = 0; m < theLayers.length; m++) {
var thisOne = theLayers[m];
var theId = duplicateMoveRotateScale (false, theLayers[m][1], Math.random()*(docWidth-thisOne[3])-thisOne[5][0]+thisOne[3]/2, Math.random()*(docHeight-thisOne[4])-thisOne[5][1]+thisOne[4]/2, 100, 100, Math.random()*360)
theLayers[m][1] = theId;
};
app.preferences.rulerUnits = originalRulerUnits;
};
////// collect layers //////
function collectLayersBounds () {
// get number of layers;
var ref = new ActionReference();
ref.putEnumerated( charIDToTypeID("Dcmn"), charIDToTypeID("Ordn"), charIDToTypeID("Trgt") );
var applicationDesc = executeActionGet(ref);
var theNumber = applicationDesc.getInteger(stringIDToTypeID("numberOfLayers"));
// process the layers;
var theLayers = new Array;
for (var m = 0; m <= theNumber; m++) {
try {
var ref = new ActionReference();
ref.putIndex( charIDToTypeID( "Lyr " ), m);
var layerDesc = executeActionGet(ref);
var layerSet = typeIDToStringID(layerDesc.getEnumerationValue(stringIDToTypeID("layerSection")));
var isBackground = layerDesc.getBoolean(stringIDToTypeID("background"));
// if group collect values;
if (layerSet != "layerSectionEnd" && layerSet != "layerSectionStart" && isBackground != true) {
var theName = layerDesc.getString(stringIDToTypeID('name'));
var theID = layerDesc.getInteger(stringIDToTypeID('layerID'));
var theBounds = layerDesc.getObjectValue(stringIDToTypeID("bounds"));
var theseBounds = [theBounds.getUnitDoubleValue(stringIDToTypeID("left")), theBounds.getUnitDoubleValue(stringIDToTypeID("top")), theBounds.getUnitDoubleValue(stringIDToTypeID("right")), theBounds.getUnitDoubleValue(stringIDToTypeID("bottom"))];
var theWidth = theseBounds[2] - theseBounds[0];
var theHeight = theseBounds[3] - theseBounds[1];
var theCenter = [theseBounds[0]+theWidth/2, theseBounds[1]+theHeight/2];
theLayers.push([theName, theID, theseBounds, theWidth, theHeight, theCenter])
};
}
catch (e) {};
};
return theLayers
};
////// duplicate layer and move, rotate and scale it //////
function duplicateMoveRotateScale (copyOrNot, theID, theX, theY, theScaleX, theScaleY, theRotation) {
selectLayerByID(theID,false);
smartify (activeDocument.activeLayer);
var ref = new ActionReference();
ref.putProperty (stringIDToTypeID ("property"), charIDToTypeID ("LyrI"));
ref.putEnumerated(charIDToTypeID("Lyr "), charIDToTypeID("Ordn"), charIDToTypeID("Trgt"));
d = executeActionGet(ref);
var theID = d.getInteger(charIDToTypeID('LyrI'));
try{
var idTrnf = charIDToTypeID( "Trnf" );
var desc10 = new ActionDescriptor();
var idnull = charIDToTypeID( "null" );
var ref6 = new ActionReference();
ref6.putIdentifier( charIDToTypeID( "Lyr " ), theID );
/* ref6.putEnumerated( charIDToTypeID( "Lyr " ), charIDToTypeID( "Ordn" ), charIDToTypeID( "Trgt" ) );*/
desc10.putReference( idnull, ref6 );
var idFTcs = charIDToTypeID( "FTcs" );
var idQCSt = charIDToTypeID( "QCSt" );
var idQcsa = charIDToTypeID( "Qcsa" );
desc10.putEnumerated( idFTcs, idQCSt, idQcsa );
var idOfst = charIDToTypeID( "Ofst" );
var desc11 = new ActionDescriptor();
var idHrzn = charIDToTypeID( "Hrzn" );
var idPxl = charIDToTypeID( "#Pxl" );
desc11.putUnitDouble( idHrzn, idPxl, theX );
var idVrtc = charIDToTypeID( "Vrtc" );
var idPxl = charIDToTypeID( "#Pxl" );
desc11.putUnitDouble( idVrtc, idPxl, theY );
var idOfst = charIDToTypeID( "Ofst" );
desc10.putObject( idOfst, idOfst, desc11 );
var idWdth = charIDToTypeID( "Wdth" );
var idPrc = charIDToTypeID( "#Prc" );
desc10.putUnitDouble( idWdth, idPrc, theScaleX );
var idHght = charIDToTypeID( "Hght" );
var idPrc = charIDToTypeID( "#Prc" );
desc10.putUnitDouble( idHght, idPrc, theScaleY );
var idAngl = charIDToTypeID( "Angl" );
var idAng = charIDToTypeID( "#Ang" );
desc10.putUnitDouble( idAngl, idAng, theRotation );
var idIntr = charIDToTypeID( "Intr" );
var idIntp = charIDToTypeID( "Intp" );
var idbicubicAutomatic = stringIDToTypeID( "bicubicAutomatic" );
desc10.putEnumerated( idIntr, idIntp, idbicubicAutomatic );
var idCpy = charIDToTypeID( "Cpy " );
desc10.putBoolean( idCpy, copyOrNot );
executeAction( idTrnf, desc10, DialogModes.NO );
//var thisCopy = app.activeDocument.activeLayer;
return theID
} catch (e) {}
};
////// function to smartify if not //////
function smartify (theLayer) {
// make layers smart objects if they are not already;
if (theLayer.kind != LayerKind.SMARTOBJECT) {
activeDocument.activeLayer = theLayer;
var id557 = charIDToTypeID( "slct" );
var desc108 = new ActionDescriptor();
var id558 = charIDToTypeID( "null" );
var ref77 = new ActionReference();
var id559 = charIDToTypeID( "Mn " );
var id560 = charIDToTypeID( "MnIt" );
var id561 = stringIDToTypeID( "newPlacedLayer" );
ref77.putEnumerated( id559, id560, id561 );
desc108.putReference( id558, ref77 );
executeAction( id557, desc108, DialogModes.NO );
return activeDocument.activeLayer
};
return theLayer
};
// based on code by mike hale, via paul riggott;
function selectLayerByID(id,add){
add = undefined ? add = false:add
var ref = new ActionReference();
ref.putIdentifier(charIDToTypeID("Lyr "), id);
var desc = new ActionDescriptor();
desc.putReference(charIDToTypeID("null"), ref );
if(add) desc.putEnumerated( stringIDToTypeID( "selectionModifier" ), stringIDToTypeID( "selectionModifierType" ), stringIDToTypeID( "addToSelection" ) );
desc.putBoolean( charIDToTypeID( "MkVs" ), false );
try{
executeAction(charIDToTypeID("slct"), desc, DialogModes.NO );
}catch(e){
alert(e.message);
}
};
Copy link to clipboard
Copied
If it should be necessary to avoid rotated Layers to extend beyond the Canvas’ edges it would be possible to split the rotation and the moving into two operations, so that the Bounding Box resulting from the rotation is known before moving.