Skip to main content
Participating Frequently
October 1, 2020
Answered

Issue duplicating compound path item on new layer

  • October 1, 2020
  • 4 replies
  • 1715 views

Hi, 

 

I have a script to auto create different colors of a sign. The first part runs fine. But, I then need to copy the path items to a new file/layer that uses an image for the background. When I run my script, it works great until it hits compound path items. When it does, it's filling in the enclosed text characters (see attached). 

 

Here is the code I'm using for the copy routine:

 

// Open the appropriate BMS file to process
var bmsFile = File.openDialog('Select the Brushed Stainless base image to use...');
if(bmsFile != null) {app.open(bmsFile);};

var srcDoc = app.documents[1];
var targetDoc = app.documents[0].layers.add();
var _sel = app.activeDocument.selection[0];

for (i=0; i<srcDoc.pathItems.length-1; i++) {
srcDoc.pathItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
}

 

I'm using Illustrator 2020

 

Thanks in advance for any help

This topic has been closed for replies.
Correct answer Silly-V

Oh, duh, this could only work when targeting a specific layer.

Assuming your document has one layer, or the art is on the 1st layer,

for (i = 0;  i < srcDoc.layers[0].pageItems.length - 1; i++) {
  if (srcDoc.layers[0].pageItems[i].typename == "PathItem" || srcDoc.layers[0].pageItems[i].typename == "CompoundPathItem") {
    srcDoc.layers[0].pageItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
  }
}

4 replies

Silly-V
Brainiac
October 2, 2020

Change this:

for (i=0; i<srcDoc.pathItems.length-1; i++) {
srcDoc.pathItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
}

 

To this:

for (i = 0;  i < srcDoc.pageItems.length - 1; i++) {
  if (srcDoc.pageItems[i].typename == "PathItem" || srcDoc.pageItems[i].typename == "CompoundPathItem") {
    srcDoc.pageItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
  }
}
Participating Frequently
October 2, 2020

Maybe this will help...here's the full script. The basics are this...I open Illustrator, select this script, open a product AI file to change the background color/text colors (there are more colors, but wanted a simple test), then open a brushed stainless background template AI file and copy the black text and braille dots over. Because the word 'ROUTE' has 2 compound paths - the R & O, it fails to properly copy them over. The enclosed areas are filled in. 

 

Results:

 

Full script

 

#target illustrator

// Color array
var pColorNames = ['blue', 'black', 'white'];
var pRed = [ 0, 16, 255];
var pGreen = [ 75, 24, 255];
var pBlue = [135, 32, 255];

// Returns just file name
//alert('File name: ' + app.activeDocument.name);

// Returns full path & file name
//alert('File name: ' + app.activeDocument.fullName);

// Open the file to porcess
var myFile = File.openDialog('Select the product file to process...');
if(myFile != null) {app.open(myFile);};

// Get file name without full path and change extension to 'jpg'
var tempFileName = myFile.name.replace('.ai','.png');

// Get active document
var doc = app.activeDocument;


// Extract destination directory and save
var fullName = myFile.fsName;
var dFolder = fullName.substring(0, fullName.lastIndexOf("\\"));
var destFolder = dFolder.concat('\\images\\');

// Create images folder if it doesn't exist
var imgFolder = Folder(destFolder);
if (!imgFolder.exists) imgFolder.create();

//////////////////////////////////////////////////////////////////////
// Loop for WHITE raised signs
//////////////////////////////////////////////////////////////////////
var NewFileName;

for (x=0; x<=1; x++) {
workTheMagic();
};

////////////////////////////////////////////////////////////////////
// Loop for BLACK raised signs
////////////////////////////////////////////////////////////////////

var blkColor = new CMYKColor();
blkColor.cyan = 75;
blkColor.magenta = 68;
blkColor.yellow = 67;
blkColor.black = 90;

// Change raised objects to black
for (x=0; x<doc.pathItems.length; x++) {
if (doc.pathItems[x].fillColor.cyan == 0 && doc.pathItems[x].fillColor.magenta == 0 && doc.pathItems[x].fillColor.yellow == 0 && doc.pathItems[x].fillColor.black == 0 ) {
doc.pathItems[x].fillColor = blkColor;
};
};

for (x=2; x<=2; x++) {
workTheMagic();
};

//////////////////////////////////////////////////////////////////////////////////
// Special stuff for BRUSHED STAINLESS sign
//////////////////////////////////////////////////////////////////////////////////

// Open the appropriate BMS file to process
var bmsFile = File.openDialog('Select the Brushed Stainless base image to use...');
if(bmsFile != null) {app.open(bmsFile);};

var srcDoc = app.documents[1];
var targetDoc = app.documents[0].layers.add();

for (i=0; i<srcDoc.pathItems.length-1; i++) {
srcDoc.pathItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
}


// Change file name
newFileName = tempFileName;
newFileName = newFileName.replace('xxx', 'brushed-stainless');

// Create new export file
var tFile = new File(destFolder + '/' + newFileName);

// Export file as GIF to product image folder
exportToPNGFile (tFile);


/////////////////////////////////////////////////////////////////////////////////////
// Close documents
//////////////////////////////////////////////////////////////////////////////////
var aiDocument;

aiDocument = app.activeDocument;
aiDocument.close( SaveOptions.DONOTSAVECHANGES );
aiDocument = null;

///////////////////////////////////////////////////////////////////////////////////////////////////////////

function workTheMagic() {
// Change file name
newFileName = tempFileName;
newFileName = newFileName.replace('xxx', pColorNames[x]);

// Create new export file
var tFile = new File(destFolder + '/' + newFileName);

// Change color of background
doc.pathItems[doc.pathItems.length-1].fillColor = makeColor(pRed[x], pGreen[x], pBlue[x]);

// Export file as GIF to product image folder
exportToPNGFile (tFile);

}

///////////////////////////////////////////////////////////////////////////////////////////////////////////

// Create new RGB color object
function makeColor(r,g,b) {
var c = new RGBColor();
c.red = r;
c.green = g;
c.blue = b;
return c;
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////

function exportToPNGFile(dest) {
if ( app.documents.length > 0 ) {

var exportOptions = new ExportOptionsPNG8();

// set PNG export options
exportOptions.antiAliasing = true;
exportOptions.transparency = true;
exportOptions.artBoardClipping = true;
exportOptions.horizontalScale = 100;
exportOptions.verticalScale = 100;

// export and save file
doc.exportFile ( dest, ExportType.PNG8, exportOptions );
}
}

Participating Frequently
October 2, 2020

Oh, duh, this could only work when targeting a specific layer.

Assuming your document has one layer, or the art is on the 1st layer,

for (i = 0;  i < srcDoc.layers[0].pageItems.length - 1; i++) {
  if (srcDoc.layers[0].pageItems[i].typename == "PathItem" || srcDoc.layers[0].pageItems[i].typename == "CompoundPathItem") {
    srcDoc.layers[0].pageItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
  }
}

Hey Silly-V, 

 

Just used your last script change (big thanks)  and this is what I got: 

 

The weirdness continues...

renél80416020
Inspiring
October 2, 2020

Salut!

Peut-être tout simplement:

Si les éléments à dupliquer sont contenus dans un groupe, sélectionnez ce groupe et lancer la sript qui suit.

// JavaScript Document for Illustrator
var srcDoc = app.activeDocument;
var _sel = selection[0]; // alert(_sel)
var bmsFile = File.openDialog();
var targetDoc = app.open(bmsFile);
var targetLayer = targetDoc.layers.add();
  _ sel.duplicate(targetLayer, ElementPlacement.PLACEATBEGINNING);

 

CarlosCanto
Community Expert
October 2, 2020

if you provide a sample file it could help speed things up.

femkeblanco
Brainiac
October 1, 2020

The last three lines would copy the pathItems in compoundPathItems, not the compoundPathItems themselves.  To copy the compoundPathItems themselves:

for (var i = 0; i < srcDoc.compoundPathItems.length; i++) {
  srcDoc.compoundPathItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
}

 

Participating Frequently
October 1, 2020

Thanks femkeblanco, 

 

Definitely headed in the right direction. I replaced the pathItem lines with your code and got the 1st image. Soooo, how do I get both the pathItems and the compoundPathItems. If I use my code and yours I still get the 2nd image. I'm guessing there needs some sort of typename check but am unclear how to do that. 

femkeblanco
Brainiac
October 1, 2020
for (var i = 0; i < srcDoc.pathItems.length; i++) {
  if (srcDoc.pathItems[i].parent.typename == "CompoundPathItem") {
  continue;}
  srcDoc.pathItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
}

for (var i = 0; i < srcDoc.compoundPathItems.length; i++) {
  srcDoc.compoundPathItems[i].duplicate(targetDoc, ElementPlacement.PLACEATBEGINNING);
}