Archive for 1月, 2014

2014/01/31 Finderで選択中のJPEG画像中のEXIF情報からGPS情報を除去する

気軽にiPhoneで撮った写真をWeb用の素材にする際に、JPEG画像のEXIF情報の中に残ってしまったGPS情報を除去するAppleScriptです。

……ちょうど、昨日のBlu-rayドライブの写真をiPhone 5で撮影。iCloud経由でiPhoneからMac上のiPhotoに転送され、それをAppleScriptからPhotoshopをコントロールして自動リサイズしてWordPressにアップロードしたのですが……

この画像にGPS情報が残っていることが判明(別にいいですけれど)。

JPEG画像からのGPS情報の除去は、割と必要性が高く、広く必要とされる処理だと思います。そこで、フリーで配布されているexiftoolを呼び出して、Finder上で選択中のJPEG画像からEXIF情報中のGPS情報だけを削除するAppleScriptを書いてみました。

もし、実行環境にexiftoolがインストールされていなかったら、WebブラウザでexiftoolのWebサイトをオープンします。

exiftoolはコマンドラインから呼び出すツールですが、ソースからのビルドやコマンドラインからのインストール指定などを行う必要はなく、一般的なインストーラーパッケージで配布されているため、どなたでも簡単に導入できると思います。

exiftool.jpg

本Scriptは、Script Menuに入れて呼び出すことを前提としています。Finder上で処理対象のJPEG画像を選択しておき(複数選択可)、Script Menuから本Scriptを呼び出して処理します。

exiftools.png

スクリプト名:Finder上で選択中の画像からGPS情報を除去する
set aPath to do shell script “which exiftool”
if aPath = “” then
  –Open Exiftool Web
  
open location “http://www.sno.phy.queensu.ca/~phil/exiftool/”
  
return
end if

set aCom to aPath & ” -gps:all= -xmp:all= “

tell application “Finder”
  set aList to selection as alias list
  
if aList = {} then return
end tell

repeat with i in aList
  
  
set jj to POSIX path of i
  
  
if jj ends with “.jpg” or jj ends with “.jpeg” then
    try
      do shell script aCom & quoted form of jj
    end try
  end if
  
end repeat

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/30 光学ドライブのトレイオープン

光学ドライブのトレイのオープンを行うAppleScriptです。shellのdrutilコマンドを呼んでいるだけです。

昔から、コンピュータのCD-ROMドライブをオープンさせるのは、AppleScriptのデモの定番で……自分も、最初にAppleScriptを覚えて実行したのは、ダイアログを表示させたり、CD-ROMドライブをオープンさせるOSAX(AudioCDgh OSAX)をClassic Mac OSにインストールして、オープンさせるというものでした。

「プログラム共有」の機能を使って、LAN上の多数のMacのCD-ROMドライブを一斉にオープンさせたりと、いろいろとイタズ……いえ、実験を繰り返していました。それだけ、光学ドライブの開閉には人一倍思い入れがあります。

ただ……最近は、光学ドライブが標準装備ではなくなって、最新型ではデスクトップ型もノート型もすべて光学ドライブを積まなくなりました。かくして、CD-ROMなどの光学ドライブをイジェクトして遊ぶという「芸」はすたれておりました。

そんな中、Twitter経由で光学ドライブのトレイのオープンについて質問が飛んでいたので、記憶が定かではなかったこともあり、あらためて調べてみました。

USB経由で外付けドライブをつなげることはできるので、自分もBlu-rayドライブを1台用意してあります(映画鑑賞用)。

  「たしか、ナントカutilとかいうコマンドを実行するんだったなー」

ぐらいのあやふやな記憶(昔、新居さんに教わった記憶が……)でなんとか正解にたどりつきました。

これらのScriptを実行すると、複数台の外付け光学ドライブを一斉にイジェクトします。特定のドライブだけイジェクトさせない、といった細かい制御が行いたい場合にはもうひと工夫必要なようです。

drutilコマンドのオプションをTerminal上でman drutilして調べると、けっこういろいろ面白いオプションが見つかります。

自動クローズ可能なドライブであれば、イジェクトもクローズもできるようです(drutil tray close)。

img_2292.JPG
▲ejectスクリプト実行前

img_2293.JPG
▲ejectスクリプト実行後。光学メディアが入っていてもアンマウント&イジェクトされる

スクリプト名:光学ドライブのトレイオープン
do shell script “/usr/bin/drutil eject”

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:光学ドライブのトレイオープン2
do shell script “/usr/bin/drutil tray eject”

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:光学ドライブのトレイオープン(内蔵ドライブのみ)
do shell script “/usr/bin/drutil eject internal”

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:光学ドライブのトレイオープン(外付けドライブのみ)
do shell script “/usr/bin/drutil eject external”

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

drutilのコマンドラインオプションには、external/internalの指定ができるように書いてあるのですが、後日Mac mini+外付けBlu-rayドライブの組み合せでInternal/Externalの区別が可能か実験してみたところ……これらの指定は効きませんでした。external/internalのオプションをつけても、内蔵/外付けの両方ともイジェクトされていました。

img_2294.jpg

img_2295.jpg

なお、あまり必然性はありませんが、DVD PlayerやToastにもイジェクト命令が実装されており、このためだけに使うのはまったくおすすめできませんが、光学ドライブトレイのイジェクトが実行可能です。

スクリプト名:DVD PlayerでDVDをイジェクト
tell application “DVD Player”
  eject dvd
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:Toastで光学ドライブのオープン
tell application “Toast Titanium”
  eject
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/29 Photoshopで作業空間のICC Profileを考慮しつつRGB値からL*a*b*値に変換

Photoshopで、作業空間のICC Profileを考慮しつつ指定のRGB色をL*a*b*に変換するAppleScriptです。

Photoshopの色変換機能を用いると指定の色空間同士の変換が行えますが、たとえばCMYKの色空間でICC Profileを考慮しないのは無意味(出力デバイス不在のCMYKなんて)ですが、RGBからの変換であってもICC Profileを考慮しつつ変換してくれないと困る場合が多いです。

そこで、現在設定中の作業用ICC Profileを考慮しつつ、色変換を行う方法を見つけました。

やり方は簡単で……カラの書類を作って指定のRGB色で塗り、塗った色をcolor samplerで取得して、取得後にL*a*b*の色に変換するというものです。

実際に、色を塗ってGUI側から調べたのと同じ数値がとれています(GUI側は小数点以下を問答無用で削除して表示)。

RGBの作業スペースにsRGBのICC Profileを指定した状態で、R:10, G:0, B:10のRGB色をL*a*b*に変換すると……

Photoshopの内蔵機能だけで変換:
{0.775146484375, 3.227569580078, -3.317077636719}

Photoshop上で実際に塗ってからピックアップ:
{0.857543945312, 3.624450683594, -3.61279296875}

……と、けっこう演算結果が違います(動作確認はPhotoshop CC+OS X 10.9にて実施)。

スクリプト名:Photoshopで作業空間のICC Profileを考慮しつつRGB値からL*a*b*値に変換
set rCol to 10
set gCol to 0
set bCol to 10

set imgHeight to 2
set imgWidth to 2

tell application id “com.adobe.photoshop”
  
  
set aDoc to make new document with properties {height:imgHeight, width:imgWidth, mode:RGB}
  
makePhotoshopSelectionRegion(0, 0, imgWidth, imgHeight) of me –選択
  
fillPhotoshopSelectedRegion(rCol, gCol, bCol) of me –塗りつぶし
  
  
tell aDoc
    set aSampler to make new color sampler with properties {class:color sampler, position:{1, 1}}
    
set myRGBColor to color sampler color of aSampler
  end tell
  
  
set redNum to red of myRGBColor
  
set greenNum to green of myRGBColor
  
set blueNum to blue of myRGBColor
  
  
set {rRes, gRes, bRes} to retLABfromRGBnumList(redNum, greenNum, blueNum) of me
  
  
close every document saving no
  
end tell

return {rRes, gRes, bRes}

–Photoshop上で選択範囲を指定色(RGB)で塗りつぶす
on fillPhotoshopSelectedRegion(rNum, gNum, bNum)
  tell application id “com.adobe.photoshop”
    tell current document
      set aCol to {class:RGB color, red:rNum, green:gNum, blue:bNum}
      
      
fill selection with contents aCol
    end tell
  end tell
end fillPhotoshopSelectedRegion

–Photoshop上で指定矩形を選択する
on makePhotoshopSelectionRegion(x1, y1, x2, y2)
  tell application id “com.adobe.photoshop”
    tell current document
      select region {{x1, y1}, {x2, y1}, {x2, y2}, {x1, y2}} combination type replaced
    end tell
  end tell
end makePhotoshopSelectionRegion

–与えられたリスト数値のRGBデータをLAB値に変換して返す
–R:0〜255, G:0〜255, B:0〜255 
–L*:0.0〜100.0, a*:-128.0〜127.0, b*: -128.0〜127.0
on retLABfromRGBnumList(rNum, gNum, bNum)
  
  
tell application id “com.adobe.photoshop”
    set myLABColor to convert color {class:RGB color, red:rNum, green:gNum, blue:bNum} to Lab
    
    
set L_Num to value_L of myLABColor
    
set A_Num to value_a of myLABColor
    
set B_Num to value_b of myLABColor
    
  end tell
  
  
return {L_Num, A_Num, B_Num}
  
end retLABfromRGBnumList

–与えられたリスト数値のLABデータをRGB値に変換して返す
–R:0〜255, G:0〜255, B:0〜255 
–L*:0.0〜100.0, a*:-128.0〜127.0, b*: -128.0〜127.0
on retRGBfromLABnumList(elNum, aNum, bNum)
  
  
tell application id “com.adobe.photoshop”
    set myRGBColor to convert color {class:Lab color, value_L:elNum, value_a:aNum, value_b:bNum} to RGB
    
    
set redNum to red of myRGBColor
    
set greenNum to green of myRGBColor
    
set blueNum to blue of myRGBColor
  end tell
  
  
set redNum to round redNum rounding as taught in school –四捨五入
  
set greenNum to round greenNum rounding as taught in school –四捨五入
  
set blueNum to round blueNum rounding as taught in school –四捨五入
  
  
  
return {redNum, greenNum, blueNum}
  
end retRGBfromLABnumList

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:Photoshopで普通にRGBからL*a*b*値に変換
set rCol to 10
set gCol to 0
set bCol to 10

set aLAB to retLABfromRGBnumList(rCol, gCol, bCol) of me

–与えられたリスト数値のRGBデータをLAB値に変換して返す
–R:0〜255, G:0〜255, B:0〜255 
–L*:0.0〜100.0, a*:-128.0〜127.0, b*: -128.0〜127.0
on retLABfromRGBnumList(rNum, gNum, bNum)
  
  
tell application id “com.adobe.photoshop”
    set myLABColor to convert color {class:RGB color, red:rNum, green:gNum, blue:bNum} to Lab
    
    
set L_Num to value_L of myLABColor
    
set A_Num to value_a of myLABColor
    
set B_Num to value_b of myLABColor
    
  end tell
  
  
return {L_Num, A_Num, B_Num}
  
end retLABfromRGBnumList

–与えられたリスト数値のLABデータをRGB値に変換して返す
–R:0〜255, G:0〜255, B:0〜255 
–L*:0.0〜100.0, a*:-128.0〜127.0, b*: -128.0〜127.0
on retRGBfromLABnumList(elNum, aNum, bNum)
  
  
tell application id “com.adobe.photoshop”
    set myRGBColor to convert color {class:Lab color, value_L:elNum, value_a:aNum, value_b:bNum} to RGB
    
    
set redNum to red of myRGBColor
    
set greenNum to green of myRGBColor
    
set blueNum to blue of myRGBColor
  end tell
  
  
set redNum to round redNum rounding as taught in school –四捨五入
  
set greenNum to round greenNum rounding as taught in school –四捨五入
  
set blueNum to round blueNum rounding as taught in school –四捨五入
  
  
  
return {redNum, greenNum, blueNum}
  
end retRGBfromLABnumList

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/29 SVGビューワーGapplin v1.2がAppleScriptに対応

SVG(Scalable Vector Graphic)の画像ビューワー「Gapplin」がバージョン1.2でAppleScriptに対応しました。

gapplin.png

SVGはテキスト(XML)ベースのグラフィックデータ形式であり、テキスト処理によりスケーラブルな(拡大縮小自在な)ベクターグラフィックを生成できるフォーマットとして、標準化され(ひそかに)普及しています。メジャーなアプリケーションでは、Adobe IllustratorがSVGの読み書きに対応しています。また、主要なWebブラウザはSVGの表示に対応しています。

このSVGのビューワー(編集はテキストエディットなどで別途行う)であるGapplinがAppleScriptに対応したので、ダウンロードして初見でいろいろいじくってみました。SVGについても、西暦2000年前後に「そういうものが出てきた」という情報を仕入れて以来、久しくさわっていません。

GapplinはWebKitを用いてSVGのプレビューを行っており、同じくWebkitを用いているOS X 10.9.1上のSafari 7.0.x上では、SVG v1.1に準拠しているようです(確認したら、Color Profile以外はだいたいサポートされている雰囲気)。GapplinもOS X 10.9上ではSVG v1.1に対応していることが期待されます。

スクリプト名:Gapplinのアプリケーションの情報を取得
tell application “Gapplin”
  properties
  
–> {frontmost:false, class:application, name:”Gapplin”, version:”1.2″}
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:GapplinでdocumnetとWindowの情報を取得
tell application “Gapplin”
  –オープン中のdocumentオブジェクトの調査
  
set dCount to count every document
  
repeat with i from 1 to dCount
    tell document i
      properties
      
–> {modified:false, source:”
      
–ドキュメントのプロパティを取得すると、SVGのソースが取得できることがわかった
      
    end tell
  end repeat
  
  
–オープン中のWindowオブジェクトの調査
  
set wCount to count every window –見えないWindowまでカウントできてしまうので注意
  
repeat with i from 1 to wCount
    tell window i
      properties
      
–> {zoomable:true, scale:1.0, dark mode:false, zoomed:false, closeable:true, class:window, index:1, visible:true, name:”TestSampleAlpha002.svg”, miniaturizable:true, id:954, miniaturized:false, resizable:true, bounds:{32, 37, 452, 548}, document:document “TestSampleAlpha002.svg”}
    end tell
  end repeat
  
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

SVGとSVGZのファイル形式変換

本アプリのネイティブフォーマットとしてSVGとSVGZ(圧縮SVG画像)を扱えるようです。SVG画像をオープンしてSVGZに変換する機能(あるいはその反対)がGUI側に存在しています。

AppleScript側でSVG/SVGZの変換を行うには、saveコマンドを用いて「as SVG」か「as SVGZ」を指定することでそれぞれの形式を指定したファイルの作成を行えばよいようです(オープン中のSVG画像をSVGZ画像に変換するコマンドはAppleScript用語辞書の中には存在せず)。

……各オブジェクトのプロパティを調査してみたら、documentオブジェクトのcompressed属性がr/o表示になっていません。おもむろに、同属性をfalseからtrueに変更したら、SVGからSVGZに変換されました。保存時に形式を変更するよりも簡単そうです。

SVG書類が存在しているフォルダ内に同名のSVGZ書類が存在する場合には……GUI側から操作するとエラー表示されますが、AppleScript側から操作すると、同名のファイルを削除してからごていねいに変換を行ってくれます(ちょっと驚きました)。

スクリプト名:GapplinでSVGからSVGZへの変換
tell application “Gapplin”
  tell document 1
    set compressed to true –SVGからSVGZへの変換
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

スクリプト名:GapplinでSVGZからSVGへの変換
tell application “Gapplin”
  tell document 1
    set compressed to false –SVGZからSVGへの変換
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

他のファイル形式への変換

SVG/SVGZ形式のファイルをPNG、TIFF、PDFに変換して書き出すことが可能です。
PNG/TIFFについては、原寸からどの程度大きさを変えるかをexportコマンドのscaleオプションで指定可能です。

……が、私の環境ではファイルパスを(拡張子まで)指定してexportさせてみましたが、AppleScriptの実行はエラーも出さずに終了するのですが、ファイル自体が実際には書き出されませんでした。GUIからは「書き出し」を行えるものの、AppleScriptからexportコマンドを実行してもダメでした。

exportコマンドが正常に動作するようになれば、大量のSVGファイルの一括変換をGapplinを用いて行うことができるようになるでしょう。いま一歩といったところです。

スクリプト名:選択したSVG書類をオープンしてTIFF形式で書き出し
tell application “Gapplin”
  close every document saving no –ねんのため、オープン中の書類をすべてクローズ
end tell

set aFile to choose file of type {“public.svg-image”} –オープンするSVG書類を選択

set newDocPath to choose file name –変換後のファイル名
set newDocPath to newDocPath as string

tell application “Gapplin”
  open aFile
  
  
tell window 1
    set dark mode to false
  end tell
  
  
tell document 1
    export to file newDocPath as TIFF
  end tell
  
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/27 Numbers 3.1でファイル保存

コメント欄でCharanさんから教えていただきました。先日のNumbers 3.1で追加されたAppleScript対応機能のうち、ファイル保存を行うsaveコマンドが動作しないものと判断していましたが、「ファイル名を拡張子まで指定すると保存できる」とのこと。

すぐに試してみたところ、まったくそのとおりで現状でもファイル保存が可能でした(えー、なにコレー)。

ただし、ファイル名にかならず拡張子「.numbers」を指定する必要があるため、ちょっとScriptに書き足してみました(ほかにも注意事項あり。後述)。

スクリプト名:Numbers 3.1でファイル保存(パス修正機能つき)
set anAlias to choose file name
set anAliasStr to anAlias as string

–拡張子「.numbers」が指定されていないと保存できないので補ってみた
if anAliasStr does not end with “.numbers” then
  set anAliasStr to anAliasStr & “.numbers”
end if

tell application “Numbers”
  tell document 1
    save in file anAliasStr
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

新規作成したNumbers書類(名称未設定の状態)をAppleScriptでファイル保存すると、オープン中の書類は保存ずみの状態になるのが普通ですが、Numbers 3.1ではオープン中の書類(保存ずみ)は「名称未設定」のままです。

numb10.png

一般的にはこのような挙動はしないはずなので、まだまだ今後のアップデートで動作内容が変わる可能性が高いと思われます。「as Numbers」のオプションも効かない(指定するとエラーになる)ので、現状はまだ暫定的な実装なはずです(でないと困ります)。

現状では、ドキュメントを新規作成していじくった後にファイル保存を行うと、前面に名称未設定のドキュメントのウィンドウが残ったままになるので、「close without saving」(ファイル非保存でクローズ)をdocumentなりwindowなりに対して実行しておく必要が出てきます。この残骸が残る状態は今後のNumbersの新バージョンで修正される可能性があるため、Apple側の将来的な対応も含めて予測して対処を行う必要がありそうです。

ちなみに、Numbers 3.1のAppleScript用語辞書に書かれているように、documentオブジェクトだけではなくwindowオブジェクトに対してもsaveコマンドが効くようです。

スクリプト名:Numbers 3.1でファイル保存(Windowを指定)
set anAlias to choose file name
set anAliasStr to anAlias as string

–拡張子「.numbers」が指定されていないと保存できないので補ってみた
if anAliasStr does not end with “.numbers” then
  set anAliasStr to anAliasStr & “.numbers”
end if

tell application “Numbers”
  tell window 1
    save in file anAliasStr
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

将来的なバージョンアップ(Numbers 3.1以降)での微妙な改修を考慮すると、こんな感じになるでしょうか。ただ、将来のバージョンで確実に動くという保証はありません。

スクリプト名:Numbers 3.1でファイル保存(パス修正機能つき)v2
set anAlias to choose file name
set anAliasStr to anAlias as string

–拡張子「.numbers」が指定されていないと保存できないので補ってみた
if anAliasStr does not end with “.numbers” then
  set anAliasStr to anAliasStr & “.numbers”
end if

tell application “Numbers”
  —オープン中のNumbers書類をすべて破棄
  
close every window without saving –重要な書類がオープンされた状態で実行してはいけない
  
  
–Numbersドキュメントを新規作成
  
make new document
  
  
–最前面のウィンドウで表示されているdocumentを保存
  
tell window 1
    save in file anAliasStr
    
close without saving
  end tell
  
  
–保存されたドキュメントを再オープン。今後はパス指定なしでsaveコマンドの実行のみで保存可能
  
open file anAliasStr
  
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/24 Numbers 3.1にAppleScriptサポート機能が復活

iWork ‘13のNumbers 3.1でAppleScript対応機能が復活しました。ただし、一部に微妙な挙動の変更があるので、注意が必要です。

numb1.png

Mac AppStoreを見ると、「AppleScriptのサポートの向上」と明記されています。

あまりに使えなかったのでめまいがしてゴミ箱行きになっていたiWork ‘13ですが、この機会に動作確認のため再度インストールしてみました。

numb0.png

NumbersのアプリケーションのアイコンをAppleScriptエディタにドラッグ&ドロップしてAppleScript用語辞書の内容を確認。

numb2.png

たしかに、用語辞書がついていますし、その中に「Numbers ‘09 Compatibility Suite」という用語群が用意されています。

Numbers 2.3の用語辞書と内容を比較してみると、「split into columns」と「split into rows」の2つの命令が削除されたほかは、命令、オブジェクトの数は合っているようです。

numb3.png

そこで、本Blogに掲載しているAppleScriptのうち「GUI Scriptingを用いていないもの」と「他のアプリケーションとの連携を行っていないもの(Numbersだけで動作が完結する)」について、すべて動作確認を行ってみました。

多くは以前と同じ動作を確認できたのですが、いくつかの重大な変更が行われていることも確認できました。以下、その内容を紹介します。

非互換スクリプト名:Numbersで書類の情報を取得する

動作内容には変更はないのですが、返り値の一部が異なります。documentのpath属性がfileに変更になっていました。

非互換スクリプト名:Numbersでウィンドウの情報を取得する

返り値の一部が変更されています。Windowオブジェクトのtitledとfloating属性がなくなっていました(影響はほぼない)。

非互換スクリプト名:Numbersで書類を保存する

実行すると「書類を自動保存できませんでした」とダイアログが出て、保存パスを指定できません。ファイルの保存ができないということで、すぐに修正を行うべき重大なバグです。こういうバグを放置したままリリースするとは、US Appleは一体何をやっているのでしょうか?

numb4.png

numb5.png

ねんのために、パスを念入りにfileに変換して指定してみましたが……状況は変わりません。

スクリプト名:Numbers 3.1でファイル保存のテスト
set anAlias to choose file name
set anAliasStr to anAlias as string

tell application “Numbers”
  tell document 1
    save in file anAliasStr –ダメだった(T_T)
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

あと、AppleScript用語辞書の「save」命令のオプションに「as Numbers」という用語が使えると書いてありますが、構文確認(コンパイル)すると、「as number」と解釈されてエラーになります。ちゃんと、実装してから用語辞書に明記してほしいものです。

numb6.png

非互換スクリプト名:Numbersで指定シート上の最初のテーブルと同じデータとサイズでシート&テーブルを連続作成

空きセルから値を取得すると、以前は数値の0が返ってきましたが、いまはmissing valueになります。また、1列目と1行目のヘッダー列の扱いが変わったようで、これらに値を設定することもできません。

非互換スクリプト名:Numbersで新規ドキュメントをオープンする

バンドル内におけるテンプレートのフォルダ位置がResourceフォルダ外に変更になりました。ただし、普通にmake new documentで新規ドキュメントの作成ができるようになったので、今後は無理矢理テンプレートをオープンする方法はつかわなくて大丈夫です。

スクリプト名:Numbers 3.1で新規ドキュメント作成
tell application “Numbers”
  make new document
end tell
–> document “名称未設定 2″ of application “Numbers”

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

今回のNumbers 3.1をAppleScript的に評価すると、60点といったところでしょうか。もともとの機能はほぼ復活して、部分的には以前の実装でおかしかったところ(rangeのnameをまともに扱えなかったり、新規ドキュメント作成がまともにできなかったり)が直っていたりと前向きに評価できます。

その一方で、最も重要な機能ともいえるファイル保存がまともにできないのは大きなマイナスです。空きセルの値の解釈が変更になったことも、プログラムの書き換えが必要になるため、感心しません。

Windowの枚数をカウントさせると、開いてもいないウインドウ(見えないウィンドウ)の枚数まで同じようにカウントできていますが、これは元々の挙動がおかしかったので、変なところで互換性を維持しなくてよいと思います。見えないウィンドウがAppleScriptからカウントできるアプリケーションは、基本的にダメなアプリケーションです(たいへんに残念なレベルです)。

せめてあともう1回、バージョン3.2ぐらいで修正されれば、「元通り」の機能レベルが回復できるのではないでしょうか。

あいかわらず、リリース前にひととおりScriptの動作内容を確認するぐらいはしてもいいと思うのですが、この内容ではリリース前に動作確認はしていないのでしょう。

■参考資料:動作確認実施AppleScriptのリスト
numb7.png

2014/01/21 InDesign CCで、ドキュメントの強制的なクローズ

InDesign CCで、オープン中のすべてのドキュメントの強制的なクローズを行うAppleScriptです。

スクリプト名:InDesign CCで、ドキュメントの強制的なクローズ
forceCloseINDdoc() of me

–InDesignドキュメントの強制的なクローズ
on forceCloseINDdoc()
  try
    using terms from application "Adobe InDesign CC"
      tell application "Adobe InDesign CC"
        set docCount to count every document
        
if docCount = 0 then return
        
tell every document
          close saving no
        end tell
      end tell
    end using terms from
  end try
end forceCloseINDdoc

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/21 InDesign CCで、table中のcellを結合

InDesign CCで、選択中のテキストフレーム内に存在する表のセルを結合するScriptです。

{2,4}のセルと{2,5}のセルを結合して1つのセルにしています。

id2.png
▲実行前

id3.png
▲実行後

スクリプト名:InDesign CCで、table中のcellを結合
tell application "Adobe InDesign CC"
  set a to selection
  
set aa to contents of item 1 of a
  
tell aa
    tell table 1
      merge cell 2 of row 4 with cell 2 of row 5
    end tell
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/21 InDesign CCで、スウォッチ名称一覧を取得

InDesign CCで、スウォッチ名称一覧を取得するScriptです。

InDesign CS3用のScriptを無変更でそのまま動きます。

スクリプト名:InDesign CCで、スウォッチ名称一覧を取得
set swList to retColNameList() of me
–> {”None”, “Registration”, “Paper”, “Black”, “C=100 M=0 Y=0 K=0″, “C=0 M=100 Y=0 K=0″, “C=0 M=0 Y=100 K=0″, “C=15 M=100 Y=100 K=0″, “C=75 M=5 Y=100 K=0″, “C=100 M=90 Y=10 K=0″}

on retColNameList()
  tell application “Adobe InDesign CC”
    set sList to {}
    
    
–スウォッチアイテムの名前と色を取得
    
set allSW to object reference of every swatch
    
repeat with aSW in allSW
      tell aSW
        set aName to name as Unicode text
        
set aColVal to color value as list
        
set the end of sList to contents of aName
      end tell
    end repeat
  end tell
  
  
return sList
  
end retColNameList

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/21 InDesign CCで選択中のテキストフレーム中にある表オブジェクトの情報を取得

InDesign CCの動作確認のために、ドキュメント内で選択中のテキストフレームの中に存在している表オブジェクトのプロパティを調査するテストScriptを書いてみました。

id1.png

InDesign CCについては、さわりはじめたばかりですが、InDesign CS3からあまり変化はないという印象です。

スクリプト名:InDesign CCで選択中のテキストフレーム中にある表オブジェクトの情報を取得
tell application “Adobe InDesign CC”
  set a to selection
  
set aa to contents of item 1 of a
  
tell aa
    tell table 1
      properties
    end tell
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/20 複数キーによるソートテスト(キー数無制限)

複数キーによる2D Listのソーティング(降順)のテスト実装を行ったAppleScriptです。

プログラムを眺めていたら、思ったよりも簡単に複数(上限なし)キー対応できることが分ったので、その場でさくっと書いてしまいました。

キー数にとくに上限はありませんが、キー数を増やせば、それだけ処理に時間がかかります。

MacBook Pro Retina(2012)Core i7 2.66GHzの環境で、リスト要素数が10,000でキーが3つだと2秒程度で処理が終了します。

# 後日、AppleStoreの店頭で3.7GHz Quad CoreのMacProで実験してみたところ、1秒だったり2秒だったりと、さほどMacBook Pro Retinaと差はありませんでした(1秒だと倍ぐらい速いことになりますが)

処理内容はおおまかにいえば……

1パス目:Primary Keyを使って2D Listをソート
2パス目:ソートずみリストのNth Keyの値を順にすべてチェック。同じ値が続く箇所をピックアップして記録
3パス目:2パス目でNth Keyの同値の内容が連続する箇所が存在していた場合には、重複部分のみ取り出して、N+1th Keyで再度ソートしてソート結果を(部分的に)差し替える

(以下、2&3パスを繰り返し)

キーはPrimaryもSecondary以下もすべて1つの1次元リスト(配列)に入れて指定します。キー値リストの内容がソート対象2D Listデータのデータ個数を超えないかどうかはチェックしていますが、キー値リストの内容の重複まではチェックしていません(キー値リストの中に0を入れてもダメ)。

スクリプト名:複数キーによるソートテスト3
script orig
  property aList : {}
end script

set aList of orig to {}

–複数キーによるソートテスト3(複数キーを許容)
set aList to {}
repeat 10000 times
  set the end of aList of orig to {“a”, random number from 1 to 10, random number from 1 to 10, random number from 1 to 100}
end repeat

set sDat to current date
set resList to multiKeySortDescending(aList of orig, {2, 3, 4}) of multiKeySort
set eDat to current date

return (eDat - sDat)

–複数キーによるソート
script multiKeySort
  
  
script spd
    property aList : {} –ソート対象の2D Listが入る
    
property bList : {} –1次キーでソートした結果が入る
    
property cList : {} –1次キーでソートした結果のうち、1次キーで同じ値が連続する範囲が入る {{1,3},{10,20}}
    
    
property dList : {} –2次キーでソートする対象の一部のリストが入る(ワーク用)
    
property eList : {} –2次キーでソートした結果のリストが入る(ワーク用)
  end script
  
  
  
–複数キー(Primary, Secondary……)による降順ソート。キーは指定用のリストに入れる
  
on multiKeySortDescending(aList, keyList)
    
    
–Initialize
    
set aList of spd to {}
    
set bList of spd to {}
    
    
    
–Param Check
    
set aLen to length of keyList
    
if class of keyList is not equal to list then
      return false –キー値のリストがlistではなかった場合
    end if
    
    
–ソート対象の2D Listの要素数を取得
    
set tmpLen to length of first item of aList
    
repeat with i in keyList
      if i > tmpLen then
        return false –キー値として指定した内容が、ソート対象のリストの要素数よりも大きかった場合
      end if
    end repeat
    
    
    
set firstKeyNo to first item of keyList
    
    
–1次キーで2D Listをソート(降順)
    
set bList of spd to shellSortListDescending(aList, firstKeyNo) of me
    
    
–複数キーによるソート検証および実行ループ
    
repeat with iii from 1 to aLen - 1
      
      
set cList of spd to {}
      
set dList of spd to {}
      
set eList of spd to {}
      
      
–n次キーの値が連続する箇所を探す
      
set curData to missing value
      
      
set sucF to false –データ連続箇所検出中フラグ(false=非連続、true=連続中)
      
set biginItem to 0
      
set endItem to 0
      
      
set itemC to 0
      
      
repeat with i in bList of spd
        set thisData to item (item iii of keyList) of i –n次キー
        
        
–現在の値と前の値が等しい(連続箇所を検出した、あるいは連続箇所の中にいる)
        
if curData = thisData then
          
          
if sucF = false then
            set biginItem to itemC
            
set sucF to true
          else if sucF = true then
            –連続箇所の検索継続中、何もしない
          end if
          
        else
          –現在の値と前の値が等しくない(連続していない、あるいは連続箇所の末尾を検出した)
          
if sucF = true then
            set the end of cList of spd to {biginItem, itemC}
            
set sucF to false
          end if
          
          
set curData to thisData
          
        end if
        
        
set itemC to itemC + 1
        
      end repeat
      
      
–n次キーの連続状態の検出中のままリスト末尾に来た場合には、最終データを出力する
      
if sucF = true and curData = thisData then
        set the end of cList of spd to {biginItem, itemC}
      end if
      
      
      
–n次キーによる重複箇所がない場合には、n次キーによるソート結果をそのまま返す
      
if cList of spd = {} then
        return bList of spd
      end if
      
      
–n+1次キーによる部分ソートし直し
      
repeat with i in cList of spd
        set {tmpB, tmpE} to i
        
        
copy items tmpB thru tmpE of (bList of spd) to (dList of spd)
        
set (eList of spd) to shellSortListDescending((dList of spd), (item (iii + 1) of keyList)) of me
        
        
set tmpCounter to 1
        
repeat with ii from tmpB to tmpE
          copy item tmpCounter of (eList of spd) to item ii of (bList of spd)
          
set tmpCounter to tmpCounter + 1
        end repeat
      end repeat
      
    end repeat
    
    
return (bList of spd)
    
  end multiKeySortDescending
  
  
–シェルソートで入れ子のリストを降順ソート
  
on shellSortListDescending(aSortList, aKeyItem)
    script oBj
      property list : aSortList
    end script
    
set len to count oBj’s list’s items
    
set gap to 1
    
repeat while (gap len)
      set gap to ((gap * 3) + 1)
    end repeat
    
repeat while (gap > 0)
      set gap to (gap div 3)
      
if (gap < len) then
        repeat with i from gap to (len - 1)
          set temp to oBj’s list’s item (i + 1)
          
set j to i
          
repeat while ((j gap) and (contents of item aKeyItem of (oBj’s list’s item (j - gap + 1)) < item aKeyItem of temp))
            set oBj’s list’s item (j + 1) to oBj’s list’s item (j - gap + 1)
            
set j to j - gap
          end repeat
          
set oBj’s list’s item (j + 1) to temp
        end repeat
      end if
    end repeat
    
return oBj’s list
  end shellSortListDescending
  
end script

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/20 複数キーによるソートテスト

複数キーによる2D Listのソーティング(降順)のテスト実装を行ったAppleScriptです。

2D Listのソートルーチンはいくつも存在しており、ユーザーによるスピードの向上が行われ、充実したものとなってきました。

ただし、複数キーによるソートルーチンについては、海外を探してはみたもののなかなか見つからず、「根気づよく探すよりも、自分で作った方が早い」という状況でした。

そこで、試験的に実装してみました。MacBook Pro Retina(2012)Core i7 2.66GHzの環境で、リスト要素数が1,000で約1秒以下、要素数を10,000にしても1秒程度(テストデータの作成で時間がかかっていました)。

最短で実装できることを重視したため、3パスでソートするようにしました。

1パス目:Primary Keyを使って2D Listをソート
2パス目:ソートずみリストのPrimary Keyの値を順にすべてチェック。同じ値が続く箇所をピックアップして記録
3パス目:2パス目でPrimary Keyの同値の内容が連続する箇所が存在していた場合には、重複部分のみ取り出して、Secondary Keyで再度ソートしてソート結果を(部分的に)差し替える

という処理にしてみました。

改良の方向性はいくつかあって……

(1)昇順、降順をパラメータで指定
(2)キーの個数を無限に増やせるようにする(再帰処理による?)
(3)スピードアップのために処理内容見直し
(4)Cocoaで処理(AppleScriptObjC)

など、いろいろ考えられます。

スクリプト名:複数キーによるソートテスト2
script orig
  property aList : {}
end script

set aList of orig to {}

–複数キーによるソートテスト2
set aList to {}
repeat 1000 times
  set the end of aList of orig to {"a", random number from 1 to 10, random number from 1 to 100}
end repeat

set sDat to current date
set resList to multiKeySortDescending(aList of orig, 2, 3) of multiKeySort
set eDat to current date

return (eDat - sDat)

–複数キーによるソート
script multiKeySort
  
  
script spd
    property aList : {} –ソート対象の2D Listが入る
    
property bList : {} –1次キーでソートした結果が入る
    
property cList : {} –1次キーでソートした結果のうち、1次キーで同じ値が連続する範囲が入る {{1,3},{10,20}}
    
    
property dList : {} –2次キーでソートする対象の一部のリストが入る(ワーク用)
    
property eList : {} –2次キーでソートした結果のリストが入る(ワーク用)
  end script
  
  
  
–複数キー(Primary, Secondary)による降順ソート
  
on multiKeySortDescending(aList, firstKeyNo, secondKeyNo)
    
    
–Initialize
    
set aList of spd to {}
    
set bList of spd to {}
    
set cList of spd to {}
    
set dList of spd to {}
    
set eList of spd to {}
    
    
–1次キーで2D Listをソート(降順)
    
set bList of spd to shellSortListDescending(aList, firstKeyNo) of me
    
    
    
–1次キーの値が連続する箇所を探す
    
set curData to missing value
    
    
set sucF to false –データ連続箇所検出中フラグ(false=非連続、true=連続中)
    
set biginItem to 0
    
set endItem to 0
    
    
set itemC to 0
    
    
repeat with i in bList of spd
      set thisData to item firstKeyNo of i
      
–set thisData to contents of item firstKeyNo of i
      
      
–現在の値と前の値が等しい(連続箇所を検出した、あるいは連続箇所の中にいる)
      
if curData = thisData then
        
        
if sucF = false then
          set biginItem to itemC
          
set sucF to true
        else if sucF = true then
          –連続箇所の検索継続中、何もしない
        end if
        
      else
        –現在の値と前の値が等しくない(連続していない、あるいは連続箇所の末尾を検出した)
        
if sucF = true then
          set the end of cList of spd to {biginItem, itemC}
          
set sucF to false
        end if
        
        
set curData to thisData
        
      end if
      
      
set itemC to itemC + 1
      
    end repeat
    
    
–1次キーの連続状態の検出中のままリスト末尾に来た場合には、最終データを出力する
    
if sucF = true and curData = thisData then
      set the end of cList of spd to {biginItem, itemC}
    end if
    
    
    
–1次キーによる重複箇所がない場合には、1次キーによるソート結果をそのまま返す
    
if cList of spd = {} then
      return bList of spd
    end if
    
    
–2次キーによる部分ソートし直し
    
repeat with i in cList of spd
      set {tmpB, tmpE} to i
      
      
copy items tmpB thru tmpE of (bList of spd) to (dList of spd)
      
set (eList of spd) to shellSortListDescending((dList of spd), secondKeyNo) of me
      
      
set tmpCounter to 1
      
repeat with ii from tmpB to tmpE
        copy item tmpCounter of (eList of spd) to item ii of (bList of spd)
        
set tmpCounter to tmpCounter + 1
      end repeat
    end repeat
    
    
    
return (bList of spd)
    
  end multiKeySortDescending
  
  
–シェルソートで入れ子のリストを降順ソート
  
on shellSortListDescending(aSortList, aKeyItem)
    script oBj
      property list : aSortList
    end script
    
set len to count oBj’s list’s items
    
set gap to 1
    
repeat while (gap len)
      set gap to ((gap * 3) + 1)
    end repeat
    
repeat while (gap > 0)
      set gap to (gap div 3)
      
if (gap < len) then
        repeat with i from gap to (len - 1)
          set temp to oBj’s list’s item (i + 1)
          
set j to i
          
repeat while ((j gap) and (contents of item aKeyItem of (oBj’s list’s item (j - gap + 1)) < item aKeyItem of temp))
            set oBj’s list’s item (j + 1) to oBj’s list’s item (j - gap + 1)
            
set j to j - gap
          end repeat
          
set oBj’s list’s item (j + 1) to temp
        end repeat
      end if
    end repeat
    
return oBj’s list
  end shellSortListDescending
  
end script

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/18 指定のファイルからFinderタグを取得する

OS X 10.9, MavericksではFinderに「タグ」を付けることができるようになりました。これは、ラベルを拡張したもので、1つのファイルに複数のラベルを付けることができ、その組み合せによって異なる意味を持たせられるものです。

>ファイルにタグを付ける
>ファイルにはFinderからタグを付けることができます。
>ファイルを選択してから、ツールバーに新しく追加されたタグボタンをクリックしましょう。

ただし、このタグはOS X 10.9ではAppleScriptからは取得も設定もできません。だいたい、この手の技術にAppleScriptが追いつくのは、メジャーなOSアップデートを1つ遅れてのことです。そのため、OS X 10.10ではAppleScriptからもFinderタグを設定したり取得したりできるようになることでしょう。

そうはいっても、今日この場ですぐに取得したいというケースもあることでしょう。

そこで、このFinderタグの「正体」を明らかにして、その情報にアクセスしてみましょう。

Finderタグは、

tag1.png

のように、Finder上のファイルに対して付けておくことができます。ただし、Finder上では3つ以上のタグの色を確認できないため、Finderの「情報を見る」コマンドで別途その内容を確認することになります。

tag2.png

shell commandからこのFinderタグにアクセスするには、mdlsコマンドを用います。

kMDItemUserTags                     = (
    "U30ecU30c3U30c8U3099",
    "U30aaU30ecU30f3U30b7U3099",
    "U30a4U30a8U30edU30fc",
    "U30afU3099U30eaU30fcU30f3",
    "U30d5U3099U30ebU30fc",
    "U30e4U30f3U30adU30fc",
    "U30afU3099U30ecU30a4"
)

属性値「kMDItemUserTags 」にFinderタグの文字列が記録されていることが確認できます。

そこで、その通りにAppleScriptを書いてみました。

実際に取得できはするものの、あんまり有用でないというべきか、やはり取得だけではなく設定もできないと面白くなさそうです(xattr -wでできるもよう)。

また、あくまで日本語環境で各ラベルに日本語文字列で色名称が指定されていることを前提としているため、英語環境などで実行すると処理が正しく動作しないことも予想されます。また、「とりあえず動けばいい」という実験的なプログラムであるため、非効率的な処理がまだ見られます。

スクリプト名:指定のファイルからFinderタグを取得する
set a to choose file

set b to detectUserTagsByMDLS(a)
set aList to paragraphs of b
set bList to {}

repeat with i in aList
  set j to contents of i
  
if j is not equal to “” then
    set the end of bList to retStrFromUCode(j) of me
  end if
end repeat
bList
–> {”レッド”, “オレンジ”, “イエロー”, “グリーン”, “ブルー”, “ヤンキー”, “グレイ”}

–指定のファイルからmdlsコマンドでkMDItemUserTagsの内容を取得する
on detectUserTagsByMDLS(aFile)
  set cRes to do shell script “mdls -name kMDItemUserTags “ & quoted form of POSIX path of aFile
  
set dRes to trimStrFromTo(cRes, “(”, “)”) of me
  
  
if dRes = “null” then set dRes to “”
  
  
return dRes
end detectUserTagsByMDLS

–Unicodeを記した文字列から実際の文字を得る
on retStrFromUCode(a)
  
  
if a ends with “,” then
    set a to repChar(a, “\”,”, “”)
  else
    set a to repChar(a, “\”", “”)
  end if
  
  
set ofst1 to offset of “\”" in a
  
set aa to text (ofst1 + 1) thru -1 of a
  
  
set aList to parseByDelim(aa, “\\U”) of me
  
  
set outStr to “”
  
repeat with i in aList
    set j to contents of i
    
    
–display dialog j
    
    
if j is not equal to “” and j is not equal to ” “ then
      set outStr to outStr & string id aHexStrToNum(j) of me
    end if
  end repeat
  
  
return outStr
  
end retStrFromUCode

–文字置換ルーチン
on repChar(origText, targStr, repStr)
  set {txdl, AppleScript’s text item delimiters} to {AppleScript’s text item delimiters, targStr}
  
set temp to text items of origText
  
set AppleScript’s text item delimiters to repStr
  
set res to temp as text
  
set AppleScript’s text item delimiters to txdl
  
return res
end repChar

–与えられた文字列を、指定デリミタ文字でparseしてリストにして返す
on parseByDelim(aData, aDelim)
  set curDelim to AppleScript’s text item delimiters
  
set AppleScript’s text item delimiters to aDelim
  
set dList to text items of aData
  
set AppleScript’s text item delimiters to curDelim
  
return dList
end parseByDelim

–16進数文字列を10進数数値に変換する
on aHexStrToNum(hexStr)
  set hStr to “0123456789ABCDEF”
  
set aNum to 0
  
set aLen to length of hexStr
  
repeat with i from aLen to 1 by -1
    set aCon to contents of character i of hexStr
    
set aVal to (offset of aCon in hStr) - 1
    
set aNum to aNum + aVal * (16 ^ (aLen - i))
  end repeat
  
return aNum as integer
end aHexStrToNum

on trimStrFromTo(aStr, fromStr, toStr)
  –fromStrは前から探す
  
if fromStr is not equal to “” then
    set sPos to (offset of fromStr in aStr) + 1
  else
    set sPos to 1
  end if
  
  
–toStrは後ろから探す
  
if toStr is not equal to “” then
    set b to (reverse of characters of aStr) as string
    
set ePos to (offset of toStr in b)
    
set ePos to ((length of aStr) - ePos)
  else
    set ePos to length of aStr
  end if
  
set aRes to text sPos thru ePos of aStr
  
return aRes
end trimStrFromTo

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/14 色差(ΔE)を求める

L*a*b*空間の2つの色をそれぞれリスト{L1,A1,B1} {L2,A2,B2}に格納して渡すと、色差(ΔE)を計算して返すAppleScriptです。

平方根を求めるSQR(square root , √)については、AppleScriptのデフォルトで機能が存在していなかったので、shellのbcコマンドを呼び出して計算して返すことにしてみました。

さまざまなテストデータを与えて計算させたところ、マイナスの符合が2個連続で出現するとbcコマンドにデクリメント(-1)として解釈されることが判明し、その回避のために数値にカッコを余計につけています。

スクリプト名:色差(ΔE)を求める
set lab1 to {“0.158220246434211″, “1.1118985414505″, “-3.02561831474304″}
set lab2 to {“0.13427734375″, “0.324890136719″, “-3.534973144531″}
set colD1 to retColorDifferenceFromLab(lab1, lab2) of me
–> 0.937762141662

–L*a*b*2色の間の色差(ΔE)を求める
–参考資料:
–http://www.konicaminolta.jp/instruments/knowledge/color/part1/11.html
on retColorDifferenceFromLab(labList1, labList2)
  
  
try
    set {L1, A1, B1} to labList1
    
set {L2, A2, B2} to labList2
  on error errrorStr number erN
    error errrorStr number erN
  end try
  
  
set sText to “echo \”scale=10; sqrt(((” & (L2 as string) & “)-(” & (L1 as string) & “))^2 + ((” & (A2 as string) & “)-(” & (A1 as string) & “))^2 + ((” & (B2 as string) & “)-(” & (B1 as string) & “))^2)\” | bc”
  
set deltaE to do shell script sText
  
  
try
    set deltaE to deltaE as number
  on error errrorStr number erN
    error errrorStr number erN
  end try
  
  
return deltaE
  
end retColorDifferenceFromLab

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/14 指定のクリエータコードに該当するICC Profileをリストアップ

指定のクリエーターコードに該当するICC ProfileをリストアップするAppleScriptです。

{{名称1、ファイルパス1(HFS pathの文字列)}, {名称2、ファイルパス2(HFS pathの文字列)}…..}

という入れ子の(2Dの)リストで結果を返します。

名称が重複するICC Profileを除外するか許容するかをdupFlagで指定します。dupFlagがfalseだと重複を許容せず、trueだと許容します。

2014年、Mac OS Xも10.9になって、まだCreator Code(英数字4文字の、メーカーごとにユニークな値。英字小文字はAppleしか使えない)なんて仕様がOSの中に残っているとは驚きです(フォントまわりにはまだ残っていそうな、、、)。

スクリプト名:指定のクリエータコードに該当するICC Profileをリストアップ
set aList to getICCProfileDataByCreatorCode(“ADBE”, false) of me
–> {{”Adobe RGB (1998)”, “Macintosh HD:System:Library:ColorSync:Profiles:AdobeRGB1998.icc”}, {”AnimePalette”, “Macintosh HD:Library:Application Support:Adobe:Color:Profiles:AnimePalette.icc”}…….

–creatorで抽出したICC Profileのリストを取得する(名称、パス)
–  aCode: ICC ProfileのCreator Code(=”XXXX”)
–  dupFlag: trueだとICC Profileの名称重複を許容、falseだと許容しない
on getICCProfileDataByCreatorCode(aCode, dupFlag)
  tell application “Image Events”
    set aList to every profile whose creator is aCode
    
    
set bList to {}
    
set cList to {}
    
    
repeat with i in aList
      set j to contents of i
      
      
tell j
        
        
–get ICC name
        
try
          set a to name
        on error
          set a to “”
        end try
        
        
–get ICC file path
        
if a is not in cList then –名称が重複するICC Profileを排除する
          if dupFlag = false then
            set the end of cList to a
          end if
          
          
try
            set b to location as alias
            
set b to b as string
            
set the end of bList to {a, b}
          on error
            
          end try
          
        end if
        
      end tell
      
    end repeat
    
    
return bList
    
  end tell
end getICCProfileDataByCreatorCode

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に

2014/01/06 Calendar.appのfile open eventを登録できないバグ@10.9

OS X 10.9, MavericksのCalendar.appで、AppleScriptからfile open alarmを作成しようとすると、

calbug1.png

というド派手なダイアログが出て、イベントの登録が行えないというバグの存在を(いまさら)知りました。

正直、AppleScriptのタイマー実行用にCalendar.appは使っていないので、個人的には影響はないのですが、困っている人もいるようです。

# Calendar.app/iCalは昔からいろいろ問題を起こしていたので、「信用していない」というのが、最大の理由です

コンソールでエラーメッセージを確認してみると……

calbug2.png

などと出ており、まったくお手上げの状況のようです。

file open event作成時のファイルパスをPOSIX pathで渡しても(これが普通)、aliasで渡しても、URL形式で渡しても状況は変わりません(全部試しました)。

Calendar.appやiCal.app、さらにMac App Storeで販売されているタイマーアプリケーションは、どいつもこいつもAppleScriptの定期実行には役立たずだと感じています。で、結局自前でタイマー機能までAppleScriptで作ってしまうので、個人的には困っていません。

スクリプト名:alarm_script
–Calendar.appのopen file alarmのバグの検証用AppleScript
–AppleScript自体の実行は完了するが、Calendar.appがエラーダイアログを表示する

set targetDate to “2015/01/06 20:20:00″
set targetDate to date targetDate

set theoutdatecal to “Timers”
set eventname to “てすと”

set aFilePath to choose file
set aPOSIXpath to POSIX path of aFilePath

(*
tell application “Finder”
  set aURL to URL of aFilePath
end tell
*)

–add outdate events to calendar
tell application “Calendar”
  tell calendar theoutdatecal
    set deactivate_date to make new event with properties {start date:targetDate, summary:eventname, allday event:false, status:confirmed}
  end tell
  
tell deactivate_date
    make new open file alarm at end with properties {trigger interval:1440, filepath:aPOSIXpath}
  end tell
end tell

▼新規書類に ▼カーソル位置に ▼ドキュメント末尾に