Photoshop: Batch Replace Smart Objects - Script Error. Please Help

  • 2
  • Question
  • Updated 2 months ago
  • Answered
  • (Edited)
Dear All,

I've been looking for a Photoshop script for a long time, that could help me batch replace images in a smart object (essentially just trying to batch convert flat 1125x750px images to 3D images).

As I'm quite the Photoshop beginner, I had someone create a mockup file and he found an existing script to work with on these forums. 

So here's what I have:
  • a mockup file of an image set as a transformed smart object
  • a folder of images resized to fit said smart object
This is what I would like the script to do:

  • for every image in said folder
  • replace smart object with images
Your man sent me a video how to execute the script and it worked just fine on his computer (Windows 7). Problem is that it doesn't work on mine (Windows 7 and Windows 10). I've tried on several computers (some had better specs than his), but unfortunately to no avail. He used a legal version of Photoshop CC 2018 and so did I, so it wouldn't have to do with that. We both can't find the issue.

The error message that I get: ''executeAction(idplacedLayerReplaceContents, desc3, DialogModes.NO''. I use the following script:


// Replace SmartObject’s Content and Save as JPG
// 2017, use it at your own risk
// Via @Circle B: https://graphicdesign.stackexchange.com/questions/92796/replacing-a-smart-object-in-bulk-with-photos...
// JPG code from here: https://forums.adobe.com/thread/737789


#target photoshop
if (app.documents.length > 0) {
    var myDocument = app.activeDocument;
    var theName = myDocument.name.match(/(.*)\.[^\.]+$/)[1];
    var thePath = myDocument.path;
    var theLayer = myDocument.activeLayer;
    // JPG Options;
    jpgSaveOptions = new JPEGSaveOptions();  
    jpgSaveOptions.embedColorProfile = true;  
    jpgSaveOptions.formatOptions = FormatOptions.STANDARDBASELINE;  
    jpgSaveOptions.matte = MatteType.NONE;  
    jpgSaveOptions.quality = 8;   
    // Check if layer is SmartObject;
    if (theLayer.kind != "LayerKind.SMARTOBJECT") {
        alert("selected layer is not a smart object")
    } else {
        // Select Files;
        if ($.os.search(/windows/i) != -1) {
            var theFiles = File.openDialog("please select files", "*.psd;*.tif;*.jpg", true)
        } else {
            var theFiles = File.openDialog("please select files", getFiles, true)
        };
        if (theFiles) {
            for (var m = 0; m < theFiles.length; m++) {
                // Replace SmartObject
                theLayer = replaceContents(theFiles[m], theLayer);
                var theNewName = theFiles[m].name.match(/(.*)\.[^\.]+$/)[1];
                // Save JPG
                myDocument.saveAs((new File(thePath + "/" + theName + "_" + theNewName + ".jpg")), jpgSaveOptions, true,Extension.LOWERCASE);
            }
        }
    }
};
// Get PSDs, TIFs and JPGs from files
function getFiles(theFile) {
    if (theFile.name.match(/\.(psd|tif|jpg)$/i) != null || theFile.constructor.name == "Folder") {
        return true
    };
};
// Replace SmartObject Contents
function replaceContents(newFile, theSO) {
    app.activeDocument.activeLayer = theSO;
    // =======================================================
    var idplacedLayerReplaceContents = stringIDToTypeID("placedLayerReplaceContents");
    var desc3 = new ActionDescriptor();
    var idnull = charIDToTypeID("null");
    desc3.putPath(idnull, new File(newFile));
    var idPgNm = charIDToTypeID("PgNm");
    desc3.putInteger(idPgNm, 1);
    executeAction(idplacedLayerReplaceContents, desc3, DialogModes.NO);
    return app.activeDocument.activeLayer
};



Please find screenshots attached of the error message that I get + layers and channels at the moment the script fails. Please note that I've blurred out the smart object design as I paid for it - would like to keep it private and not for all to view.

If someone could help me out I'd really REALLY appreciate it. I've literally been caving myself into my apartment for the past 4 days trying to resolve this.
Photo of Bufu Mofo

Bufu Mofo

  • 3 Posts
  • 1 Reply Like

Posted 2 months ago

  • 2
Photo of Max Johnson

Max Johnson, Champion

  • 555 Posts
  • 288 Reply Likes
Tested and runs on a Win10 PC with Photoshop CC 2019. Test images were on desktop and did not include any special characters or spaces in the names or directories.

What *DID* break was if I had no layer selected at all, like you have in your screenshot. Have you tried running the script with the smart object layer selected in the layers panel?

If that doesn't fix it, I recommend saving a new document called test.psb with a new smart object in it and testing with a couple jpegs with really simple names like a.jpg, b.jpg off your desktop folder.  
Photo of Bufu Mofo

Bufu Mofo

  • 3 Posts
  • 1 Reply Like
Thank you for your reply. I selected the layer, ran the script again, and then a different pop up message came up (after about 10 mins. of loading) with the error attached.

While I initially thought it had something to do with my 3D settings not working properly, I downloaded a random free mockup with smart object elsewhere, followed your advice - loaded the script and it worked!

But what I still don't understand is that the specially designed mockup for 1125x750px images keeps showing errors, while it runs flawlessly with the script on the computer of the person who provided me with it. Sometimes I get the error as well as the faulty image attached - while it should obviously had to come out as a 3D object. 
Photo of Max Johnson

Max Johnson, Champion

  • 555 Posts
  • 288 Reply Likes
I hacked in a try/catch in there to make it able to skip and broken files, if its a particular file that is messing things up. It won't solve the problem if it's inherent in the template itself, but it'll let you bypass individual errors. 

main();
function main(){
if (app.documents.length > 0) {
    var myDocument = app.activeDocument;
    var theName = myDocument.name.match(/(.*)\.[^\.]+$/)[1];
    var thePath = myDocument.path;
    var theLayer = myDocument.activeLayer;
    // JPG Options;
    jpgSaveOptions = new JPEGSaveOptions();  
    jpgSaveOptions.embedColorProfile = true;  
    jpgSaveOptions.formatOptions = FormatOptions.STANDARDBASELINE;  
    jpgSaveOptions.matte = MatteType.NONE;  
    jpgSaveOptions.quality = 8;   
    // Check if layer is SmartObject;
    if (theLayer.kind != "LayerKind.SMARTOBJECT") {
        alert("selected layer is not a smart object")
    } else {
        // Select Files;
        if ($.os.search(/windows/i) != -1) {
            var theFiles = File.openDialog("please select files", "*.psd;*.tif;*.jpg", true)
        } else {
            var theFiles = File.openDialog("please select files", getFiles, true)
        };
        if (theFiles) {
            for (var m = 0; m < theFiles.length; m++) {
                // Replace SmartObject
                try {
                    theLayer = replaceContents(theFiles[m], theLayer);
                    var theNewName = theFiles[m].name.match(/(.*)\.[^\.]+$/)[1];
                    // Save JPG
                    myDocument.saveAs((new File(thePath + "/" + theName + "_" + theNewName + ".jpg")), jpgSaveOptions, true,Extension.LOWERCASE);
                } catch(e) {
                        if( !confirm("There was an error with "+theFiles[m].name+" ... skip and continue?") ){ return; }
                }
            }
        }
    }
};
}
// Get PSDs, TIFs and JPGs from files
function getFiles(theFile) {
    if (theFile.name.match(/\.(psd|tif|jpg)$/i) != null || theFile.constructor.name == "Folder") {
        return true
    };
};
// Replace SmartObject Contents
function replaceContents(newFile, theSO) {
    app.activeDocument.activeLayer = theSO;
    // =======================================================
    var idplacedLayerReplaceContents = stringIDToTypeID("placedLayerReplaceContents");
    var desc3 = new ActionDescriptor();
    var idnull = charIDToTypeID("null");
    desc3.putPath(idnull, new File(newFile));
    var idPgNm = charIDToTypeID("PgNm");
    desc3.putInteger(idPgNm, 1);
    executeAction(idplacedLayerReplaceContents, desc3, DialogModes.NO);
    return app.activeDocument.activeLayer
};
Photo of Bufu Mofo

Bufu Mofo

  • 3 Posts
  • 1 Reply Like
Thank you. Ran the script and when it finished a message popped up which basically said that the issue laid within the image itself, not the script. Eventually it turned out that the image its pixels were the same as the smart object image its pixels resolution, only the image resolution was not (72DPI opposed to 300DPI). Adjusted the DPI and it now works flawlessly. Thank you :)