Jump to content

Texture between Pixi and THREE


Recommended Posts

I'm trying to merge 2D Pixi graphic into a Threejs scene.
I'm using PIXI.RenderTexture to generate a texture of a Pixi sprite but now i need to pass it as a sampler2D to a Threejs shader.
Is it possible?
How can i extract uSampler from the texture to pass it to the shader?

PS: i don't want to use WebGlExtract to generate canvas, or image, or base64 data fro the new texture, those will kill performances.. 

Thanks to anyone will answer!

Link to comment
Share on other sites

Yes, it is possible, I use it.


As for texture, let me get you the code parts.. i dont have workable fddle, but here it is, int typescript. You can change it to js easily.

First, patches for pixi-v4 so it doesnt store reversed Y textures. 

	export function patchRenderTarget(renderer: any) {
		PIXI.RenderTarget.prototype.calculateProjection = function(destinationFrame: PIXI.Rectangle, sourceFrame: PIXI.Rectangle)
			const pm = this.projectionMatrix;

			sourceFrame = sourceFrame || destinationFrame;


			pm.a = 1 / destinationFrame.width * 2;
			pm.d = -1 / destinationFrame.height * 2;

			pm.tx = -1 - (sourceFrame.x * pm.a);
			pm.ty = 1 - (sourceFrame.y * pm.d);

		renderer.filterManager.quad.map = function(targetTextureFrame: PIXI.Rectangle, destinationFrame: PIXI.Rectangle)
			let x = 0; // destinationFrame.x / targetTextureFrame.width;
			let y = 0; // destinationFrame.y / targetTextureFrame.height;

			this.uvs[0] = x;
			this.uvs[1] = y + (destinationFrame.height / targetTextureFrame.height);

			this.uvs[2] = x + (destinationFrame.width / targetTextureFrame.width);
			this.uvs[3] = y + (destinationFrame.height / targetTextureFrame.height);

			this.uvs[4] = x + (destinationFrame.width / targetTextureFrame.width);
			this.uvs[5] = y;

			this.uvs[6] = x;
			this.uvs[7] = y;

			x = destinationFrame.x;
			y = destinationFrame.y;

			this.vertices[0] = x;
			this.vertices[1] = y;

			this.vertices[2] = x + destinationFrame.width;
			this.vertices[3] = y;

			this.vertices[4] = x + destinationFrame.width;
			this.vertices[5] = y + destinationFrame.height;

			this.vertices[6] = x;
			this.vertices[7] = y + destinationFrame.height;

			return this;

And here is how you render it. Assume that you have "this.app" application and "this.rt" renderTexture.

let obj = this.app.currentScene.getObjectByName('pixiTarget') as THREE.Mesh;
if (!obj) return;

this.renderer.render(this.stage, this.rt);

let mat = obj.material as THREE.MeshBasicMaterial;
let textureProps = this.app.renderer.properties.get(mat.map);
let baseTex =this.rt.baseTexture as any;

textureProps.__webglTexture = baseTex._glTextures[this.renderer.CONTEXT_UID].texture;


Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


  • Recently Browsing   0 members

    • No registered users viewing this page.
  • Create New...