5
Help us understand the problem. What are the problem?

More than 3 years have passed since last update.

posted at

updated at

Animate CC 2018のカメラをJavaScriptで操作する

Adobe Animate CC 2018はカメラがスクリプトで操作できるようになりました。基本的なズームとパン(移動)を使った作例でご紹介します。jsdo.itに掲げたサンプル001は、カメラがマウスポインタの動きに応じてパンし、水平ドラッグでズームします。

サンプル001■Controlling camera in Animate CC 2018

1710003_003.png
>> jsdo.itへ

カメラとレイヤー深度を設定する

Animate CC 2018のHTML5 Canvasドキュメントでカメラを操作するには、タイムラインで[カメラを追加]しなければなりません(図001)。また、遠近の視差を表現しないとつまらないでしょう。そのためには、高度なレイヤーでレイヤー深度を調整してください(「高度なレイヤーを使用したレイヤー深度の作成」および「高度なレイヤーとレイヤー深度」参照)。

図001■カメラを追加して高度なレイヤーはオンにする

1710003_001.png

カメラを取得する

カメラを操作するには、カメラのオブジェクトを取得しなければなりません。そのためのメソッドがAdobeAn.VirtualCamera.getCamera()です。引数にはメインタイムライン(exportRoot)を渡します。

var camera = AdobeAn.VirtualCamera.getCamera(exportRoot);

カメラをコントロールするためのAPIは、「実行時のインタラクティブカメラの使用」をご参照ください。また、[コードスニペット]に[カメラ]のコードが加わりましたので、そちらを参考にしてもよいでしょう(図002)。

図002■[コードスニペット]パネルの[カメラ]の項目(HTML5 Canvas)

1710003_002.png

カメラのズームを操作する

カメラのズームは、メソッドgetZoom()setZoom()によりそれぞれパーセンテージで取得・設定します。

// ズームのパーセンテージを得る
var zoom = camera.getZoom();
// ズームのパーセンテージを定める
camera.setZoom(zoom);

ステージ上の水平ドラッグでズームイン/ズームアウトさせるのがつぎのコードです。Stage.stagemousedownイベントでドラッグ開始の座標(mouseDown)を得て、ドラッグのDisplayObject.pressmoveイベントによりカメラのズームを変えています。

var mouseDown = new createjs.Point();

stage.addEventListener('stagemousedown', function(event) {
    mouseDown.x = event.stageX;
    mouseDown.y = event.stageY;
});
stage.addEventListener('pressmove', function(event) {
    var zoom = camera.getZoom() + (event.stageX - mouseDown.x) * 0.02;
    if (100 < zoom && zoom < 250) {
        camera.setZoom(zoom);
    }
});

カメラの位置を操作する

カメラの位置は、メソッドgetPosition()setPosition()でそれぞれ取得・設定します。getPosition()メソッドの戻り値は、xyおよびzのプロパティをもったオブジェクトです。setPosition()メソッドには、座標値を3つの引数として渡します。

// カメラの位置を得る
var position = camera.getPosition();
// カメラの位置を定める
camera.setPosition(x, y, z);

つぎのコードは、マウスポインタがステージ中央から上下左右どちらにあるかによって、カメラの位置を動かします。アニメーションはTicker.tickイベントのリスナー関数で扱います。そうすると、マウスポインタの座標が取れませんので、Stage.stagemousemoveイベントで座標を変数に納めました。なお、ステージ(Canvas)の大きさを調べるとき注意すべきことについて、「HTML5 Canvasで書き出したCanvasの大きさが倍になる」をご参照ください。

var stageCenter = new createjs.Point(
    canvas.width / stage.scaleX / 2,
    canvas.height / stage.scaleY / 2
);
var mouseMove = new createjs.Point();
var mouseDown = new createjs.Point();
stage.addEventListener('stagemousemove', function(event) {
    mouseMove.x = event.stageX;
    mouseMove.y = event.stageY;
});
createjs.Ticker.addEventListener('tick', function(event) {
    var position = camera.getPosition();
    var positionX = (mouseMove.x > stageCenter.x) ? position.x - 1 : position.x + 1;
    var positionY = (mouseMove.y > stageCenter.y) ? position.y - 1 : position.y + 1;
    if (-90 < positionX && positionX < 90) {
        position.x = positionX;
    }
    if (-40 < positionY && positionY < 0) {
        position.y = positionY;
    }
    camera.setPosition(position.x, position.y, position.z);
});

ここでひとつ、ECMAScript 6の新しいMathクラスのメソッドをご紹介します。引数の符号(sign)つまり正か負か0かを、それぞれ+1、-1、0で返すMath.sign()です。このメソッドを使うと、上記コードでカメラの動く方向を決める条件(3項)演算子の式が、つぎのように書き替えられます。

// var positionX = (mouseMove.x > stageCenter.x) ? position.x - 1 : position.x + 1;
// var positionY = (mouseMove.y > stageCenter.y) ? position.y - 1 : position.y + 1;
var positionX = position.x + Math.sign(stageCenter.x - mouseMove.x);
var positionY = position.y + Math.sign(stageCenter.y - mouseMove.y);

以上のスクリプトをまとめたのが、つぎのコード001です。冒頭のサンプル001は、FLAファイルのメインタイムラインにこのコードを書いてパブリッシュしました。

コード001■カメラをマウスポインタの移動でパン/ドラッグでズームする

var camera = AdobeAn.VirtualCamera.getCamera(exportRoot);
var stageCenter = new createjs.Point(
    canvas.width / stage.scaleX / 2,
    canvas.height / stage.scaleY / 2
);
var mouseMove = new createjs.Point();
var mouseDown = new createjs.Point();
stage.addEventListener('stagemousemove', function(event) {
    mouseMove.x = event.stageX;
    mouseMove.y = event.stageY;
});
createjs.Ticker.addEventListener('tick', function(event) {
    var position = camera.getPosition();
    var positionX = position.x + Math.sign(stageCenter.x - mouseMove.x);
    var positionY = position.y + Math.sign(stageCenter.y - mouseMove.y);
    if (-90 < positionX && positionX < 90) {
        position.x = positionX;
    }
    if (-40 < positionY && positionY < 0) {
        position.y = positionY;
    }
    camera.setPosition(position.x, position.y, position.z);
});
stage.addEventListener('stagemousedown', function(event) {
    mouseDown.x = event.stageX;
    mouseDown.y = event.stageY;
});
stage.addEventListener('pressmove', function(event) {
    var zoom = camera.getZoom() + (event.stageX - mouseDown.x) * 0.02;
    if (100 < zoom && zoom < 250) {
        camera.setZoom(zoom);
    }
});

[追記: 2017年10月29日]「カメラの位置を操作する」に、Math.sign()メソッドによるコードの書き替えを追加。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Sign upLogin
5
Help us understand the problem. What are the problem?