リンクをクリップボードにコピー
コピー完了
appやdocumentなどのオブジェクトが,何のイベントに対応していて捕捉できるか調べたいです。効率よく調べる方法はありますか?
イベント一覧を見てもいまいちどんなときに発動するのかわかりません。現状,対象オブジェクトにすべてのイベントリスナーを追加し,手動で変化を起こして反応を観察しています。
// 例:app.alignDistributePreferencesの変化を何のイベントで捕捉できるか調べる
// 結果:反応するイベントなし
// preact
import { h } from 'preact' ;
import { useEffect } from 'preact/hooks' ;
// adobe
import * as InDesign from 'indesign' ;
const { app } = InDesign ;
const EventList = [
'beforePlace',
'afterPlace',
'afterLinksChanged',
'afterNew',
'beforeDelete',
'afterDelete',
'beforeUpdate',
'afterUpdate',
'beforeEmbed',
'afterEmbed',
'beforeUnembed',
'afterUnembed',
'beforeMove',
'afterMove',
'onInvoke',
'beforeInvoke',
'afterInvoke',
'beforeDisplay',
'beforeQuit',
'afterQuit',
'afterContextChanged',
'afterSelectionChanged',
'afterSelectionAttributeChanged',
// 'beforeDeactivate',
// 'afterActivate',
'afterOpen',
'beforeClose',
'afterClose',
] ;
export const App = () => {
const targetObject = app.alignDistributePreferences ;
const handleEvent = (event) => {
console.log(event.eventType) ;
} ;
const addListeners = () => {
for(let eventLabel of EventList) {
try {
targetObject.addEventListener(eventLabel, handleEvent) ;
} catch(e) {
// skip
}
}
} ;
const removeListeners = () => {
console.log('remove') ;
for(let eventLabel of EventList) {
try {
targetObject.removeEventListener(eventLabel, handleEvent) ;
} catch(e) {
// skip
}
}
} ;
// componentDidMount
useEffect(() => {
console.log('init') ;
addListeners() ;
// componentDidUnmount
return removeListeners ;
}, []) ;
return (
<div>
<sp-button
onClick={removeListeners}
>
Remove Events
</sp-button>
</div>
) ;
} ;
このあたりの仕様はExtendScriptと一緒ですから大体はバブリングしますのでおーまちさんの言われる通りトップレベルオブジェクトでトラップ可能ではないかと思います。
例外として、eventListener周りのイベントはバブリングしませんのでリスナー自体をトラップする必要があります。
ただ、appに当てちゃうとぜ〜んぶ反応するのでテストの際はdocumentに当ててテスト用のドキュメント以外に影響が出ないようにすることが多いです。
たとえば、以下のような構成で…
var listner = app.activeDocument.addEventListener (
‘afterPlace’,
function (ev){
var tg = ev.target;
var mybnds = tg.geometricBounds;
tg.geometricBounds = [mybnds[0],mybnds[1],mybnds[0]+30,mybnds[1]+30];
tg.fit (FitOptions.
...
InDesignで取得可能なイベントは
https://developer.adobe.com/indesign/dom/api/e/Event/
では網羅されていなくて、
https://developer.adobe.com/indesign/dom/api/d/DocumentEvent/
https://developer.adobe.com/indesign/dom/api/i/ImportExportEvent/
https://developer.adobe.com/indesign/dom/api/m/MutationEvent/
https://developer.adobe.com/indesign/dom/api/p/PrintEvent/
あたりも見る必要があります。
お~まちさん、Ten Aさんがおっしゃっているように、ほとんどのイベントは親オブジェクトに伝搬していくので、appにイベントリスナを置いとけば捕まえられます。
捕まえられないのは”This event does not bubble”って書いてあるやつです。メニューアクションのafterInvokeとかがそうで
...リンクをクリップボードにコピー
コピー完了
私がイベントを取得する際は、appオブジェクトにすべてのイベントリスナを設定して、手動操作しています。
イベントは上位オブジェクトに伝播するのでappオブジェクトだけに設定して問題ないと思います。
発生したイベントのEvent.targetもしくはEvent.parentで、どのオブジェクトで発生したかわかるので。
(自信がないので別の方の意見も聞きたいです)
リンクをクリップボードにコピー
コピー完了
すべてのイベントリスナーを設定する方針は一緒なのですね。appだけに網を張っていれば良いなら少し楽になります。ありがとうございます。
私もほかのかたの意見も聞いてみたいので,ここのサイトに解説がある・自分はこうしているなどの声を引き続き募集しております。
リンクをクリップボードにコピー
コピー完了
このあたりの仕様はExtendScriptと一緒ですから大体はバブリングしますのでおーまちさんの言われる通りトップレベルオブジェクトでトラップ可能ではないかと思います。
例外として、eventListener周りのイベントはバブリングしませんのでリスナー自体をトラップする必要があります。
ただ、appに当てちゃうとぜ〜んぶ反応するのでテストの際はdocumentに当ててテスト用のドキュメント以外に影響が出ないようにすることが多いです。
たとえば、以下のような構成で…
var listner = app.activeDocument.addEventListener (
‘afterPlace’,
function (ev){
var tg = ev.target;
var mybnds = tg.geometricBounds;
tg.geometricBounds = [mybnds[0],mybnds[1],mybnds[0]+30,mybnds[1]+30];
tg.fit (FitOptions.proportionally);
tg.fit (FitOptions.centerContent);
});
listner.name = ‘testEvent’;
リンクをクリップボードにコピー
コピー完了
なるほど,特定の書類に影響を封じ込められるのはいいですね。実は当初書いたコードはイベントの削除が不十分で,アプリ終了まで残っていたのでこの対策の重要性を実感しました。ありがとうございます。
リンクをクリップボードにコピー
コピー完了
どのアプリケーションもイベント周りは謎が多いです(^-^;
リンクをクリップボードにコピー
コピー完了
InDesignで取得可能なイベントは
https://developer.adobe.com/indesign/dom/api/e/Event/
では網羅されていなくて、
https://developer.adobe.com/indesign/dom/api/d/DocumentEvent/
https://developer.adobe.com/indesign/dom/api/i/ImportExportEvent/
https://developer.adobe.com/indesign/dom/api/m/MutationEvent/
https://developer.adobe.com/indesign/dom/api/p/PrintEvent/
あたりも見る必要があります。
お~まちさん、Ten Aさんがおっしゃっているように、ほとんどのイベントは親オブジェクトに伝搬していくので、appにイベントリスナを置いとけば捕まえられます。
捕まえられないのは”This event does not bubble”って書いてあるやつです。メニューアクションのafterInvokeとかがそうですね。
リンクをクリップボードにコピー
コピー完了
ありがとうございます。alignDistributePreferencesの場合,もしかしたらMutationEventのafterAttributeChangedが反応するかもしれません(未検証)。
bubbleは意味を知りませんでしたがそういう意味でしたか。イベントが親要素に泡のように浮上していくイメージのようですね。参考になりました。