• Global community
    • Language:
      • Deutsch
      • English
      • Español
      • Français
      • Português
  • 日本語コミュニティ
    Dedicated community for Japanese speakers
  • 한국 커뮤니티
    Dedicated community for Korean speakers
Exit
0

Looking to select all items on the layer "Text Layer" and then run pathfinder subtract

Community Beginner ,
May 05, 2023 May 05, 2023

Copy link to clipboard

Copied

I'm trying to write a script that selects all items on the layer "Text Layer" and then run pathfinder subtract.  Here is what I have but it continue to error out.  Any help would be appreciated.  

 

I'm getting Error Number: 1287 

Error String: Cannot determine the spread this object is on. It might be an anchored object the is in overset or uncomposed text 

Line: 5

Sourc: textLayer.pageItems.everyItem().select();

 

 

var doc = app.activeDocument;
var textLayer = doc.layers.itemByName("Text Layer");

textLayer.pageItems.everyItem().select();

app.executeMenuCommand("Minus Front");
TOPICS
Scripting

Views

1.3K

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 05, 2023 May 05, 2023

Copy link to clipboard

Copied

If the items are on multiple pages, select won't work. Instead iterate through the items and select individually. 

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Beginner ,
May 05, 2023 May 05, 2023

Copy link to clipboard

Copied

Is there a way to do that with a script?  I'm outlining all the text on that layer and then I want it to select all items.  In this case there are 3 items, first name last  name and a white box below those.  We're hoping that we can select all those items and then apply the pathfinder subtract so it creates a mask essentially.  

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 05, 2023 May 05, 2023

Copy link to clipboard

Copied

I'm not JS guy so can't give you working code, but you need to iterate through the collection of PageItems, push all that are on the same page and same layer and then use what you've found for selection. 

 

▒► ID-Tasker / ID-Tasker Server - work smart not hard ◄▒

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 06, 2023 May 06, 2023

Copy link to clipboard

Copied

As Brian and Robert mentioned, you need to work page by page. On each page get the frames on the text layer, then use InDesign's subtractPath() method:

function textLayerFrames (page) {
  var f = page.pageItems.everyItem().getElements();
  var a = [];
  for (var i = 0; i < f.length; i++) {
    if (f[i].itemLayer.name === 'Text Layer') {
      a.push (f[i]);
    }
  }
  return a;
}

pages = app.documents[0].pages.everyItem().getElements();
for (i = 0; i < pages.length; i++) {
  frames = textLayerFrames (pages[i]);
  frames[0].subtractPath (frames);
}

 You're not working with any selection here. Working with selections should really be avoided as much as possible, working with script functions such as subtractPath() are much more robust.

 

P.

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Beginner ,
May 08, 2023 May 08, 2023

Copy link to clipboard

Copied

Peter,

Thanks for this.  It seems to be almost doing what I would like, just in reverse.  I've attached images of the goal vs what is happening once I run the script.  Pervious to this I outline all the text in the doc.  

 

This image is where we start.  The outlined text are compound objects then the white box.  

 

ss1.jpg

 

This image is if I select the three items on the Text Layer (ctrl-a) and then run pathfinder subtract. This is the final look we are trying to achieve across the entire document.  

ss2 hopeful final.jpg

 

This is the result I'm getting when I run the script. 

ss after script run.jpg

 

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 08, 2023 May 08, 2023

Copy link to clipboard

Copied

Because script have no idea which object should be used as a reference. 

And it probably should combine TextObjects first then cut it from the white box. 

 

▒► ID-Tasker / ID-Tasker Server - work smart not hard ◄▒

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 08, 2023 May 08, 2023

Copy link to clipboard

Copied

Robert is probably right: it's a matter of the stacking order of the objects and how a script orders the objects. Can you show the content of the text layer? Is the image on that layer or somewhere else? Maybe post your document (or a small representative sample).

 

Actually, try replacing subtractPath with excludeOverlapPath and see whether makes a difference.

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Participant ,
May 10, 2023 May 10, 2023

Copy link to clipboard

Copied

After some test, i think that the problem is the order of the elements of the array.

 

Given three objects (Rectangle (white frame), polygon (outlined text), textFrame) it doesn’t matter how they are stacked in the ‘Text Layer’, their order in the array is always the same: rectangle, polygon, textframe. 

 

You have to rearrange the array and then the script works.

 

function textLayerFrames (page) {
  var f = page.pageItems.everyItem().getElements();
  var a = [];
  for (var i = 0; i < f.length; i++) {
    if (f[i].itemLayer.name === 'Text Layer') {
      a.push (f[i]);
    }
  }
  alert(a);
  var b = [];
  b.push(a[2]);
  b.push(a[1]);
  b.push(a[0]);
  alert(b);
  return b;
}

pages = app.documents[0].pages.everyItem().getElements();
for (i = 0; i < pages.length; i++) {
  frames = textLayerFrames (pages[i]);
  frames[0].subtractPath (frames);
}

 

 

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 10, 2023 May 10, 2023

Copy link to clipboard

Copied

Elements in the collection are always ordered by the creation order.

 

To be honest I don't understand why the script works - maybe InDesign is simply ignoring the fact that in your array you have the same object that you are using as the "reference" point - would be much safer - and correct - if your array won't contain white rectangle at all - just the outlined text and TF. 

 

▒► ID-Tasker / ID-Tasker Server - work smart not hard ◄▒

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Participant ,
May 10, 2023 May 10, 2023

Copy link to clipboard

Copied

Hi @Robert Tkaczyk.

As you can see in the 3 cols. image, it doesn't matter the creation order (in my case, copy and paste).

Array 'a' has always the same order: rectangle, polygon, text frame.

I don't know why.

Sin-título-12.jpg

 

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 11, 2023 May 11, 2023

Copy link to clipboard

Copied

Stacking order is elusive. It was discussed in this forum some years ago, and its behaviour changed at some stage. An experiment now shows that pageItems and allPageItems show different behaviour w.r.t. stacking order. Take this situation:

PeterKahrel_0-1683794423036.png

Two rectangles and two text frames. The 0 and 1 suffixes denote the order of creation. The frames in the screenshot were moved around a bit (order of creation was texxt frame 0, text frame 1, rectangle 0, rectangle 1).

 

This script:

items = app.documents[0].pageItems.everyItem().getElements();
for (i = 0; i < items.length; i++) {
  $.writeln (items[i].name + ' -- ' + items[i].index);
}

prints this in the console:

 

rectangle 1 -- 0

rectangle 0 -- 1
text frame 0 -- 0
text frame 1 -- 1

 

That is, no matter the creation order, the order is the order in the Layers panel but grouped by item type: rectangles before text frames.

 

However, this script

items = app.documents[0].allPageItems;
for (i = 0; i < items.length; i++) {
  $.writeln (items[i].name + ' -- ' + items[i].index);
}

prints the items in the order shown in the Layers panel:

 

text frame 0 -- 0
rectangle 1 -- 0
text frame 1 -- 1
rectangle 0 -- 1

 

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Participant ,
May 11, 2023 May 11, 2023

Copy link to clipboard

Copied

LATEST

@Peter Kahrel thank you for the explanation.

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
May 11, 2023 May 11, 2023

Copy link to clipboard

Copied

So, what happens if you replace

var f = page.pageItems.everyItem().getElements();

with

var f = page.allPageItems;

in the script above? If you see the reverse of what you expect, then reverse the array by using  unshift() instead of push(): replace

a.push (f[i]);

with

a.unshift (f[i]);

Which of course is pretty whacky. You could also try a different pathfinder method (minusBack(), intersectPath(), etc.).

 

P.

Votes

Translate

Translate

Report

Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines