You are not logged in.
By Ben Waldie
In this month's column, we're going to discuss a specific type of interface element that is often incorporated into AppleScript Studio projects' a table view. Table views consist of one or more cells (displayed using columns and rows), which may be used to display data. Think of a table view as being similar in layout to a worksheet in Excel. See figure 1 for an example of a 2-column table view in an AppleScript Studio project's interface.
Applescript:
set content of table view 1 of scroll view 1 of window 1 to {"Macintosh HD", "Users", "bwaldie"}
See figure 7 for an example of how a table view would appear, after executing the code above.
Applescript:
set content of table view 1 of scroll view 1 of window 1 to {{"Macintosh HD", "Macintosh HD:"}, {"Users", "Macintosh HD:Users:"}, {"bwaldie", "Macintosh HD:Users:bwaldie:"}}
Figure 8 shows an example of how a table view would appear, after executing the code above.
Applescript:
set content of table view 1 of scroll view 1 of window 1 to {{|name|:"Macintosh HD", |path|:"Macintosh HD:"}, {|name|:"Users", |path|:"Macintosh HD:Users:"}, {|name|:"bwaldie", |path|:"Macintosh HD:Users:bwaldie:"}}
Creating a Data Source
It is possible to write code to create a data source and link it to a table view manually, rather than allowing this to be done dynamically. To do this, first use the make command to create the data source. Then, set the data source of the table view to reference the newly created data source. For example:
Applescript:
set theDataSource to make new data source at end
set data source of table view 1 of scroll view 1 of window 1 to theDataSource
Adding Columns and Rows
Prior to AppleScript Studio 1.4, it was necessary to write code to build data columns and data rows within a table view's data source. In fact, you may still find situations where you will want to do this. To create a data column or a data row within a data source, use the make command, as demonstrated here.
Applescript:
make new data column at end of data columns of theDataSource
Or
Applescript:
make new data row at end of data rows of theDataSource
Deleting Columns and Rows
Deleting data columns and data rows from a table view's data source is done using the delete command. For example:
Applescript:
delete data row 1 of theDataSource
Or
Applescript:
delete data column 1 of theDataSource
Getting the Selection of a Table View
To access the selection of a table view, reference the selected data row or selected data rows properties of the table view. For example:
Applescript:
selected data row of table view 1 of scroll view 1 of window 1
--> data row id 4 of data source id 2
Pulling Things Together
Now, let's pull together several of the techniques that we have discussed throughout this column. Enter the following example code into the main script of your AppleScript Studio project.
Applescript:
on clicked theObject
if name of theObject = "add" then
set theNewFile to choose file without invisibles
tell data source of table view 1 of scroll view 1 of window 1
if (count data columns) = 0 then
repeat 2 times
make new data column at end of data columns
end repeat
end if
set theNewRow to make new data row at end of data rows
set contents of data cell 1 of theNewRow to name of (info for theNewFile)
set contents of data cell 2 of theNewRow to theNewFile as string
end tell
else if name of theObject = "delete" then
if (count data rows of data source of table view 1 of scroll view 1 of window 1) is greater than 0 then
set theSelectedRow to selected data row of table view 1 of scroll view 1 of window 1
delete theSelectedRow
end if
else if name of theObject = "reveal" then
if (count data rows of data source of table view 1 of scroll view 1 of window 1) is greater than 0 then
set theSelectedRow to selected data row of table view 1 of scroll view 1 of window 1
set thePath to contents of data cell 2 of theSelectedRow
tell application "Finder" to reveal alias thePath
end if
end if
end clicked
on will open theObject
set theFolder to choose folder without invisibles
tell application "Finder"
set theFiles to every file of theFolder
set theTableViewContents to {}
repeat with a from 1 to length of theFiles
set theCurrentFile to item a of theFiles
set theCurrentFileName to name of theCurrentFile
set end of theTableViewContents to {theCurrentFileName, theCurrentFile as string}
end repeat
end tell
set content of table view 1 of scroll view 1 of window 1 to theTableViewContents
end will open
Next, build and run the project. If all goes well, you should be prompted to choose a folder. Next, the project's interface should be displayed, and the table view should be populated with the names and paths of any files that were found within the specified folder. Clicking the + button should prompt you to select a new file to add to the end of the table view. Clicking the button should remove the selected row from the table view. Clicking the Reveal button should display the file that is currently selected in the table view, in the Finder.
If you have any trouble following along, feel free to download a copy of the completed project here.
In Conclusion
You should now have a basic understanding of how to utilize table views in AppleScript Studio projects. For more guidance as you put the practices we have discussed to use, be sure to browse the AppleScript Studio Terminology Reference guide, included in Xcode's documentation and on the Apple Developer Connection website. And, take some time to explore the example projects in the Developer/Examples/AppleScript Studio/ folder, installed with Xcode. Here, you will find numerous fully editable example projects that incorporate table views. Also, feel free to post your AppleScript Studio questions the AppleScript Studio forum on MacScripter's online BBS.
Until next time just script it!
-Ben Waldie
Ben Waldie, Automated Workflows, LLC
AppleScript & Automator Tips & Articles - http://www.automatedworkflows.com/tips/tips.html
Mac Automation Made Simple Video Podcast Series - http://www.automatedworkflows.com/tips/podcast.html
Automator for Mac OS X Visual QuickStart Guide - http://www.automatedworkflows.com/books/books.html
Offline
Ben,
Thanks for the great tutorial...
After looking at the example (2 column) tables, I created 4 columns on the table in the scroll view, but I would like to be able add the columns to the NIB window dynamically.
I tried this below :
Added a fifth column "Flag" to the headers list, and a dummy value of "yes" to the corresponding data value for each row in the loop, but when I built and ran it only the first four data columns displayed.
Applescript:
-- This does not contain all the code, SEE the next script for the complete code I have so far
-- This did not work with the 4 column table while using the "repeat no_of_columns times"
on will open theObject
set aColumnHeaders to {"SeqNo", "Flag", "Item Name", "Item Class", "Item Path"}
set aColumnWidths to {60, 80, 180, 120,400}
set no_of_columns to count aColumnHeaders
set theDataSource to make new data source at end
set data source of table view 1 of scroll view 1 of window 1 to theDataSource
repeat no_of_columns times
make new data column at end of data columns of theDataSource
end repeat
repeat loop...
[...]
set end of theTableViewContents to {counter, "yes", this_name, this_class, this_path}
end repeat
end will open
The nice thing would be to have a NIB window ->Scroll View -> Table with a couple of hardcoded columns, and build the remaining columns dynamically as the need arose. I dont want to build a Table with something like 10 fields, in order to use the table to display from 1 to 10 fields.
I am trying to build a dynamic table that I can call from applescript when "choose from list" is not enough. I noticed how you deleted columns dynamically, but did not find how they could be added on the fly.
I was able to :
( 1 ) assign the column headers, and column widths dynamically, but not add extra columns.
( 2 ) Double click on a row, and {open, reveal} the corresponding file/folder/symlink, etc, or take some other action.
As soon as I can figure it out, I would like to do the following :
( 1 ) Setup to allow sorting via the column headers.
( 2 ) Select a row and click a button to trigger an action (this should be fairly simple).
( 3 ) Call this app from a separate applescript, and pass it the 2-dimensional arrays to display in the table. (this might be harder) If I have no other choice I can write the data to a file, that this app looks for when it launches, and it can load the data there. There might be an easier way ?
Any ideas ?
Bill Hernandez
Plano, Texas
Applescript:
-- This contains what I have so far, and is working very well...
on will open theObject
set aColumnHeaders to {"SeqNo", "Item Name", "Item Class", "Item Path"}
set aColumnWidths to {60, 180, 120,400}
set no_of_columns to count aColumnHeaders
set theDataSource to make new data source at end
set data source of table view 1 of scroll view 1 of window 1 to theDataSource
repeat no_of_columns times
make new data column at end of data columns of theDataSource
end repeat
set theFolder to choose folder without invisibles
tell application "Finder"
-- set theFiles to every file of theFolder as alias list
-- set theFiles to every file of the entire contents of theFolder as alias list
set theFiles to every item of the entire contents of theFolder as alias list
end tell
set theTableViewContents to {}
tell table view 1 of scroll view 1 of window 1
repeat with counter from 1 to length of aColumnHeaders
set the content of header cell of table column counter to (item counter of aColumnHeaders) as string
set the width of table column counter to (item counter of aColumnWidths) as integer
end repeat
end tell
set home_posix_path to POSIX path of (path to home folder from user domain as text)
set len to count characters of home_posix_path
if (last character of home_posix_path is equal to "/") then
-- set len to len - 1
end if
set str2match to (characters 1 through len of home_posix_path) as string
repeat with counter from 1 to length of theFiles
set this_file to item counter of theFiles
tell application "Finder" to set w_props to get properties of this_file
set this_name to displayed name of w_props
set this_class to (class of w_props) as string
if (this_class is equal to "«class alia»") then
set this_class to "alias"
else if (this_class is equal to "«class cfol»") then
set this_class to "folder"
else if (this_class is equal to "«class docf»") then
set this_class to "document"
end if
set this_path to POSIX path of (this_file as string)
if (str2match is equal to ((characters 1 through len of this_path) as string)) then
set this_path to "~" & (characters len through -1 of this_path) as string
end if
set end of theTableViewContents to {counter, this_name, this_class, this_path} -- this_file as string}
end repeat
set content of table view 1 of scroll view 1 of window 1 to theTableViewContents
end will open
on clicked theObject
(*Add your script here.*)
tell window of theObject
close
end tell
tell application of theObject
quit
end tell
end clicked
on double clicked theObject
(*Add your script here.*)
if name of theObject = "table_view" then
if ((count data rows of data source of table view 1 of scroll view 1 of window 1) is greater than 0) then
set theSelectedRow to selected data row of table view 1 of scroll view 1 of window 1
set thePath to contents of data cell 4 of theSelectedRow
set thePath to do shell script "echo " & thePath
-- THESE should be globals so they are only initialized once
set b1 to "Reveal"
set b2 to "Open"
set s to "Which would you prefer ?" & return
set s to s & "( 1 ) Reveal the item within its parent container." & return
set s to s & "( 2 ) Open the item (file, or folder, etc)." & return & return
set which_choice to button returned of (display dialog s buttons {b1, b2} default button {b2})
tell application "Finder"
activate
if (which_choice is equal to b1) then
reveal POSIX file thePath as alias
set w_ref to Finder window 1
select w_ref
set toolbar visible of w_ref to false
set w_props to {bounds:{10, 46, 300, 500}, current view:list view, sidebar width:0, toolbar visible:false, statusbar visible:true}
set properties of w_ref to w_props
else
open POSIX file thePath as alias
end if
end tell
end if
end if
end double clicked
Last edited by mbs402 (2009-04-30 12:50:15 am)
Offline