Cocoaの日々: Xcode のマクロ定義
こちらの記事をみて、昔 cocoa 勉強会でちょこっと紹介した内容に似たようなのがあったのを思い出しました。
久しぶりなのでブログに書いてみようかと思いました。
Objective-C 2.0 の プロパティ定義文を挿入する UserScript
さきの記事ではテキストマクロとしてプロパティ定義文を挿入して実際のプロパティ名は自分で入力するような形をとっていました。
私はもっと怠け者なので文字入力なしで済ましたいと思ったので UserScript にしました。
UserScript とは
これ。
ちょっとしたことができる仕組みです。
デフォルトで入っているのものでおそらくみんながお世話になっているだろう
コメントアウトのショートカット Cmd+/ は実は Perl で書かれた UserScript が実行されています。
何ができる?
こんなのが実行できます。
- Automator のワークフローを実行
- シェルスクリプト
- LL 言語
- AppleScript
入力としては以下のものを受けられます。
- 選択文字列
- ドキュメント全体
出力はこんな感じ。
- 新規書類で開く
- クリップボードに入れる
- 選択部分の置き換え
- 選択部分の後に挿入
- ドキュメントの内容を置き換え
- ドキュメントの内容の後に挿入
- 警告の表示
メニューから " Edit User Scrippts ..." を選べば編集画面が表示されます。
ショートカットキーもここでわりあてられます。
@property を挿入する UserScript
#!/usr/bin/env ruby lines = `pbpaste` lines.each { |line| if line.match(/([_A-Za-z][_A-Za-z0-9]*\s*)+([\s\*]+)([_A-Za-z][_A-Za-z0-9]*);/) klas = $1 star = $2 ivar = $3 if klas != nil if /\ANSString/ =~ klas print "@property (nonatomic, copy) #{klas.strip} #{star.strip}#{ivar};\n" elsif /\Aid/ =~ klas if /delegate/ =~ ivar print "@property (assign) #{klas.strip} #{star.strip}#{ivar};\n" else print "@property (nonatomic, retain) #{klas.strip} #{star.strip}#{ivar};\n" end elsif /\*/ =~ star print "@property (nonatomic, retain) #{klas.strip} #{star.strip}#{ivar};\n" else print "@property (assign) #{klas.strip} #{star.strip}#{ivar};\n" end elsif star == nil end end }
使い方は
インスタンス変数定義部分をまとめてコピーして挿入したい場所でこのスクリプトを実行。
すると
- NSString は @property (nonatomic, copy)
- delegate という変数名は @property (assign)
- その他オブジェクトは @property (nonatomic, retain)
- オブジェクト以外は @property (assign)
として挿入します。
@synthesize を挿入する UserScript
#!/usr/bin/env ruby lines = `pbpaste` lines.each { |line| if line.match(/([_A-Za-z][_A-Za-z0-9]*\s*)+([\s\*]+)([_A-Za-z][_A-Za-z0-9]*);/) klas = $1 star = $2 ivar = $3 print "@synthesize #{ivar};\n" end }
使い方は
インスタンス変数定義部分をまとめてコピーして挿入したい場所でこのスクリプトを実行。
release を挿入する UserScript
#!/usr/bin/env ruby lines = `pbpaste` def releaseAndNil(variable) print "[#{variable} release], #{variable} = nil;\n" end lines.each { |line| if line.match(/([_A-Za-z][_A-Za-z0-9]*\s*)+([\s\*]+)([_A-Za-z][_A-Za-z0-9]*);/) klas = $1 star = $2 ivar = $3 if klas != nil if /\ANSString/ =~ klas releaseAndNil(ivar) elsif /\Aid/ =~ klas if /delegate/ =~ ivar print "delegate = nil;" else releaseAndNil(ivar) end elsif /\*/ =~ star releaseAndNil(ivar) end end end }
使い方は
インスタンス変数定義部分をまとめてコピーして挿入したい場所でこのスクリプトを実行。
すると
- delegate という変数名の場合は delegate = nil;
- その他オブジェクトは [変数名 release], 変数名 = nil;
- オブジェクト以外の場合は なにも出力しない
として挿入します。
その他
今回のスクリプトは普段使っていて特に問題はありませんでしたが、結構適当なのでコーディングスタイルが違う人は使えない代物かもしれません。ご利用は自己責任でお願いします。