AppleScript指令碼入門

nealyang231發表於2017-09-20

作為入門文章,這裡儘量寫的簡單明瞭一點。況且,AppleScript本身也是一個非常容易的指令碼語言。

介紹

作為指令碼語言,其實就是一些指令的集合。這種語言和英語類似,因此也易讀、易寫、易於理解。
他的作用也就是讓計算機程式之間的溝通成為可能。

初試AppleScript

指令碼就是一系列的指令。
工具:
clipboard.png

基本操作:

command+k ---> 編譯

command+r ---> 執行

control+點選編輯區上半部分 ---> 提示

認識指令碼的編寫

直接上程式碼:

say "Let's study applescript" using "Fred"
beep 2

上面的程式碼就是讓計算機發聲。最後發兩次“咚”的聲音。
省略using關鍵字,就是用預設的朗讀語音。

tell application "Finder"
    empty the trash
end tell

上面的程式碼是呼叫Finder程式,去清空回收站裡面的垃圾。

tell關鍵字呼叫程式。end tell 結束呼叫。

### 結束語
是不是感覺這個指令碼非常簡單且好玩?OK,下面接著一點點來捋一捋他的基本操作吧。

## 處理數字

### 變數
AppleScript也是用變數

 set x to 25

這裡,就設定了一個x變數,儲存著25這個值。
注意,變數名是一個片語成,中間不能有空格。當然,我們不能夠使用AppleScript中的保留字來作為變數名。當然,不能以數字開頭,但是數字可以出現在變數名中間,下劃線也是可以的。

### 計算

set width to 8
set height to 9
set area to width * height

上面的指令碼大家應該看一下就懂。

屬於叫做運算子,常用的運算子有:+、-、*、/、^、 對的,加減乘除乘方

處理文字

文字也就是我們常說的字串

彈窗

clipboard.png

由於結果區只能顯示最後一行語句的執行結果。所以這裡我們使用對話方塊(display dialog)的形式來演示。

注意:AppleScript是一個由有限詞彙構成的一個指令碼語言,閱讀你寫的指令碼的時候,
判別哪些是指令,哪些不是。對於Mac微機來說是一件非常複雜的一件事。
所以AppleScript需要依賴一些線索幫助其 讀懂指令碼中語句行的各個元素的含義。這就是為什麼要把字串放到雙引號裡面。

對於上述,測試如下指令碼 :

set stringToBeDispalyed to "hi there"
display dialog "stringToBeDisplayed"
display dialog stringToBeDispalyed

字串操作

拼接

set nameOfActress to "Neal is "
set actressRating to " very pretty"
set resultingString to nameOfActress & actressRating
display dialog resultingString

& 是用來拼接字串。

檢視字串長度

set theLength to the length of "Neal"

the length of 用來獲取字串的長度。這裡順便說一句,字串中特殊字元是需要轉義的。

型別轉換

通過上面的學習,你應該知道數字和字串不是一個資料型別,所以將一種資料型別轉換到另一種資料型別,叫做資料型別轉換。AppleScript資料型別轉換如下:


set strToNumber to "16" as number
set numToStr to 12 as string

list

弱型別語言中的陣列

set exampleList to {1,2,3,"hahah",9}

上面的exampleList即是一個列表。

操作

向列表的開頭和結尾處新增

程式碼如下:


set addToBegin to {"winter"}
set addToEnd to {"summer", "autumn"}
set currentList to {"spring"}
set modifiedList to addToBegin & currentList & addToEnd

對的,這裡我們依舊使用 & 來做拼接。

取值

你可以使用元素的序號來取代元素,最左邊的index是1,其實是2,以此類推。可以使用這種方式來從列表中取值,也可以修改類表中值。

set testList to {"Neal", "haha"}
set item 2 of testList to "yang"
get testList

對於第二句,同樣的效果還有:

set the second item of testList to "yang"
set the 2nd item of testList to "yang"

簡直和英語一毛一樣有麼有。但是注意上面這種一字母拼寫的序 數詞最多隻能使用到“tenth”,
之後,就要使用“item 11”的形式。或者寫成 “11th item”的形式。
除了使用序數詞,還可以使用“last item”指代列表中最後專案。

所以,當你只操作列表中最後一個值的時候,你不必知道列表具體有多少專案。
AppleScript允許你以相反的方向來指代元素,也就是可以從右向左數。這需要你使用負數,-1 指代最後一個元素,
-2指代倒數第2個元素。例[11]可以獲得和例[10]一樣的結果

set myList to {"neal", "haha"}
set valueOfLastItem to item -1 of myList

下面展示下,如何一次去多個值。

set myList to {"a", "b", "c", "d", "e", "f"}
set shortList to items 2 through 5 of myList

是的,上面就是執行結果為: {"b", "c", "d", "e"}

reverse

set reversedList to reverse of {2, 3, 4, 6, 7}

{7, 6, 4, 3, 2}

獲取陣列長度

set theListLength to the length of {"ds", 1, 2, 3}
set theListLength to the count of {"ds", 1, 2, 3}

the length of 和 the count of 效果是一樣的。就是獲取列表的長度

隨機取值

set x to some item of {1, 2, 3, 4, 5, 7, 7, 6, 5}

隨機返回列表中的任一元素

型別轉換

set myList to {"a"}
set myString to "b"
--set result to myList & (myString as list)
set result to myList & myString

感覺可以對於js學習,弱型別語言都可以自動型別轉換的。

除了通過型別轉換將一個字串變成一個列表,你還可以建立一個列表,列表的元素是組成字 符串的每一個字母。

set itemized to every character of "Nealyang"

{"N", "e", "a", "l", "y", "a", "n", "g"}

相比於單詞,我們還可以把一個句子按照單詞分開。這裡我們可以使用蘋果指令碼的去限器( AppleScript’s text item delimiters)實現

首先定義一個字元作為分割文字的標記,以這個標記 分割出來的元素將被包含在列表裡。

優秀的指令碼編寫要求如果蘋果指令碼文字去限器的值被更改了,一旦完 成任務還要將它改回原來的值

set myString to "neal's personal website is www.nealyang.cn"
set oldDelimiters to AppleScript's text item delimiters
set AppleScript's text item delimiters to " "
set myList to every text item of myString
set AppleScript's text item delimiters to oldDelimiters
get myList

{"neal's", "personal", "website", "is", "www.nealyang.cn"}

注意這裡設定完 AppleScript's text item delimiters 後,分割用 every text item of 不是every character of

空格 " "我們是可以自定義的。類似js中split

record

理解為js中的物件吧

set stringToBeDisplayed to "Neal is pretty boy"
set tempVar to display dialog stringToBeDisplayed buttons {"So,so", "Don't know", "yes"}
set theButtonPressed to button returned of tempVar
display dialog "You pressed the following button " & theButtonPressed

上面的 button returned of 就是取值的語句。
因為dialog按鈕按下後會返回如下格式:{"button returned":"xxxx"}

簡單的操作如下:

    set test to {neal:"yang"}
    set lala to neal of test

註釋

註釋很簡單

-- 註釋一行

# 註釋一行

(xxx) 註釋多行

條件語句

我們把“if...then”指令叫做“條件語句”(conditional statement)。請注意,條件語句 還需要一個“end if”收尾。

比較簡單,直接上程式碼吧:

set ageEntered to 73
set myAge to 24
if ageEntered is myAge then
    display dialog "You are as old as I am "
    beep
end if
say "this sentence is spoken anyway"

當然,我們也可以在 if ... then ... 和 end if 之間加上 else 關鍵字。
如果“if...then”指令和要執行的語句寫在同一行,那麼就不再需要“end if”

錯誤捕獲

意外的終止是我們所不希望的。比如,你的指令碼需要開啟一個資料夾處理其中的檔案, 但是這個資料夾已經被刪除了,你會希望指令碼允許使用者選擇其它合適的資料夾,而不是意外退出。

你可以把這些可能引起執行錯
誤的語句放入“try...end try”模組中

try
    set x to 1 / 0
on error the error_message number the error_number
    display dialog "Error: " & the error_number & "." & the error_message buttons {"OK"}
end try

Error: -2701.1.0 不能被零除

如果你在“on error”指令後面放上一個變數名,那麼錯誤描述資訊將被賦給這個變數。如果你 在變數名前面加上“number”字樣,那麼錯誤程式碼將被賦給變數。

路徑、資料夾和應用程式

先是硬碟,硬碟下面包含資料夾、應用程式和檔案(上圖中沒有顯示出檔案和應用程式)。所 有這些元素按照一定的層次組織起來。
這樣我們就可以通過路徑(path)這個概念來確定一個檔案 的位置

執行

choose folder

alias "Macintosh HD:Users:Nealyang:Documents:code:code-work:huilianyi:hooks:"

你可以發現,路徑一般的都符合這樣的格式:
硬碟:資料夾:子資料夾:子資料夾:

tell application "Finder"
    open folder "Macintosh HD:Users:Nealyang:Documents:code:code-work:huilianyi:hooks:"
end tell

注意上面的alias。假如我在桌面上為“Documents”資料夾中的檔案“report.cwk”建立了一個替身。如果今後我 移動“report.cwk”到其它位置,或者把它重新命名為“funny_story.cwk”,雙擊替身依然能夠開啟這 個檔案。這是因為替身並不以“Macintosh HD:users:Documents:report.cwk”的方式記錄檔案 “report.cwk”
的儲存位置(和名字),而是記錄這個檔案的ID。

為了避免因為檔案被移動或改名造成的指令碼執行中斷,我們應當讓指令碼記錄檔案的ID而不是 “符號連結”的路徑

set thePath to alias "Macintosh HD:Users:Nealyang:Documents:code:code-work:huilianyi:hooks:README.md"

## 重複(迴圈)

關鍵字 repeat ... end repeat

列出所選資料夾中所有的資料夾名稱

 set folderSelected to choose folder "Select a folder"
 tell application "Finder"
    set listOfFolders to every folder of folderSelected
 end tell
 
 set theList to {}
 repeat with aFolder in listOfFolders
    set temp to the name of aFolder
    set theList to theList & temp
 end repeat
 

## 函式

這個比較簡單,容易理解。

on test(lala)
    display dialog lala
end tst


test("haha")

上面就是定義了一個test函式,然後下面是呼叫

下面一個return的例子

on largest(a, b)
    if a > b then
        return a
    end if
    return b
end largest

set theLargetst to largest(4, 6)

結束語

如上就是AppleScript大概的基本知識,如果對他感興趣,就趕快動手來寫一寫有意思的Mac指令碼吧~

關於如何利用指令碼呼叫作業系統的程式,可以參考Mac官網的這篇文章

相關文章