Copy link to clipboard
Copied
Hello,
I have a script which counts how many things are in a group.
Is it becuase indesign is reading a parent bound plus the image inside the rectangle, PLUS the blue box, so there is three things?
I have the following code and am struggling to know how to intergrate a group which has an image and another thing
My thought was to adjust this part
if (item instanceof Group && item.allPageItems.length === 2) to have OR group selection of image, bounding rectangle, and other thing then ... but I'm just not getting anywhere
Any advice would be great
Thanks
Smyth
app.doScript(function() {
// Get the active document
var doc = app.activeDocument;
// Get document grid preferences
var gridPreferences = doc.gridPreferences;
var baselineIncrement = gridPreferences.baselineDivision;
// Add a precision threshold to handle floating-point precision issues
var precisionThreshold = 0.1; // This helps to avoid errors when height is close to baselineIncrement
// Function to adjust height
function adjustHeight(item) {
var currentHeight = item.geometricBounds[2] - item.geometricBounds[0];
if (currentHeight > baselineIncrement + precisionThreshold) {
// Reduce the bottom edge to shrink the height
if (item instanceof Image && item.parent instanceof Rectangle) {
adjustHeight(item.parent); // Adjust the height of the parent frame, not the image itself
} else {
item.geometricBounds = [
item.geometricBounds[0],
item.geometricBounds[1],
item.geometricBounds[2] - baselineIncrement,
item.geometricBounds[3]
];
}
} else {
// Move the item upwards if its height is equal to or less than one baseline (within threshold)
var moveAmount = Math.abs(baselineIncrement); // Ensure positive value
item.geometricBounds = [
item.geometricBounds[0] - moveAmount,
item.geometricBounds[1],
item.geometricBounds[2] - moveAmount,
item.geometricBounds[3]
];
}
}
// Function to find and assign smaller and larger items in a group of two
function findSmallerGroupItem(group) {
var groupItem1 = group.allPageItems[0];
var groupItem2 = group.allPageItems[1];
var heightItem1 = groupItem1.geometricBounds[2] - groupItem1.geometricBounds[0];
var heightItem2 = groupItem2.geometricBounds[2] - groupItem2.geometricBounds[0];
var smallGroupItem, largeGroupItem;
// Compare heights and assign smaller and larger
if (heightItem1 < heightItem2) {
smallGroupItem = groupItem1;
largeGroupItem = groupItem2;
} else {
smallGroupItem = groupItem2;
largeGroupItem = groupItem1;
}
return {
smallGroupItem: smallGroupItem,
largeGroupItem: largeGroupItem
};
}
// Function to resize and center the smaller group item
function resizeAndCenterSmallerGroupItem(smallGroupItem, largeGroupItem) {
var largeTop = largeGroupItem.geometricBounds[0];
var largeBottom = largeGroupItem.geometricBounds[2];
var largeCenter = (largeTop + largeBottom) / 2;
// Calculate the new height and top position for the smaller item
var smallWidth = smallGroupItem.geometricBounds[3] - smallGroupItem.geometricBounds[1];
var smallNewTop = largeCenter - (baselineIncrement / 2);
// Resize the smaller item to match baseline increment
smallGroupItem.geometricBounds = [
smallNewTop,
smallGroupItem.geometricBounds[1],
smallNewTop + baselineIncrement,
smallGroupItem.geometricBounds[3]
];
// Adjust the smaller item’s horizontal position if necessary
var currentBounds = smallGroupItem.geometricBounds;
smallGroupItem.geometricBounds = [
currentBounds[0],
currentBounds[1],
currentBounds[2],
currentBounds[3] // No horizontal adjustment needed in this case
];
}
// Function to process each item or group recursively
function processItem(item) {
if (item instanceof Group && item.allPageItems.length === 2) {
// If the item is a group with exactly two items, find smaller and larger items
var groupItems = findSmallerGroupItem(item);
// Resize and center the smaller item within the larger item
resizeAndCenterSmallerGroupItem(groupItems.smallGroupItem, groupItems.largeGroupItem);
// Now adjust the height of the larger item as well
adjustHeight(groupItems.largeGroupItem);
} else if (item instanceof GraphicLine || item instanceof TextFrame || item instanceof Rectangle) {
adjustHeight(item);
} else if (item instanceof Group) {
for (var j = 0; j < item.allPageItems.length; j++) {
processItem(item.allPageItems[j]);
}
} else if (item instanceof Image) {
// Check if the image is inside a rectangle (frame)
var parent = item.parent;
if (parent instanceof Rectangle) {
adjustHeight(parent);
} else {
adjustHeight(item);
}
} else {
alert("Selection contains unsupported items. Please select only vertical rules, text frames, picture boxes, or groups.");
}
}
// Check if there are any selected objects
if (app.selection.length === 0) {
alert("Please select one or more vertical rules, text frames, picture boxes, or groups.");
} else {
// Iterate over all selected objects
for (var i = 0; i < app.selection.length; i++) {
processItem(app.selection[i]);
}
}
}, ScriptLanguage.JAVASCRIPT, null, UndoModes.ENTIRE_SCRIPT, "Adjust Item Height Based on Baseline Increment");
PageItems:
AllPageItems:
Hi @SmythWharf , Also, as @Robert at ID-Tasker , suggests .allPageItems returns an array (not a collection) of all objects inside of the group, while .pageItems returns a collection of the top level objects that are page items inside the group.
So here on a selected group, .allPageItems gets the image, its container frame, and the text frame. If I get the .pageItem collection as an array via .getElements(), just the 2 page item objects—the image rectangle container and the text frame are retur
...Copy link to clipboard
Copied
Switch from "allPageItems" to "pageItems".
pageItems is a collection of "direct" childrens only - allPageItems is a collection of all childrens and their childrens and so on.
If your group in on a page - and is the only object on that page - myPage.pageItems will return ONLY this group - but myPage.allPageItems will return this group PLUS everything in this group.
Copy link to clipboard
Copied
And yes, linked image is a child of the Rectangle.
Copy link to clipboard
Copied
Hello,
Thank you for the advice, this was distroying my soul.
I will give it a shot tonight when I am back home.
I know the script and this function is very daft on appearance but it's a workarround for a content management system running through InDesign.
Ill update later,
Best,
Smyth
Copy link to clipboard
Copied
PageItems:
AllPageItems:
Copy link to clipboard
Copied
Hello,
Nice bit of software to show that - Thats interesting becuase I did also have a script to show me the bounds of all objects which gave me four results which took me back as I had precived image plus item groups as three things - but complete oversight as the group of course has its own bounds... of which your page items demo shows four parts three parent to the group
Aces
Can't wait to update the code later!
Thank you
Smyth
Copy link to clipboard
Copied
Thanks.
Browsing is just a small part - the real power is in Batch Processing of the elements.
Copy link to clipboard
Copied
Hi @SmythWharf , Also, as @Robert at ID-Tasker , suggests .allPageItems returns an array (not a collection) of all objects inside of the group, while .pageItems returns a collection of the top level objects that are page items inside the group.
So here on a selected group, .allPageItems gets the image, its container frame, and the text frame. If I get the .pageItem collection as an array via .getElements(), just the 2 page item objects—the image rectangle container and the text frame are returned:
var g = app.activeDocument.selection[0]
alert("\rAll Page Items: \r" + g.allPageItems +"\r\rPage Items: \r" + g.pageItems.everyItem().getElements())
Copy link to clipboard
Copied
Thank you both for your insight.
@Robert at ID-Tasker Yes I had a quick look at the ID Tasker... curious thing.
@rob day I will look into this
Regarding the above I have adjusted the processItem and the findSmallerGroupItem functions and up pageItems has done it - a good thing to learn!
Thank you very much!
Best,
Smyth
Copy link to clipboard
Copied
and up pageItems has done it
Here’s another example of the diiference between the allPageItems Array and the pageItem Collection, where you might not get the result you expect.
Visually it looks like this group has 6 items, but allPageItems returns 8 objects, and pageItems returns 2 pageItems:
var g = app.activeDocument.selection[0]
alert("\rAll Page Items: (" + g.allPageItems.length + ") \r" + g.allPageItems +"\r\rPage Items: (" + g.pageItems.count() + ") \r" + g.pageItems.everyItem().getElements())
Copy link to clipboard
Copied
Group within group is the "extra" object.