追記:エフェクト版についてはCC SlantのStretchingチェック外しのほうがかんたんやもです…。
シェイプレイヤー版
どんな形でもよいですが、長方形パスが一番効果がわかりやすいです。
シェイプトランスフォームのスケールに以下のエクスプレッションを適用。
(レイヤーのトランスフォームではありません)
*長方形パス以外の場合、適宜content(“〇〇”)の名前を変えてください。
var mTopY = content("長方形 1").content("長方形パス 1").size[1];
var mSkew = content("長方形 1").transform.skew;
var mRstPt = [mTopY * -Math.tan(degreesToRadians(mSkew)) , mTopY];
var mLgt = length([0,0],mRstPt);
var mRto = mTopY/mLgt;
[value[0],value[1]*mRto];
歪曲の値を変えても、長さが保たれたままになります!
*歪曲軸はゼロ度のみに対応しています。
エフェクト版
歪曲軸を90度にしてください。
エフェクト項目の『縦横比を固定』チェックを外し、『スケールの高さ』に以下を適用します。
var mTopY = thisLayer.height;
var mSkew = effect("トランスフォーム")("歪曲");
var mRstPt = [mTopY * -Math.tan(degreesToRadians(mSkew)) , mTopY];
var mLgt = length([0,0],mRstPt);
var mRto = mTopY/mLgt;
value*mRto;
歪曲の値を変えても、長さが保たれたままになります!
*歪曲軸は90度のみに対応しています。
*エフェクト『トランスフォーム』を適用したレイヤーがコラップスしていた場合、エフェクト『トランスフォーム』の位置とアンカーポイントに以下を適用すれば、結果がレイヤーに追従するようになります!
- アンカーポイントを[0,0]にして、『value + position;』を適用。
- 位置に『effect(“トランスフォーム”)(“アンカーポイント”);』を適用。
使いどころ
拙作スクリプトの機能用に作ったので、デザイン作業で使うかは未知なんですが、例えば横揺れで弾む場合に使えたりしますね。
解説
AEではシェイプとエフェクトで、なぜかデフォルト歪曲軸が90度違う仕様です。なので、まずはエフェクトの場合は90度回転させときます。
その状態で歪曲させると縦線の長さが伸びていくので、とりあえず『どんだけ伸びたか?』を出します。
元の長さはsizeやheight、原点[0,0]はレイヤーやシェイプの左下とします。
んで、左上点の伸びた結果位置を歪曲(せん断)の式で出します。「座標変換、アフィン変換、skew tan」やらで調べると出てきますね。たいがい行列式で載ってますが、XYに分けると以下です。
X = x + ( tanθ * y )
Y = y
これのxとyに、左上点の元の位置[0,mTopY]を入れて、θに歪曲の値を入れれば、歪曲した結果位置が出るというわけですね。
なぜかAEの歪曲は「Y座標プラス側が下」のはずなのに、「Y座標プラス側が上」の歪曲の形になるので、tanθをマイナスにしてやります。また、歪曲の値(角度)はラジアンに直します。すると以下になります。
X = 0 + mTopY * -Math.tan(degreesToRadians(mSkew));
Y = mTopY;
0 + の部分は意味ないので省略できますね。
この[X,Y] ( エクスプレッション内ではmRstPt ) が、歪曲したときの左上点の位置です。そこと左下原点[0,0]の距離を出します。
var mLgt = length([0,0],mRstPt);
元の長さがmTopYで、歪曲した長さがmLgtなので『どんだけ伸びたか』は mLgt / mTopY ですね。
しかし、伸びた分を縮ませたいので、その逆の割合 mTopY / mLgt をスケールに掛けてやれば、元の長さに戻るというわけです。
mTopYを位置として使ったり長さとして使ったりしていて混乱しますが、原点[0,0]からだと長さも位置もかわらん、ということです。
以上です!
参考:
だえうホームページ C言語で画像のスキュー
画像処理ソリューション アフィン変換