23 Replies Latest reply on Dec 23, 2011 2:15 PM by Gordon The Scripter

    Text Variables and Scripts

    Level 1
      I have a number of standard documents that a setup script uses. In each document there are text variables called Author and Job Number.

      I'm working in VB and these commands can display the name and index of the variable but can't seem to find the way to actually change the value of the variable.

      Set IDoc = InD.ActiveDocument
      MsgBox IDoc.TextVariables("Author").Name
      MsgBox IDoc.TextVariables("Author").Index

      Any help would be much appreciated.
        • 1. Re: Text Variables and Scripts
          Level 1
          TextVariable is "ReadOnly" - or "InsertOnly" ;)

          Property ResultText As String
          read-only
          Member of InDesign.TextVariableInstance
          The text that replaces the variable marker. Note: This property cannot be set; it can be used only to update variables. .

          robin

          --
          www.adobescripts.com
          • 2. Re: Text Variables and Scripts
            Peter Kahrel Adobe Community Professional & MVP
            You set the contents of a variable ucing variableOptions.contents. Example:

            app.activeDocument.textVariables.item ('Author').variableOptions.contents = "Krugh"

            For VB you need to change capitalisation here and there.

            Peter
            • 3. Re: Text Variables and Scripts
              Level 1
              sorry :(

              Peter is right

              robin

              --
              www.adobescripts.com
              • 4. Re: Text Variables and Scripts
                Level 1
                He is indeed! Thanks Peter!! I've been writing code for 25 or so years, every from WordPerfect 5.0 (DOS) macros to WordBasic to CorelScript and gobs of VB and I've never struggled as much to find commands as I have with this InDesign stuff.

                I found the VariableOptions and tried .Text, .Value everything I could think of but found no reference to .Contents.

                I have the CS3 scripting guide and tutorial PDFs but neither of those even mentions the TextVariable. Where does one get such info?!?!?

                Again, thanks a bunch,
                Ken
                • 5. Re: Text Variables and Scripts
                  Peter Kahrel Adobe Community Professional & MVP
                  >Where does one get such info?

                  It should be in the guides, and I guess you should be able to find it in the object browser. InDesign's object model is indeed complex. To find which methods and properties exist, you have to go through the lists (guides, obj viewer) and see what's there. It's like reading a dictionary.

                  Peter
                  • 6. Re: Text Variables and Scripts
                    Level 1
                    Peter, I found the VariableOptions in the object browser but, again, didn't see a reference to .Contents.

                    Can I get personal and ask how you knew about the .Contents?

                    Ken
                    • 7. Re: Text Variables and Scripts
                      Kasyan Servetsky Level 5
                      Hi,

                      I checked OMV, SciptDebugger's dictionary and VB6's object browser but didn't find "contents" property of "variableOptions" in any of them. Peter, how did you find it?

                      Kasyan
                      • 8. Re: Text Variables and Scripts
                        Kasyan Servetsky Level 5
                        Aha! Although it hasn't been documented,it can be seen in Data Browser.
                        • 9. Re: Text Variables and Scripts
                          Peter Kahrel Adobe Community Professional & MVP
                          It isn't particularly clear indeed. VariableOptions has any of these properties (as an object)

                          PageNumberVariablePreference
                          ChapterNumberVariablePreference
                          DateVariablePreference
                          FileNameVariablePreference
                          MatchCharacterStylePreference
                          MatchParagraphStylePreference
                          CustomTextVariablePreference

                          As Ken wanted to set a text variable, I then looked under customTextVariablePreference, where I found contents.

                          Actually, it so happened that I figured this out last week for a script, and it took me a good deal longer than the above description may have suggested!

                          Peter
                          • 10. Re: Text Variables and Scripts
                            [Jongware] Most Valuable Participant
                            It seems to defy logic.

                            <pre>
                            TextVariable.variableOptions
                            |
                            (TextVariable.variableType)
                            |
                            +-PageNumberVariablePreference
                            +-ChapterNumberVariablePreference
                            +-DateVariablePreference
                            +-FileNameVariablePreference
                            +-MatchCharacterStylePreference
                            +-MatchParagraphStylePreference
                            +-CustomTextVariablePreference -> contents
                            </pre>

                            I had to scan the entire contents of the Object Help before finding these in the "Preferences Suite".

                            A likely reason is that each of these 'preferences' (a confusing choice of name) have wildly different properties, so they had to be captured in a single object (the variableOptions). For example, the DateVariablePreference has no contents but a format instead.

                            Perhaps Ole should finish his object tree idea.
                            • 11. Re: Text Variables and Scripts
                              Level 1
                              Well, this has all been VERY helpful, at least I'm somewhat on my way.

                              The Data Browser (Windows / VB 6) has a loooong list of Classes. By selecting TextVariable in the Classes list I get the Members in the right side, one of which is VariableOptions. At the bottom of the Object Browser there is a description with a list of preferences, one of which is CustomTextVariablePreference. CustomTextVariablePreference is listed in the Classes list, members of which are "Contents" and "Parent." Not sue I would have gotten to the line of code that actually works from all of this (IDoc.TextVariables("Author").VariableOptions.Contents = "Oy-vey!") but maybe It'll just take some getting used to.

                              Peter, Mind if I ask in what exactally you're looking all this up?

                              Thanks again everyone.

                              Ken
                              • 12. Re: Text Variables and Scripts
                                Peter Kahrel Adobe Community Professional & MVP
                                Most of the time I use Teus de Jong's object browser (http://www.teusdejong.nl/), which is a good way to look things up. You can set it to display things in VB style. If I can't find things in a browser, I search a list of all properties and methods, here: http://www.kahrel.plus.com/indesignscripts.html (look for Script dictionary). This is a dumb list, but it has been useful for me.

                                InDesign scripting does take some getting used to, but it's worth the effort. Like you, I used to do WordPerfect scripts, and that's a different universe altogether.

                                Peter
                                • 13. Re: Text Variables and Scripts
                                  Level 1
                                  Fellow Scripters,

                                  I agree that the documentation should cover text variables better--and I created it. There just wasn't time to get them in, and it's high on my list of things to fix for CS4.

                                  Ken, I don't think you need another browser--the VB6 version is at least as good as the JavaScript versions mentioned above. The only trick is to understand that TextVariable.VariableType tells you which "preferences" object to look at for the settings for the variable.

                                  For a simple text (custom) variable, you'd see that the VariableType is idVariableType.idCustomTextType. That tells you that the object you want to look at is the CustomTextVariablePreference object. Looking at that object, you can see that it has only a Content and a Parent property.

                                  This, by the way, is why the type of the TextVariable.VariableOptions property is a Variant--it can be any of the text variable preferences objects. When you think of the question in terms of the user interface, this seems reasonable--the different preferences objects correspond to the menu choices in the Text Variables dialog box. The menu choice you make changes the controls that appear in the dialog box. The controls correspond to the options in the preferences object.

                                  Which brings me to a point: the more you know about the way that InDesign works, the easier it is to understand the object model. That said, InDesign is a big program, with a very large object model!

                                  Sorry I didn't get to text variables in the documentation, and I'll do better next time. Until then, ask questions here! It's an incredible resource.

                                  Thanks,

                                  Ole
                                  • 14. Re: Text Variables and Scripts
                                    [Jongware] Most Valuable Participant
                                    Adding to Peter's wealth of data: as I found the Help browser infuriatingly slow and cumbersome, I extracted all Help data into a handy set of hyperlinked-to-the-gills html pages. D/L from my site at http://www.jongware.com/binaries/indesigncs3jshelp.zip if you like to see it.

                                    The only thing that I really miss is caused by an artefact of the source XML data: if a reference can return multiple objects, that list of objects is written down in plain ASCII, and I'm unable to harvest links from these. So the references to the different variableTypes showed up as plain text -- if they had been hyperlinks too, I might've spotted'em sooner.

                                    [Edit: Ole, nothing to apologize for! As an old WP macro programmer -- I see there are more than a few here -- and an unwilling VBA user, I was able to create and maintain an entire workflow based on just a few scripts, which amazingly kept on working by and large through 3 major versions of ID.]
                                    • 15. Re: Text Variables and Scripts
                                      Peter Kahrel Adobe Community Professional & MVP
                                      Coming back to scripted text variables, here's a script that illustrates a couple of things that were raised in this thread. I use it to display and set all text variables in a document. I use it to set variables in documents I use as masters for journals, to set things like volume, issue, year, date, and whatever else.

                                      When first run, the script creates a two-column table on the first page of the document. It places variable names in the first column, their values in the second column. To set different values for any variable, replace the value in the second column with the new value. Then run the script again.

                                      Peter

                                      (PS: jongware's list is a great tool indeed, should have mentioned that)

                                      doc = app.activeDocument;
                                      if ( doc.textFrames.item ('vars___') == null)
                                      show_variables (doc);
                                      else
                                      set_variables (doc);

                                      function show_variables (doc)
                                      {
                                      var v = doc.textVariables;
                                      var table_contents = [];
                                      var n = 0;
                                      for (var i = 0; i < v.length; i++)
                                      {
                                      if (v[i].variableType == VariableTypes.customTextType)
                                      {
                                      table_contents.push (v[i].name);
                                      table_contents.push (v[i].variableOptions.contents);
                                      n++;
                                      }
                                      }
                                      var tf = doc.pages[0].textFrames.add ({label: 'vars___'});
                                      tf.geometricBounds = [20,20,500,500];
                                      var table = tf.insertionPoints[0].tables.add();
                                      table.columnCount = 2;
                                      table.bodyRowCount = n;
                                      table.contents = table_contents;
                                      }

                                      function set_variables (doc)
                                      {
                                      var t = doc.textFrames.item ('vars___').parentStory.tables[0];
                                      var var_names = t.columns[0].contents;
                                      var new_contents = t.columns[1].contents;
                                      var vars = doc.textVariables;
                                      for( var i = 0; i < var_names.length; i++)
                                      vars.item (var_names[i]).variableOptions.contents = new_contents[i];
                                      // doc.textFrames.item ('vars___').remove()
                                      }
                                      • 16. Re: Text Variables and Scripts
                                        Level 1
                                        Peter,
                                        Many thanks for sharing this code.

                                        Initial observation using InDesign CS3 5.0.2 on OS X 10.5.3:
                                        Most of us use picas and points in InDesign and your code calls
                                        tf.geometricBounds = [20,20,500,500]; which creates a multi-spread text frame. I changed the values to fall within a common 8x10" page.

                                        var tf = doc.pages[0].textFrames.add ({label: 'vars___'});
                                        tf.geometricBounds = [1,1,47,47];
                                        var table = tf.tables.add ({columnCount: 2, bodyRowCount: 1});
                                        table.columns[0].width = "12p";
                                        table.columns[1].width = "34p";

                                        One of the things that immediately occurred to me using this script was the opportunity to mimic variable properties in the document as a means of coding the script to include header or footer "Use:" cases for variable definition and adjustment.

                                        Is there a simple way to call existing variables of all types into a table where the table cells reflect each of the ExtendScript values for ease of use in coding?
                                        • 17. Re: Text Variables and Scripts
                                          Peter Kahrel Adobe Community Professional & MVP
                                          McClure,

                                          >... the opportunity to mimic variable properties in the document as a means of coding the script to include header or footer "Use:" cases for variable definition and adjustment.

                                          >Is there a simple way to call existing variables of all types into a table where the table cells reflect each of the ExtendScript values for ease of use in coding?

                                          I'm afraid I don't understand what you mean. Could you elaborate?

                                          Thanks,

                                          Peter
                                          • 18. Re: Text Variables and Scripts
                                            Level 1
                                            Thanks for Responding Peter,
                                            Example: Recording a macro in a program yields code that mimics activity. The code can then be used in a variety of ways in other scripts and it also simplifies an understanding of program functionality.

                                            Ole pointed out, Extend Scripting needs to reflect the way InDesign works and the Object Model is very complex. An approach that first mimics or reflects the defaults in the program could help to simplify change and could act as a form of documentation.

                                            If we could first build a table of all text variables in the document in a way that defines the variable type and property, then alterations become easier and more robust.

                                            One of the amazing aspects to InDesign is the idea of unlimited text variables that can be passed automatically to populate other text frames in a file or book of documents. However, there are a number of rules related to how the variables behave that become limitations within a book file. For instance, the Running Header variable is the only one that allows 1st or Last instance of "Use:" but logically is applied in a linear fashion - always applies the content of the instance to style instance page and subsequent pages until the value is changed.

                                            Assuming the program allows it, it would be amazing to build on the instance of "Use:" in different ways using the Table or a hidden frame label.

                                            Regards,
                                            John
                                            • 19. Re: Text Variables and Scripts
                                              Peter Kahrel Adobe Community Professional & MVP
                                              Sorry, I still don't get it. Are we talking about the same type of variable?

                                              Peter
                                              • 20. Re: Text Variables and Scripts
                                                Level 1
                                                Sorry I guess I not explained this well.

                                                No, I'm referring to all the other variable types - specifically the Running Header variable that allows for First and Last instance of "Use:".

                                                John
                                                • 21. Re: Text Variables and Scripts
                                                  Peter Kahrel Adobe Community Professional & MVP
                                                  John,

                                                  The other variable types are a bit harder to handle than text variables (in a script). As text variables are the only ones that are changed regularly, they're the only ones for which I think quick access is sensible to script. Other variable types are set once (in my experience anyway).

                                                  Peter
                                                  • 22. Re: Text Variables and Scripts
                                                    Level 1
                                                    Thanks Peter,
                                                    There's no question that the VariableTypes.MATCH_PARAGRAPH_STYLE_TYPE is much harder to work with but I discovered that it can be used as a conditional. The variable is only active when the layer it resides on is active. So a multi-layered document can conditionally apply the same Running Header variable with different content as long as only one of the layers the variable resides on is active.

                                                    This has a lot of potential for complex projects and allows different content to be used to define the contents of the same variable on different layers.

                                                    The problem I'm running into is that it only applies to the page it's defined on and all subsequent pages until changed. I need to find a way to take the contents of the Running Header variable on one page and apply it to several text frames that precede the first instance page.

                                                    Maybe there's a way to pass the contents of the variable using a frame label ID scheme.

                                                    Thanks again for the VariableTypes.CUSTOM_TEXT_TYPE example. It's great and applies variables to all layers from a hidden and or non-printing layer.

                                                    Regards,
                                                    John
                                                    • 23. Re: Text Variables and Scripts
                                                      Gordon The Scripter

                                                      Peter,

                                                       

                                                      Thank you! Thank you! Thank you! for this code example. I have been looking all over for a working code example to do just this.

                                                       

                                                      I tried your code snippet and it worked for me.

                                                       

                                                      Can you tell me what I am doing wrong in the following thread?

                                                       

                                                      http://forums.adobe.com/thread/940934

                                                       

                                                      Thanks,

                                                      Gordon