Showing posts with label Dialog. Show all posts
Showing posts with label Dialog. Show all posts

2009-07-17

Display Dialog with Radio Buttons of Array Elements

The Final Installment in Selecting an Array Element

Radio Buttons are the third user interface option when it comes to selecting items from a list. Like a Drop Down Menu, a user is only permitted to select a single choice. When the number of items to select from is limited, it is easiest to select from a set of radio buttons.

All three versions of Array Element selection presented have some unique feature. The checkbox version had a method of controlling how many items would appear in a column. That could be incorporated here. This function has the ability to display an optional script version and discusses that in the scripts comments. This version, as do all the others, could actually accept an Adobe InDesign or Adobe InCopy collection. A collection is a superset of an Array object and collections have properties other than .length. For example if you wanted to get the name of all the Master Pages in a document...
var mps = app.documents[0].masterSpreads.everyItem().name
You could also just refer to the name of one item in the collection using the code within the function below. Just read the embedded documentation.


//
function chooseFromList( lst , prmt , dflt ) {
//-------------------------------------------------------------------------
//-- C H O O S E F R O M L I S T
//-------------------------------------------------------------------------
//-- Generic: Yes for any version of Adobe InDesign or Adobe InCopy
//-- that can display a custom dialog.
//-------------------------------------------------------------------------
//-- Purpose: Displays a dialog with a series of radio buttons with
//-- choices passed into 'lst'.
//-------------------------------------------------------------------------
//-- Returns: index of chosen item or -1 if they clicked cancel
//-------------------------------------------------------------------------
//-- Parameters: 3
//-- lst: An array of things that can be coorersed into strings
//-- prmt: a string that will be used to instruct the user what they
//-- should select. Something like ; 'Select a Paragraph Style:'
//-- dflt: a
//-------------------------------------------------------------------------
//-- Sample Use:
//~ var a = [2, 4, 6, 8, 'who', 'do', 'we', 'appriciate']
//~ var daChoice = chooseFromList ( a , 'Select Something:' )
//~ if ( daChoice != -1 ) alert ( 'You picked: ' + a[daChoice] )
//-------------------------------------------------------------------------
//-- Written by Jon S. Winters on 2008.12.24
//-- Edited: 2009.07.17 to provide better comments.
//-- eps@electronicpublishingsupport.com
//-------------------------------------------------------------------------
//-- Version 1.1: Force Adobe InDesign to display dialogs. Without the
//-- line below the dialog may not appear on some systems.
app.scriptPreferences.userInteractionLevel = UserInteractionLevels.INTERACT_WITH_ALL ;
//-- Assign a default default choice if one isn't passed;
dflt = dflt || 0 ;
//-- If the default value is less than 0, reset to zero.
//-- This was initially done because this function was created for
//-- a script where the user would get the dialog multiple times
//-- throughout the course of the day and the persistent
//-- target engine would pass as default the last choice
//-- but if a user cancels, then the last choice will be -1.
dflt = (dflt <>
//-- Standard way to make a new dialog with a prompt and a cancel button.
var listDialog = app.dialogs.add({canCancel:true, name:prmt}) ;
//-- Setup the buttons array which will be filled as the dialog is
//-- constructed.
var buttons = new Array () ;
//-- Go through the processes of setting up the areas of the dialog
//-- consult the Adobe Documentaion if you really want to know
//-- what is going on here. Otherwise, just use it.
with (listDialog) {
with (dialogColumns.add()) {
var userChoice = radiobuttonGroups.add()
with ( userChoice ) {
//-- Loop through every item of the list. Note, if the list
//-- is really a collection of Adobe InDesign or Adobe
//-- InCopy objects, they will have .name properties.
//-- Thus, you can add .name in the staticLabel. See
//-- the commented out version.
for ( var loopIndex = 0 ; loopIndex <>
//-- Below for standard Array of Elements that can be
//-- displayed as a string. Note the conversion to
//-- the String object. This will be necessary for
//-- list elements that don't have strings.
buttons[loopIndex] = radiobuttonControls.add( {staticLabel:String(lst[loopIndex]) } );
//-- Below version will allow you to see the name of a item
//-- in a collection.
//~ buttons[loopIndex] = radiobuttonControls.add( {staticLabel:lst[loopIndex].name } );
} //-- end of for loop
//-- Note, the next thing is interesting. We are currently in
//-- a with (radionbuttonGroup) statement. That has a
//-- selectedButton property. And now that all the
//-- buttons have been added, the selected buttton
//-- can be set to the default value.
selectedButton = dflt ;
} ///-- end of with radiobuttonGroups
//
//-- This next thing is also interesting. ExtendScript, like
//-- ECMAScript and Javascript, has a global object. That
//-- object is referenced as
//-- this
//-- some of my scripts set a global 'scriptVersion'
//-- if the scriptVersion exists, then the dialog will get
//-- the text of that scriptVersion
if (this.scriptVersion) {
with (dialogRows.add() ) {
with (dialogRows.add() ) {
staticTexts.add({staticLabel:String(this.scriptVersion)}) ;
}
}
}
//
}
}
//-- Show the dialog, and wait for them to click OK or Cancel.
var listResult = listDialog.show() ;

//-- return the selected list index unless they clicked Cancel.
return ( listResult ? userChoice.selectedButton : -1 ) ;
}
//

2009-07-16

Display Dialog with Dropdown Menu of Array Elements

Another way to display an array
(How's that for alliteration?)
A recent post dealt with displaying a dialog box with a checkbox for every array elements. That works if you want to select more than a single entry in the array. But many times you only need the option to choose a single array element. In that case the GUI should include a dropdown menu or a set of radio buttons. This generic ExtendScript function takes an array of elements and a prompt string and constructs and displays a dialog box allowing the user to select an element of the array.
The function returns not the array element but the index in the array of that element.
Note, if you want the items sorted then use the .sort() method on the array prior to passing it to the function.
If the user doesn't select an array element or clicks cancel the function returns a -1 value. Note, in JavaScript an array can't be referenced with a negative index. But in ExtendScript, if you have a collection, instead of a true array, then -1 is the last item in the ExtendScript collection.
This function was written for a script that allows the user to select text in Adobe InDesign or Adobe InCopy and toggle the Bold or Italic font styles with a keyboard shortcut. The script is quite nice because nothing is hard coded. Instead a site installs the pieces, assigns the keyboard shortcuts, and then uses it. The first time they use it, it displays a dialog asking what Character Style to apply to the selected text. Any future time the same type of text is selected, the script will know what Character Style to apply. It works great. That script requires Character Styles when a normal Bold or Italic font style won't suffice such as when you not only apply a bold, but you actually switch fonts. This script is for sale to any site that needs it, just send a e-mail to eps@electronicpublishingsupport.com
A separate link to toggleStyle() will be setup eventually.

//
function selectArrayElementViaDropdown(lst,prmt) {
//-----------------------------------------------------------
//-- S E L E C T A R R A Y E L E M E N T F R O M D R O P D O W N
//-----------------------------------------------------------
//-- Generic: Yes for current versions of Adobe Products
//-- that support custom dialog boxes
//-----------------------------------------------------------
//-- Purpose: Displays a dialog a single dropdown menu of
//-- choices passed into 'lst'.
//-----------------------------------------------------------
//-- Parameters: 2
//-- lst: An Array of items to display to the user
//-- prmt: A string prompt to ask the users what to do.
//-----------------------------------------------------------
//-- Returns: index of chosen item or -1 if they clicked cancel
//-----------------------------------------------------------
//-- Calls: Nothing.
//-----------------------------------------------------------
//-- Sample Use:
//~ var pStyleNames = ['Body bj', 'Body Ragged brr', 'Body Wire bw']
//~ var selectedStyle = selectArrayElementViaDropdown ( pStyleNames , 'Choose the Paragraph Style to apply to the body of this story' ) ;
//~ if ( selectedStyle >= 0 ) {
//~ var theStyleNameToUse = pStyleNames[selectedStyle]
//~ // Do something with the style name here
//~
//~
//~ }// End of the if block
//-----------------------------------------------------------
//-- Written sometime in 2009 by Jon S. Winters
//-- eps@electronicpublishingsupport.com
//-----------------------------------------------------------
//
var listDialog = app.dialogs.add({canCancel:true});
with (listDialog) {
with (dialogColumns.add()) {
with (dialogRows.add() ) {
// show prompt
staticTexts.add({staticLabel:prmt});
}
with (dialogRows.add() ) {
//show the list
var userChoice = dropdowns.add({stringList:lst})
}
}
}
//-- Show the dialog
var listResult = listDialog.show() ;
//
if (listResult) {
return userChoice.selectedIndex ;
}
else {
return -1 ;
}
}
//

2009-07-13

Display Dialog of Checkboxes of Array Elements

For a project to print or export Adobe InDesign pages to PostScript Files, PDFs, or EPS files to fixed folder locations with fixed output settings (EPS settings, Print Styles, PDF Export Styles), I needed a dialog to display the pages in active document so the user could choose to exclude certain pages from the output. The reason being if you are working with a multi-page Adobe InDesign document, you might need to output some pages before the rest are 'finished'.
So my script to output these pages to a pre-specified folder on a file server (controlled by a site specific XML file), needed a way to control which pages were going to print.
The code snippet looks like this...

//-- Limit which pages to print if the method details indicates to
if ( limitOutputToSpecificPages ) {
var arrayToCheck = app.documents[0].pages.everyItem().name ;
var prmt = 'Pages:' ;
var pagesToOutput = selectListOptions( arrayToCheck , prmt , true )
}
//
//-- Determine how to handle the naming of the extra pages
//-- Loop through the pages
for (var pgIndex = numPages - 1 ; pgIndex >= 0 ; pgIndex-- ) {

//-- Deny output of pages if the user didn't check to output them
if ( limitOutputToSpecificPages && ( ! pagesToOutput[pgIndex] ) ) {
continue ;
}
//
//-- HANDLE THE OUTPUT HERE


}// end of for loop

Of course that snippet leaves out a lot of details, but basically if a value (limitOutputToSpecificPages) says to limit to specific pages, use a function (below) to display a dialog of page numbers with check boxes. The function (below) returns an array of true or false values.
And if the value is false, then skip the rest of the inner part of the for loop (the continue causes teh for loop to not finish, but to go back and check for the end point and increment the loop index)


//
function selectArrayElementsViaCheckboxes(lst,prmt,dflt,colLimit) {
//-------------------------------------------------------------------------
//-- S E L E C T A R R A Y E L E M E N T S V I A C H E C L B
O X E S
//-------------------------------------------------------------------------
//-- Generic: Yes! Should work with all current versions of Adobe
Products
//-- that support custom dialog boxes.
//-------------------------------------------------------------------------
//-- Purpose: Displays a dialog with a series of checkboxes with
//-- choices passed into 'lst'.
//-------------------------------------------------------------------------
//-- Parameters: 4
//-- lst: The array whose contents will be displayed to the user
//-- prmt: A string to be used as a prompt
//-- dflt: (optional) A boolean indicating if ALL the checkboxes
//-- should initially be selected (checked) or deselected
//-- (unchecked). _ALL_!
//-- colLimit: (optional) The maximum number of entries to place
//-- in any one column.
//-------------------------------------------------------------------------
//-- Returns: an array the the same length of the of chosen items. If
the
//-- items are selected as a result of the checkbox items being
//-- checked, the array will be set to true, else false.
//-- If the user cancels the dialog, then the returned array is []
//-------------------------------------------------------------------------
//-- Calls: Nothing.
//-------------------------------------------------------------------------
//-- Sample Use:
//-- var sampleArray = ['extreme', 'fantastic', 'great',
'monstrous', 'monumental', 'prodigious', 'stupendous', 'tremendous']
//-- var chosenItems = selectArrayElementsViaCheckboxes
( sampleArray , 'Select the desired words:' , true , 4 )
//-- for ( i = 0 ; i < chosenItems.length ; i++ ) {
//-- if ( chosenItems[i] ) {
//-- $.writeln('User selected: ' + sampleArray[i] ) ;
//-- }
//-- }
//-------------------------------------------------------------------------
//-- Written by Jon S. Winters on 2008.12.24
//-- Edited: 2009.07.13 onboard flight to Charlotee, NC
//-- eps@electronicpublishingsupport.com
//-------------------------------------------------------------------------

//-- Force Adobe InDesign to display dialogs. Without the
//-- line below the dilaog may not appear on some systems.
app.scriptPreferences.userInteractionLevel =
UserInteractionLevels.INTERACT_WITH_ALL ;

//-- Assign a default default choice if one isn't passed;
//-- This should either be true or false
dflt = ( dflt == undefined ) ? true : Boolean ( dflt ) ;
//
//-- Verify that there is a limit to the number of items in a column.
if ( ! colLimit ) { colLimit = 10 ; }

//-- create a new array of user responses to return
var userChoices = new Array () ;

var listDialog = app.dialogs.add({canCancel:true}) ;
var buttons = new Array () ;

with (listDialog) {
with (dialogColumns.add()) {
with ( borderPanels.add() ) {
with ( dialogColumns.add() ) {
staticTexts.add({staticLabel:prmt});
with (dialogRows.add()) {
//-- loop thorugh the passed list and create the checkbox as
well as the array to return
for ( var listIndex = 0 ; listIndex < lst.length ; listIndex++ ) {

if ( listIndex % colLimit == 0 ) {
var Col = dialogColumns.add();
}
with ( Col ) {
userChoices[listIndex] =
( checkboxControls
.add({staticLabel:String(lst[listIndex]),checkedState:dflt})) ;
}
}
}
}
}
}
}
//-- Show the dialog
var listResult = listDialog.show() ;

if ( listResult ) {
var returnArray = new Array () ;
//-- loop the result and rebuild the results

for ( var listIndex = 0 ; listIndex < lst.length ; listIndex++ ) {
returnArray.push ( userChoices[listIndex].checkedState ) ;
}
//-- return the selected list index unless they
return returnArray ;
}
else {
//-- User clicked Cancel -- return an empty array
return [] ;
}
}
//