Skip to main content
EmojiStickers.com
Known Participant
June 2, 2024
Answered

Trying to fix my script to batch process 3400 files

  • June 2, 2024
  • 4 replies
  • 3664 views

I am trying to fix my script, but it is just not working. I attached a before and after file of what result I am seeking. I have over 3400 files to process. 

 

Basically, I need the script to do the following:

 

Move Cutlines layer (Top layer) below Artwork layer (Bottom layer)

Hide top layer, which is now Artwork

Select all on bottom layer, which is Cutlines

Set fill color to #FFFFFF

Set stroke color to #F5F5F5

Set stroke weight to 0.1 px

Select all

Apply drop shadow effect (Mode: Normal, Opacity: 100%, X Offset: 2px, Y Offset: 2px, Blur: 3px, and color #b4b4b4)

Show all layers

Select all

Export selection as PNG 1000ppi PNG 8

Save as eps file. 

 

The script below is what I have and it's just not working. 

// Prompt the user to select the source and destination folders
var sourceFolder = Folder.selectDialog("Select the folder with EPS files to process");
var destinationFolder = Folder.selectDialog("Select the destination folder to save processed files");

if (sourceFolder != null && destinationFolder != null) {
    var files = sourceFolder.getFiles("*.eps");
    for (var i = 0; i < files.length; i++) {
        var doc = app.open(files[i]);
        if (doc) {
            moveCutlinesBelowArtwork(doc);
            hideTopLayer(doc);
            processCutlinesLayer(doc);
            showAllLayers(doc);
            exportSelectionAsPNG(doc, destinationFolder, files[i].name);
            saveAsEPS(doc, destinationFolder, files[i].name);
            doc.close(SaveOptions.DONOTSAVECHANGES);
        } else {
            $.writeln("Could not open file: " + files[i].name);
        }
    }
    $.writeln("Processing complete!");
} else {
    $.writeln("Folder selection was cancelled.");
}

function moveCutlinesBelowArtwork(doc) {
    if (doc.layers.length >= 2) {
        var cutlinesLayer = doc.layers[0];
        var artworkLayer = doc.layers[1];
        cutlinesLayer.move(artworkLayer, ElementPlacement.PLACEAFTER);
    } else {
        $.writeln("Document does not have at least two layers.");
    }
}

function hideTopLayer(doc) {
    if (doc.layers.length >= 2) {
        var artworkLayer = doc.layers[0];
        artworkLayer.visible = false;
    } else {
        $.writeln("Document does not have at least two layers.");
    }
}

function processCutlinesLayer(doc) {
    var cutlinesLayer = doc.layers[doc.layers.length - 1]; // Ensure it's the bottom layer
    
    selectAllOnLayer(cutlinesLayer);

    for (var i = 0; i < cutlinesLayer.pageItems.length; i++) {
        var item = cutlinesLayer.pageItems[i];
        if (item.typename === "PathItem") {
            item.filled = true;
            item.fillColor = hexToRgbColor("#FFFFFF");
            item.stroked = true;
            item.strokeColor = hexToRgbColor("#F5F5F5");
            item.strokeWidth = 0.1;
        }
    }

    applyDropShadow();
}

function selectAllOnLayer(layer) {
    layer.hasSelectedArtwork = true;
    app.executeMenuCommand("group");
}

function hexToRgbColor(hex) {
    var rgb = new RGBColor();
    rgb.red = parseInt(hex.substring(1, 3), 16);
    rgb.green = parseInt(hex.substring(3, 5), 16);
    rgb.blue = parseInt(hex.substring(5, 7), 16);
    return rgb;
}

function applyDropShadow() {
    var dropShadowEffect = app.effects.getByName("Drop Shadow");
    var options = new DropShadowOptions();
    options.mode = ShadowMode.NORMAL;
    options.opacity = 100;
    options.xOffset = 2;
    options.yOffset = 2;
    options.blur = 3;
    options.color = hexToRgbColor("#b4b4b4");

    app.executeMenuCommand("Live Effects");
    app.executeMenuCommand("Drop Shadow");
}

function showAllLayers(doc) {
    for (var i = 0; i < doc.layers.length; i++) {
        doc.layers[i].visible = true;
    }
}

function exportSelectionAsPNG(doc, destinationFolder, fileName) {
    var exportOptions = new ExportOptionsPNG24();
    exportOptions.transparency = true;
    exportOptions.horizontalScale = 1000 / 72 * 100; // 1000 ppi
    exportOptions.verticalScale = 1000 / 72 * 100;   // 1000 ppi
    exportOptions.artBoardClipping = true;

    var file = new File(destinationFolder + "/" + fileName.replace(".eps", ".png"));
    doc.exportFile(file, ExportType.PNG24, exportOptions);
    $.writeln("Exported to PNG: " + fileName.replace(".eps", ".png"));
}

function saveAsEPS(doc, destinationFolder, fileName) {
    var epsOptions = new EPSSaveOptions();
    epsOptions.compatibility = Compatibility.ILLUSTRATOR10;
    epsOptions.preview = EPSPreview.None;
    epsOptions.cmykPostScript = false;
    epsOptions.embedAllFonts = true;
    epsOptions.includeDocumentThumbnails = true;
    epsOptions.saveMultipleArtboards = false;

    var file = new File(destinationFolder + "/" + fileName);
    doc.saveAs(file, epsOptions);
    $.writeln("Saved as EPS: " + fileName);
}

 

This topic has been closed for replies.
Correct answer Sergey Osokin

 

// Prompt the user to select the source and destination folders
var sourceFolder = Folder.selectDialog("Select the folder with EPS files to process");
var destinationFolder = Folder.selectDialog("Select the destination folder to save processed files");

if (sourceFolder != null && destinationFolder != null) {
  var files = sourceFolder.getFiles("*.eps");
  for (var i = 0; i < files.length; i++) {
    var doc = app.open(files[i]);
    if (doc) {
      moveCutlinesBelowArtwork(doc);
      processCutlinesLayer(doc);
      showAllLayers(doc);
      exportAsPNG(doc, destinationFolder, files[i].name, 1000);
      saveAsEPS(doc, destinationFolder, files[i].name);
      doc.close(SaveOptions.DONOTSAVECHANGES);
    } else {
      $.writeln("Could not open file: " + files[i].name);
    }
  }
  $.writeln("Processing complete!");
} else {
  $.writeln("Folder selection was cancelled.");
}

function moveCutlinesBelowArtwork(doc) {
  if (doc.layers.length >= 2) {
    var cutlinesLayer = doc.layers[0];
    var artworkLayer = doc.layers[1];
    cutlinesLayer.move(artworkLayer, ElementPlacement.PLACEAFTER);
  } else {
    $.writeln("Document does not have at least two layers.");
  }
}

function processCutlinesLayer(doc) {
  var cutlinesLayer = doc.layers[doc.layers.length - 1]; // Ensure it's the bottom layer

  for (var i = 0; i < cutlinesLayer.pageItems.length; i++) {
    var item = cutlinesLayer.pageItems[i];
    setAppearance(item);
  }

  cutlinesLayer.hasSelectedArtwork = true;
  app.executeMenuCommand("group");
  applyDropShadow(app.selection[0]);
}

function setAppearance(item) {
  if (item.typename === "GroupItem") {
    for (var i = 0; i < item.pageItems.length; i++) {
      setAppearance(item.pageItems[i]);
    }
  }

  if (item.typename === "CompoundPathItem" && item.pathItems.length > 0) {
    item = item.pathItems[0];
  }

  if (item.typename === "PathItem") {
    item.filled = true;
    item.fillColor = hexToRgbColor("#FFFFFF");
    item.stroked = true;
    item.strokeColor = hexToRgbColor("#F5F5F5");
    item.strokeWidth = 0.1;
  }
}

function hexToRgbColor(hex) {
  var rgb = new RGBColor();
  rgb.red = parseInt(hex.substring(1, 3), 16);
  rgb.green = parseInt(hex.substring(3, 5), 16);
  rgb.blue = parseInt(hex.substring(5, 7), 16);
  return rgb;
}

// Based on Live Effects Functions for Illustrator by m1b
// https://github.com/mark1bean/live-effect-functions-for-illustrator/
function applyDropShadow(item) {
  try {
    var rgb = hexToRgbColor("#B4B4B4");
    var data = {
      blendMode: 0, /* 0=Normal, 1=Multiply, 2=Darken, etc. */
      opacity: 1.0, /* 0...1 */
      horzOffsetPts: 2,
      vertOffsetPts: 2,
      blur: 3,
      useDarkness: false, /* if true, will use 'Color' */
      darkness: 100,
      usePSLBlur: true,
      pair: true,
      shadowColor: [rgb.red / 255, rgb.green / 255, rgb.blue / 255]
    }
    var xml = '<LiveEffect name="Adobe Drop Shadow"><Dict data="I blnd #1 R opac #2 R horz #3 R vert #4 R blur #5 B usePSLBlur #6 I csrc #7 R dark #8 B pair #9 "><Entry name="sclr" valueType="F"><Fill color="#10"/></Entry></Dict></LiveEffect>'
        .replace(/#1/, data.blendMode)
        .replace(/#2/, data.opacity)
        .replace(/#3/, data.horzOffsetPts)
        .replace(/#4/, data.vertOffsetPts)
        .replace(/#5/, data.blur)
        .replace(/#6/, data.usePSLBlur ? 1 : 0)
        .replace(/#7/, data.useDarkness ? 1 : 0)
        .replace(/#8/, data.darkness)
        .replace(/#9/, data.pair ? 1 : 0)
        .replace(/#10/, [5].concat(data.shadowColor).join(' '));
    item.selected = true;
    item.applyEffect(xml);
    app.redraw();
  } catch (err) {}
}

function showAllLayers(doc) {
  for (var i = 0; i < doc.layers.length; i++) {
    doc.layers[i].visible = true;
  }
}

function exportAsPNG(doc, destinationFolder, fileName, ppi) {
  if (isNaN(ppi)) ppi = 72;
  if (ppi > 2400) ppi = 2400;
  if (ppi < 72) ppi = 72;

  var exportOptions = new ImageCaptureOptions();
  exportOptions.resolution = ppi;
  exportOptions.antiAliasing = true;
  exportOptions.transparency = true;
  exportOptions.artBoardClipping = false;
  exportOptions.horizontalScale = 100;
  exportOptions.verticalScale = 100;

  var cutlinesLayer = doc.layers[doc.layers.length - 1];
  cutlinesLayer.hasSelectedArtwork = true;
  var selBnds = app.selection[0].visibleBounds;

  var file = new File(destinationFolder + "/" + fileName.replace(".eps", ".png"));
  doc.imageCapture(file, selBnds, exportOptions);
  $.writeln("Exported to PNG: " + fileName.replace(".eps", ".png"));
}

function saveAsEPS(doc, destinationFolder, fileName) {
  var epsOptions = new EPSSaveOptions();
  epsOptions.compatibility = Compatibility.ILLUSTRATOR10;
  epsOptions.preview = EPSPreview.None;
  epsOptions.cmykPostScript = false;
  epsOptions.embedAllFonts = true;
  epsOptions.includeDocumentThumbnails = true;
  epsOptions.saveMultipleArtboards = false;

  var file = new File(destinationFolder + "/" + fileName);
  doc.saveAs(file, epsOptions);
  $.writeln("Saved as EPS: " + fileName);
}

 

 

 

4 replies

Sergey Osokin
Sergey OsokinCorrect answer
Inspiring
June 3, 2024

 

// Prompt the user to select the source and destination folders
var sourceFolder = Folder.selectDialog("Select the folder with EPS files to process");
var destinationFolder = Folder.selectDialog("Select the destination folder to save processed files");

if (sourceFolder != null && destinationFolder != null) {
  var files = sourceFolder.getFiles("*.eps");
  for (var i = 0; i < files.length; i++) {
    var doc = app.open(files[i]);
    if (doc) {
      moveCutlinesBelowArtwork(doc);
      processCutlinesLayer(doc);
      showAllLayers(doc);
      exportAsPNG(doc, destinationFolder, files[i].name, 1000);
      saveAsEPS(doc, destinationFolder, files[i].name);
      doc.close(SaveOptions.DONOTSAVECHANGES);
    } else {
      $.writeln("Could not open file: " + files[i].name);
    }
  }
  $.writeln("Processing complete!");
} else {
  $.writeln("Folder selection was cancelled.");
}

function moveCutlinesBelowArtwork(doc) {
  if (doc.layers.length >= 2) {
    var cutlinesLayer = doc.layers[0];
    var artworkLayer = doc.layers[1];
    cutlinesLayer.move(artworkLayer, ElementPlacement.PLACEAFTER);
  } else {
    $.writeln("Document does not have at least two layers.");
  }
}

function processCutlinesLayer(doc) {
  var cutlinesLayer = doc.layers[doc.layers.length - 1]; // Ensure it's the bottom layer

  for (var i = 0; i < cutlinesLayer.pageItems.length; i++) {
    var item = cutlinesLayer.pageItems[i];
    setAppearance(item);
  }

  cutlinesLayer.hasSelectedArtwork = true;
  app.executeMenuCommand("group");
  applyDropShadow(app.selection[0]);
}

function setAppearance(item) {
  if (item.typename === "GroupItem") {
    for (var i = 0; i < item.pageItems.length; i++) {
      setAppearance(item.pageItems[i]);
    }
  }

  if (item.typename === "CompoundPathItem" && item.pathItems.length > 0) {
    item = item.pathItems[0];
  }

  if (item.typename === "PathItem") {
    item.filled = true;
    item.fillColor = hexToRgbColor("#FFFFFF");
    item.stroked = true;
    item.strokeColor = hexToRgbColor("#F5F5F5");
    item.strokeWidth = 0.1;
  }
}

function hexToRgbColor(hex) {
  var rgb = new RGBColor();
  rgb.red = parseInt(hex.substring(1, 3), 16);
  rgb.green = parseInt(hex.substring(3, 5), 16);
  rgb.blue = parseInt(hex.substring(5, 7), 16);
  return rgb;
}

// Based on Live Effects Functions for Illustrator by m1b
// https://github.com/mark1bean/live-effect-functions-for-illustrator/
function applyDropShadow(item) {
  try {
    var rgb = hexToRgbColor("#B4B4B4");
    var data = {
      blendMode: 0, /* 0=Normal, 1=Multiply, 2=Darken, etc. */
      opacity: 1.0, /* 0...1 */
      horzOffsetPts: 2,
      vertOffsetPts: 2,
      blur: 3,
      useDarkness: false, /* if true, will use 'Color' */
      darkness: 100,
      usePSLBlur: true,
      pair: true,
      shadowColor: [rgb.red / 255, rgb.green / 255, rgb.blue / 255]
    }
    var xml = '<LiveEffect name="Adobe Drop Shadow"><Dict data="I blnd #1 R opac #2 R horz #3 R vert #4 R blur #5 B usePSLBlur #6 I csrc #7 R dark #8 B pair #9 "><Entry name="sclr" valueType="F"><Fill color="#10"/></Entry></Dict></LiveEffect>'
        .replace(/#1/, data.blendMode)
        .replace(/#2/, data.opacity)
        .replace(/#3/, data.horzOffsetPts)
        .replace(/#4/, data.vertOffsetPts)
        .replace(/#5/, data.blur)
        .replace(/#6/, data.usePSLBlur ? 1 : 0)
        .replace(/#7/, data.useDarkness ? 1 : 0)
        .replace(/#8/, data.darkness)
        .replace(/#9/, data.pair ? 1 : 0)
        .replace(/#10/, [5].concat(data.shadowColor).join(' '));
    item.selected = true;
    item.applyEffect(xml);
    app.redraw();
  } catch (err) {}
}

function showAllLayers(doc) {
  for (var i = 0; i < doc.layers.length; i++) {
    doc.layers[i].visible = true;
  }
}

function exportAsPNG(doc, destinationFolder, fileName, ppi) {
  if (isNaN(ppi)) ppi = 72;
  if (ppi > 2400) ppi = 2400;
  if (ppi < 72) ppi = 72;

  var exportOptions = new ImageCaptureOptions();
  exportOptions.resolution = ppi;
  exportOptions.antiAliasing = true;
  exportOptions.transparency = true;
  exportOptions.artBoardClipping = false;
  exportOptions.horizontalScale = 100;
  exportOptions.verticalScale = 100;

  var cutlinesLayer = doc.layers[doc.layers.length - 1];
  cutlinesLayer.hasSelectedArtwork = true;
  var selBnds = app.selection[0].visibleBounds;

  var file = new File(destinationFolder + "/" + fileName.replace(".eps", ".png"));
  doc.imageCapture(file, selBnds, exportOptions);
  $.writeln("Exported to PNG: " + fileName.replace(".eps", ".png"));
}

function saveAsEPS(doc, destinationFolder, fileName) {
  var epsOptions = new EPSSaveOptions();
  epsOptions.compatibility = Compatibility.ILLUSTRATOR10;
  epsOptions.preview = EPSPreview.None;
  epsOptions.cmykPostScript = false;
  epsOptions.embedAllFonts = true;
  epsOptions.includeDocumentThumbnails = true;
  epsOptions.saveMultipleArtboards = false;

  var file = new File(destinationFolder + "/" + fileName);
  doc.saveAs(file, epsOptions);
  $.writeln("Saved as EPS: " + fileName);
}

 

 

 

EmojiStickers.com
Known Participant
June 3, 2024

Send an email to support@emojistickers.com.

I will send you out some sticker packs. You solved my problem. Thank you so much!!!

Sergey Osokin
Inspiring
June 3, 2024

1) Drop shadow effect can be realized by scripting.

2) I see that you have "Export selection to PNG" in your task description, but your script exports by artboard size to PNG, not by object size.

3) The top layer does not need to be hidden to set a new appearance (color, stroke, shadow) of the Cutlines layer contents.

EmojiStickers.com
Known Participant
June 3, 2024

Ok, I def only want to export the object, not the artboard. How do I do this?

 

Sergey Osokin
Inspiring
June 3, 2024

You're talking about 1000 ppi, but ChatGPT has just scaled the 512x512 px example to 7111x7111 px, and the resolution remains 72 dpi. But maybe you need to leave the PNG WxH as it is, but have the PNG have 1000 dpi?

Kurt Gold
Community Expert
Community Expert
June 2, 2024
EmojiStickers.com
Known Participant
June 2, 2024

"No-nonsense" clarifications?

Kurt Gold
Community Expert
Community Expert
June 2, 2024

Yes, no-nonsense.

 

Providing the entire Illustrator Preferences file is not very useful when you are asked to just provide an action set file (.aia) for inspection.

Inspiring
June 2, 2024

I’m guessing this script is AI-generated. The `applyDropShadow` function is 100% nonsense. There is no `app.effects` property in AI’s JSX API (not that that line does anything useful with the result), nor is there a `DropShadowOptions` constructor.

 

Take out that function and the rest of the script appears to run to completion (I won’t vouch that it produces the result you want).

 

I can’t think offhand of a way to apply a custom drop shadow via AI’s own automation—neither ExtendScript nor Actions can control that feature. There might be something in the C++ SDK. Or you might be able to manipulate AI’s GUI menus and dialogs using an external automation tool, e.g. AutoIt (Windows) or GUI Scripting (Mac), although that is another brittle mess entirely.

 

Better to find some other way to add the drop shadow element to the artwork. You’d need to provide more information and multiple examples.

EmojiStickers.com
Known Participant
June 2, 2024

Actually ChatGPT has written me scripts that have worked like a charm. Just can't figure this one out. And I provided before and after .ai files as examples.