Search code examples
javascriptxmladobe-indesign

InDesign Scripting: Deleting elements from the structure panel


I've imported some XML files inside InDesign (you can see the structure in the picture below) and I've also created a script to get some statistics concerning this hierarchy.

For example, to count the "free" elements:

var items = app.activeDocument.xmlElements.everyItem();
var items1 = items.xmlElements.itemByName("cars");
var cars = items1.xmlElements.everyItem();
var c_free = cars.xmlElements.itemByName("free");
var cars_free = c_free.xmlElements.count().length;
  • I also have apartments in my structure that's why I'm using itemByName.

The code above returns the correct number of free cars in my structure.

What I'm trying to do - without any luck so far - is to target those free items (inside cars) and either delete all of them or a specific number.

My last attempt was using:

var del1 = myInputGroup2.add ("button", undefined, "Delete All");
del1.onClick = function () {
    cars.xmlElements.everyItem().remove();
}

inside a dialog I've created.

Any suggestions will be appreciated cause I'm really stuck here.

Strucure


Solution

  • I would probably use XPath for this. You can use evaluateXPathExpression to create an array of the elements you want to target. Assuming your root element is cars and it contains elements called cars1, and you want to delete all free elements within a cars1 element, you could do something like:

    var myDoc = app.activeDocument;
    //xmlElements[0] is your root element, in this case "cars". The xPath expression is evaluated from cars.
    //evaluateXPathExpression returns an array of all of the free elements that are children of cars. 
    var myFrees = myDoc.xmlElements[0].evaluateXPathExpression("cars1/free");
    for (var i = myFrees.length - 1; i>=0; i--){
        myFrees[i].remove();
    }
    

    Tweaking this would require some knowledge of xPath, but it's not terribly hard to learn the basics and it does seem like the simplest approach.