如何执行 AppleScript“复制”的等效操作来自脚本桥的命令?

发布于 2024-09-10 19:46:28 字数 464 浏览 4 评论 0原文

有没有办法从 Scripting Bridge 在容器内进行远程复制?在 AppleScript 中,这看起来像“将 [容器] 的 [元素] 复制到 [容器中的位置]”。例如,在 TextEdit 文档的上下文中,您可以“将其文本的第一段复制到其文本的末尾”,以将第一段复制到文档的末尾,同时保留所有格式。

有没有办法使用 Scripting Bridge 从 Objective-C 进行操作?

我尝试了这样的操作:

SBObject* foo = [container objectAtIndex: 0];
[container addObject: foo];

并收到一条消息“无法添加已存在的对象。”在控制台上;看起来 addObject 和各种 replace* 方法仅在您构建新的 SBObject 实例并插入它时才起作用。

Is there a way to do a remote copy within a container from Scripting Bridge? In AppleScript, this looks like "copy [element] of [container] to [location in container]". For example, in the context of a tell to a TextEdit document, you can "copy first paragraph of its text to end of its text" to copy the first paragraph to the end of the document while preserving all formatting.

Is there any way to do with from Objective-C using Scripting Bridge?

I tried something like this:

SBObject* foo = [container objectAtIndex: 0];
[container addObject: foo];

And got a message "can't add an object that already exists." on the console; it appears that addObject and the various replace* methods only work when you're building a new SBObject instance and inserting it.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

柏林苍穹下 2024-09-17 19:46:33

当 AppleScript 内置 copy 命令的第二个参数是应用程序引用时,AppleScript 会“有效地”为应用程序 duplicateset 命令提供别名,取决于第一个参数是否是另一个引用。为避免混淆,在处理 AppleScript 中的可编写脚本的应用程序时,最好显式使用 duplicateset

对于 SB,您需要在头文件中查找 duplicate... 方法。请注意,SB 的 duplicate 命令是半瘫痪的(SB 有不少缺点),因为它一次只能处理一个对象。大多数应用程序将允许您在单个命令中操作多个对象(请注意其脚本支持中的任何错误),例如 AppleScript 会让您说:

tell application "iTunes"
    duplicate (every track whose artist is "Foo") to (playlist "Bar")
end tell

but SB won't;相反,您必须提取单个引用的列表并迭代它们,一次处理一个。使您的代码相当冗长,并且如果您在其他地方有大量对象,则效率会非常低。

另一个选择是 objc-appscript,它可以正确完成所有这些工作,并且不太容易出现应用程序兼容性问题一般性(正如 Matt Neuburg 所说,“怪异的兼容性”)。另外,您还可以使用 ASTranslate,它将 AppleScript 命令转换为等效的 Python/Ruby/ObjC 语法 - 在弄清楚如何正确表达命令时非常方便:

#import "ITGlue/ITGlue.h"
ITApplication *itunes = [ITApplication applicationWithName: @"iTunes"];
ITReference *ref = [[itunes tracks] byTest: [[ITIts artist] equals: @"Foo"]];
ITDuplicateCommand *cmd = [[ref duplicate] to: [[itunes playlists] byName: @"Bar"]];
id result = [cmd send];

如果您使用的是 10.6,则另一个选择是使用 AppleScriptObjC 桥,它允许您将 AS 和 ObjC 组合在同一个程序中,而无需任何令人讨厌的 NSAppleScript 废话。这将允许您使用 AppleScript 来完成它最擅长的事情(与其他应用程序通信),并使用 ObjC 来完成其他所有事情。官方文档有限制,但是网络- 搜索应该会弹出各种第三方资源。 MacScripter.net 可能是一个不错的起点 - 除了 ASOC 论坛之外,Craig Williams 不久前还发布了一系列教程。

(顺便说一句,Craig 还在 Apress 的 Learn AppleScript 第三版中贡献了有关 ASOC 的一章,该书是我共同撰写的,其中包含大量有关应用程序脚本原理和实践的信息,包括对 set/ 的说明重复/复制。)

When the second parameter to AppleScript's built-in copy command is an application reference, AppleScript 'helpfully' aliases to an application duplicate or set command, depending on whether the first parameter is another reference or not. To avoid confusion, it's best to use duplicate or set explicitly when dealing with scriptable apps in AppleScript.

As for SB, you would need to look for a duplicate... method in the header file. Be aware that SB's duplicate command is semi-crippled (SB has quite a few shortcomings) since it can only deal with a single object at a time. Most applications will allow you to manipulate multiple objects in a single command (caveat any bugs in their scripting support), e.g. AppleScript will let you say:

tell application "iTunes"
    duplicate (every track whose artist is "Foo") to (playlist "Bar")
end tell

but SB won't; instead you have to extract a list of single references and iterate over those, processing them one at a time. Makes your code rather longwinded, and can be very inefficient if you've a large number of objects elsewhere.

Another option is objc-appscript, which does all this stuff correctly and is much less prone to application compatibility issues in general ('quirk-for-quirk compatibility', as Matt Neuburg puts it). Plus you get ASTranslate, which converts AppleScript commands to the equivalent Python/Ruby/ObjC syntax - very handy when figuring out how to phrase a command correctly:

#import "ITGlue/ITGlue.h"
ITApplication *itunes = [ITApplication applicationWithName: @"iTunes"];
ITReference *ref = [[itunes tracks] byTest: [[ITIts artist] equals: @"Foo"]];
ITDuplicateCommand *cmd = [[ref duplicate] to: [[itunes playlists] byName: @"Bar"]];
id result = [cmd send];

Yet another option, if you're on 10.6, would be to use the AppleScriptObjC bridge, which allows you to combine AS and ObjC in the same program without any of that nasty NSAppleScript nonsense. That would allow you to use AppleScript for what it's best at (communicating with other apps) and ObjC for everything else. Official documentation is limited, but a web-search should throw up various third-party resources. MacScripter.net might be a good place to start - in addition to the ASOC forum, Craig Williams posted a series of tutorials a while back.

(BTW, Craig also contributed a chapter about ASOC to the third edition of Apress's Learn AppleScript, which I co-wrote, and which includes lots of information on application scripting principles and practices, including clarification of set/duplicate/copy.)

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文