以下の記事の続きのような内容になり、今回も開発・実行環境は p5.js Web Editor を利用します。
●PixiJS を p5.js のキャンバスの上で統合させる形で使う(環境は p5.js Web Editor を利用)【試行錯誤の途中】 - Qiita
https://qiita.com/youtoy/items/bbf9a0790ed9ea353080
この記事でやりたいことは、p5.js で用意したキャンバスを利用しつつ、その上で PixiJS の描画を扱うというものです。上記の記事では、p5.js の draw()
から PixiJS の描画に関わるパラメータの変更を行うところまでやっていました。
しかし、p5.js での描画を行って、それを PixiJS と組み合わせた形にするのができていませんでした(描画が変な状態になっていました)。
今回は、この部分の改善対応を進めていきます。
PixiJS と p5.js を組み合わせて使う下準備
今回の内容を試すための下準備として、ライブラリの読み込みなどが必要になります。
そのあたりの話は、冒頭に掲載していた前の記事に書いているので、そちらをご参照ください
PixiJS の背景透過
前回やろうとして、うまくいっていなかった PixiJS の背景透過から着手します。
ググってみると、以下のやり方ができそうだということが分かりました。
●pixi.jsで背景を半透明にする | Runstant
http://runstant.com/pentamania/projects/82dc0e31
●Transparent Background - PixiJS Examples
https://pixijs.io/examples/#/demos-basic/transparent-background.js
上記のものは、 PIXI.Application()
の中でのオプション指定で transparent: true
を指定する、というもののようでした。これを、前回の記事で作ったプログラムで試すと、メインのキャンバスの背景透過が実現できました。
さらに、p5.js の描画を PixiJS と組み合わせて意図通りの描画をさせる、というものに着手していきます。
p5.js の描画と PixiJS の描画とを組み合わせる
前回の記事では、p5.js で作成したキャンバスを直接 PixiJS の Application()
を紐付けて、この状態で、p5.js のキャンバス上で描画を行ってみたら、意図しない描画の崩れが発生していました。原因に関しては、PixiJS の描画との競合が生じたのか、または別の原因なのかは分かっていない状態でした。
これを改善する方法を考えてみたのですが、PixiJS の描画を p5.js のメインのキャンバスと切り離してやれば良いのではないかと思いました。具体的には、 createGraphics()
を使って PixiJS用の描画レイヤーを準備し、p5.js のメインのキャンバスはこれと分けるという戦略です。
createGraphics() を使った方法を試す
結論から書くと、 createGraphics() を使って PixiJS の描画用レイヤーを作るという方法で、問題は解決できました。まず、そのプログラムを掲載します。
let pg;
let app, bunny;
function setup() {
createCanvas(400, 400);
pg = createGraphics(width, height, WEBGL);
app = new PIXI.Application({
view: pg.elt,
width: width,
height: height,
backgroundColor: 0x2c3e50,
transparent: true,
});
app.loader
.add("bunny", "https://pixijs.io/examples/examples/assets/bunny.png")
.load(startup);
}
function startup() {
bunny = new PIXI.Sprite(app.loader.resources.bunny.texture);
bunny.anchor.set(0.5);
bunny.x = app.renderer.width / 2;
bunny.y = app.renderer.height / 2;
app.stage.addChild(bunny);
}
function draw() {
background(220);
if (bunny) {
bunny.rotation += 0.1;
rect(frameCount % width, frameCount % height, 100, 100);
fill(100, 100, 190);
image(pg, 0, 0);
}
}
先ほど書いていたように、 PIXI.Application()
で、transparent: true
を指定しました。また、PixiJS の描画は、WebGLモードを設定した createGraphics()` で作った部分に紐付けて、p5.js で作成したメインのキャンバス上に
image()` で描画するような形にしています。
そして、PixiJS による描画をメインのキャンバスに描画する前に、p5.js による矩形の描画を行うようにしてみました。
これを実行した結果は以下の通りで、想定通りの動作になりました。
#p5js のキャンバス上で、 #PixiJS の描画と p5js の描画の両方を扱う処理、うまくいったっぽい!
— you (@youtoy) March 19, 2022
中央で画像が回転しているのが PixiJS での描画で、青っぽい四角が動いているのが p5.js による描画で、メインのキャンバスは p5.js の createCanvas() で生成したもののみを用いています。 pic.twitter.com/p8gsWOMzhc
なお、オプション指定の部分で、透過させる背景に backgroundColor: 0x2c3e50
という背景色指定をしていますが、これは透過が失敗した時のために分かりやすいように設定したものです。背景透過がうまくいった場合は、設定した意味がないものになります。
スプライトの個数を増やしてみる
次に、描画するスプライトの数を複数にしてみます。
具体的なプログラムは以下となります。
let pg;
const spriteNumMax = 4;
let app,
bunny = Array(spriteNumMax);
function setup() {
createCanvas(400, 400);
pg = createGraphics(width, height, WEBGL);
app = new PIXI.Application({
view: pg.elt,
width: width,
height: height,
backgroundColor: 0x2c3e50,
transparent: true,
});
app.loader
.add("bunny", "https://pixijs.io/examples/examples/assets/bunny.png")
.load(startup);
}
function startup() {
for (let i = 0; i < spriteNumMax; i++) {
bunny[i] = new PIXI.Sprite(app.loader.resources.bunny.texture);
bunny[i].anchor.set(0.5);
bunny[i].x = app.renderer.width * 0.3 + 50 * i;
bunny[i].y = app.renderer.height * 0.3 + 50 * i;
app.stage.addChild(bunny[i]);
}
}
function draw() {
background(220);
if (bunny[spriteNumMax - 1]) {
for (let i = 0; i < spriteNumMax; i++) {
bunny[i].rotation += 0.05 * (i + 1);
}
rect(frameCount % width, frameCount % height, 100, 100);
fill(100, 100, 190);
image(pg, 0, 0);
}
}
そして、動作している時の様子は以下のとおりです。
先ほどの、#p5js のキャンバス上で、 #PixiJS の描画と p5js の描画の両方を扱う処理のお試しの続き。
— you (@youtoy) March 19, 2022
PixiJS で描画するスプライトの数を複数にしてみた(回転している 4つ)。青っぽい四角が動いている p5.js での描画は先ほどのものと同じ処理で変わりないです。
うまく動いてる! pic.twitter.com/S1qRyL1jkG
無事に意図通りに動きました。
おわりに
今回、p5.js で作ったメインのキャンバス上で、PixiJS と p5.js の描画を両方扱うような処理を試しました。
今後は、PixiJS が得意で p5.js には標準実装されていなそうな処理を扱うネタをやっていければと思います。
【追記】 その後の進捗
元々やりたかったこととして、p5.jsベースのプログラムの中で PixiJS のフィルタを使う、というものがあったのですが、それができそうな感じになってきました。
【p5.js と PixiJS を混ぜるお試しの続き】
— you (@youtoy) March 20, 2022
ついに p5.js Web Editor上の #p5js をベースにしたプログラムで、 #PixiJS のグローフィルタ(PIXI.filters.GlowFilter)を適用する、というのができた!
キー操作でフィルタの ON/OFF もできるようにしていて、動画ではその切り替えも行っています。 pic.twitter.com/FhxTUfnKPO
【カーソルの座標に合わせてグローフィルタのパラメータを変化させる】
— you (@youtoy) March 21, 2022
p5.js Web Editor上の #p5js ベースのプログラムで、 #PixiJS のグローフィルタ(PIXI.filters.GlowFilter)を使う話の続き。
p5.js の mouseX・mouseY の値によって、グローフィルタの色・光り方の強度が変わるようにしてみた。 pic.twitter.com/7yARnZXi3d