最近想用一用系统自带的提醒事项和日历软件,但是总觉得打开应用操作太麻烦,想通过 Alfred 快捷操作。
但是最后没发现很好用的、现成的 workflow,于是只能研究一下苹果提供的脚本服务。
本来在犹豫,因为不想花功夫去学 AppleScript,幸好发现最近苹果已经支持 JavaScript 来写脚本了,所以就花了半天时间研究了一下。

什么是自动化任务

我这里说的自动化任务,主要是用来提高工作效率的小程序,例如:

  • 定期清理下载文件夹下的特定文件
  • 通过 Alfred 快速创建日历事件,免去鼠标操作
  • 快速实现图片裁剪、文件中的文本替换等任务
  • 通过 Alfred 快速操作浏览器,例如打开某个收藏夹
  • 设置邮箱规则,定期清理无用邮件

在哪里编写、使用我们的脚本

1 Script 应用

苹果提供了 Script Editor 应用
在这里插入图片描述
你可以使用 Object C、AppleScript 或者 JavaScript 编写一些小脚本,按照官方网站说明,可以生成几种类型的脚本:

  • Applets:可以双击执行的小脚本
  • Droplets:可以将文件拖拽到脚本上进行执行
  • Scripts:可以被其他脚本 / 命令行调用、执行的脚本
  • Stay-open scripts:打开后持续执行的小脚本,每 30 秒左右会执行一次

Script 软件的使用说明,可以参考官网

2 automator

编写后的脚本,可以通过多种方式执行,除了上述所说的双击、拖拽文件、命令行以外,还可以在 mac 自带的 automator 中添加、使用 JS 脚本,如下方截图
在这里插入图片描述

3 Alfred

付费软件 Alfred 中的 workflow 中可以添加 AppleScript 或 JavaScript 写的 NSApple 脚本,其中 JavaScript 语言的脚本只能通过 Run Script 添加,不能通过 Run NSAppleScript 添加

在这里插入图片描述
记得选择 oascript(JS) 作为脚本的“语言”
在这里插入图片描述

自动化脚本基本框架

类似 C 语言中的 main 函数,Mac 在执行 JS 脚本时,会调用 run 函数,因此需要在脚本中对该函数进行定义

function run(input, parameters) {
	...
}

Droplets 相对特殊,需要对拖拽到脚本上的文件进行处理,会调用 openDocuments 函数

function openDocuments(droppedItems) {
    // Process the dropped items here
}

如果需要使用 Stay-open scripts,需要在保存脚本时选择相应选项,同时定义 idle

function idle() {
    ...
}

函数

在这里插入图片描述
如果希望在退出脚本时执行特殊动作,需要定义 quit 函数

function quit() {
    app.displayDialog("The script is quitting.")
}

与系统中的应用进行互动

系统中的一些应用是可以与脚本进行互动的,我们需要关心到底有哪些应用支持与脚本互动,又具有哪些能力。
Script 应用提供了词典功能,在词典中定义了系统中支持与脚本互动的所有应用,及其所有动作。
你可以通过 文件 > 打开词典,来打开词典,快捷键 Command + Shift + O
在这里插入图片描述
我们以系统自带的备忘录为例,看看到底有哪些能力
在这里插入图片描述
在实际的使用过程中,当你需要与某个应用互动时,你需要首先使用 Application 生成一个应用,例如我们生成一个 Notes 实例

var notes = Application('Notes');
// 通过 notes 实例与备忘录应用产生互动

例如我可以利用上面生成的 notes 做些事情

// 获取文件夹列表,并打印文件夹名称
var f = notes.folders;
for (i in f) {
	console.log(f[i].name());
}

// 新增一个笔记,并添加到第一个文件夹
var new_note = notes.Note({
	name: '标题',
	body: '内容'
})
notes.folders[0].push(new_note)

进行简单的用户交互

脚本提供了一些用户交互能力,例如调用对话框、用户输入框、文件选择器等。

1 对话框

var app = Application.currentApplication()
app.includeStandardAdditions = true
 
 
var dialogText = "An error has occurred. Would you like to continue?"
app.displayDialog(dialogText, {
    buttons: ["Don't Continue", "Continue"],
    defaultButton: "Continue",
    cancelButton: "Don't Continue"
})
// Result: {"buttonReturned":"Continue"}

在这里插入图片描述

2 用户输入框

var app = Application.currentApplication()
app.includeStandardAdditions = true
 
var alertText = "An error has occurred."
var alertMessage = "The amount of available free space is dangerously low. Would you like to continue?"
app.displayAlert(alertText, {
    message: alertMessage,
    as: "critical",
    buttons: ["Don't Continue", "Continue"],
    defaultButton: "Continue",
    cancelButton: "Don't Continue"
})
// Result: {"buttonReturned":"OK"}

在这里插入图片描述

3 系统通知

var app = Application.currentApplication()
 
app.includeStandardAdditions = true
 
app.displayNotification("All graphics have been converted.", {
    withTitle: "My Graphic Processing Script",
    subtitle: "Processing is complete.",
    soundName: "Frog"
})

在这里插入图片描述

4 文件选择器

var app = Application.currentApplication()
app.includeStandardAdditions = true
 
var document = app.chooseFile({
    withPrompt: "Please select a document to process:"
})
document
// Result: Path("/Users/yourUserName/Documents/ImportantDoc.pages")

在这里插入图片描述

5 用户选项

var app = Application.currentApplication()
app.includeStandardAdditions = true
 
var fruitChoices = ["Apple", "Banana", "Orange"]
var favoriteFruit = app.chooseFromList(fruitChoices, {
    withPrompt: "Select your favorite fruit:",
    defaultItems: ["Apple"]
})
favoriteFruit
// Result: ["Apple"]

在这里插入图片描述

一些遗憾

苹果的脚本虽然支持 JavaScript,但是并不如对 AppleScript 的支持那么好,例如有一些操作就只能提供了 AppleScript 的 API,包括:

  • 调用命令行
  • 模拟用户点击操作

如果你希望使用这些功能,那么可能你还是得学习 AppleScript 语言,或者通过别的方式找到解决方案。

参考

Logo

这里是“一人公司”的成长家园。我们提供从产品曝光、技术变现到法律财税的全栈内容,并连接云服务、办公空间等稀缺资源,助你专注创造,无忧运营。

更多推荐