phaser/src/textures/TextureSource.js

346 lines
11 KiB
JavaScript
Raw Normal View History

2018-02-12 16:01:20 +00:00
/**
* @author Richard Davey <rich@photonstorm.com>
2022-02-28 14:29:51 +00:00
* @copyright 2022 Photon Storm Ltd.
2019-05-10 15:15:04 +00:00
* @license {@link https://opensource.org/licenses/MIT|MIT License}
2018-02-12 16:01:20 +00:00
*/
var CanvasPool = require('../display/canvas/CanvasPool');
2017-07-04 12:23:58 +00:00
var Class = require('../utils/Class');
var IsSizePowerOfTwo = require('../math/pow2/IsSizePowerOfTwo');
2017-07-04 12:23:58 +00:00
var ScaleModes = require('../renderer/ScaleModes');
2018-02-08 04:01:44 +00:00
/**
* @classdesc
* A Texture Source is the encapsulation of the actual source data for a Texture.
*
* This is typically an Image Element, loaded from the file system or network, a Canvas Element or a Video Element.
2018-02-08 04:01:44 +00:00
*
* A Texture can contain multiple Texture Sources, which only happens when a multi-atlas is loaded.
*
* @class TextureSource
2018-10-10 09:49:13 +00:00
* @memberof Phaser.Textures
2018-02-08 04:01:44 +00:00
* @constructor
* @since 3.0.0
*
* @param {Phaser.Textures.Texture} texture - The Texture this TextureSource belongs to.
2022-09-27 22:39:23 +00:00
* @param {(HTMLImageElement|HTMLCanvasElement|HTMLVideoElement|Phaser.GameObjects.RenderTexture|WebGLTexture|Phaser.Types.Textures.CompressedTextureData|Phaser.Textures.DynamicTexture)} source - The source image data.
2020-11-23 10:22:13 +00:00
* @param {number} [width] - Optional width of the source image. If not given it's derived from the source itself.
* @param {number} [height] - Optional height of the source image. If not given it's derived from the source itself.
* @param {boolean} [flipY=false] - Sets the `UNPACK_FLIP_Y_WEBGL` flag the WebGL Texture uses during upload.
2018-02-08 04:01:44 +00:00
*/
2017-07-04 12:23:58 +00:00
var TextureSource = new Class({
2017-07-04 12:23:58 +00:00
initialize:
function TextureSource (texture, source, width, height, flipY)
2017-07-04 12:23:58 +00:00
{
if (flipY === undefined) { flipY = false; }
var game = texture.manager.game;
/**
* A reference to the Canvas or WebGL Renderer.
*
* @name Phaser.Textures.TextureSource#renderer
* @type {(Phaser.Renderer.Canvas.CanvasRenderer|Phaser.Renderer.WebGL.WebGLRenderer)}
2018-05-04 17:51:02 +00:00
* @since 3.7.0
*/
this.renderer = game.renderer;
2018-02-08 04:01:44 +00:00
/**
* The Texture this TextureSource instance belongs to.
2018-02-08 04:01:44 +00:00
*
* @name Phaser.Textures.TextureSource#texture
2018-08-02 11:34:57 +00:00
* @type {Phaser.Textures.Texture}
2018-02-08 04:01:44 +00:00
* @since 3.0.0
*/
2017-07-04 12:23:58 +00:00
this.texture = texture;
2018-02-08 04:01:44 +00:00
/**
* The source of the image data.
*
* This is either an Image Element, a Canvas Element, a Video Element, a RenderTexture or a WebGLTexture.
2018-02-08 04:01:44 +00:00
*
* In Phaser 3.60 and above it can also be a Compressed Texture data object.
*
* @name Phaser.Textures.TextureSource#source
2022-09-27 22:39:23 +00:00
* @type {(HTMLImageElement|HTMLCanvasElement|HTMLVideoElement|Phaser.GameObjects.RenderTexture|WebGLTexture|Phaser.Types.Textures.CompressedTextureData|Phaser.Textures.DynamicTexture)}
* @since 3.12.0
*/
this.source = source;
/**
* The image data.
*
* This is either an Image element, Canvas element or a Video Element.
*
* @name Phaser.Textures.TextureSource#image
* @type {(HTMLImageElement|HTMLCanvasElement|HTMLVideoElement)}
2018-02-08 04:01:44 +00:00
* @since 3.0.0
*/
this.image = (source.compressed) ? null : source;
2017-07-04 12:23:58 +00:00
2018-02-08 04:01:44 +00:00
/**
* Holds the compressed textured algorithm, or `null` if it's not a compressed texture.
*
* Prior to Phaser 3.60 this value always held `null`.
2018-02-08 04:01:44 +00:00
*
* @name Phaser.Textures.TextureSource#compressionAlgorithm
2020-11-23 10:22:13 +00:00
* @type {number}
2018-02-08 04:01:44 +00:00
* @default null
* @since 3.0.0
*/
this.compressionAlgorithm = (source.compressed) ? source.format : null;
2017-07-04 12:23:58 +00:00
2018-02-08 04:01:44 +00:00
/**
* The resolution of the source image.
*
* @name Phaser.Textures.TextureSource#resolution
* @type {number}
* @default 1
* @since 3.0.0
*/
2017-07-04 12:23:58 +00:00
this.resolution = 1;
2018-02-08 04:01:44 +00:00
/**
* The width of the source image. If not specified in the constructor it will check
* the `naturalWidth` and then `width` properties of the source image.
*
* @name Phaser.Textures.TextureSource#width
2020-11-23 10:22:13 +00:00
* @type {number}
2018-02-08 04:01:44 +00:00
* @since 3.0.0
*/
this.width = width || source.naturalWidth || source.videoWidth || source.width || 0;
2017-07-04 12:23:58 +00:00
2018-02-08 04:01:44 +00:00
/**
* The height of the source image. If not specified in the constructor it will check
* the `naturalHeight` and then `height` properties of the source image.
*
* @name Phaser.Textures.TextureSource#height
2020-11-23 10:22:13 +00:00
* @type {number}
2018-02-08 04:01:44 +00:00
* @since 3.0.0
*/
this.height = height || source.naturalHeight || source.videoHeight || source.height || 0;
2017-07-04 12:23:58 +00:00
2018-02-08 04:01:44 +00:00
/**
* The Scale Mode the image will use when rendering.
* Either Linear or Nearest.
*
* @name Phaser.Textures.TextureSource#scaleMode
* @type {number}
2018-02-08 04:01:44 +00:00
* @since 3.0.0
*/
2017-07-04 12:23:58 +00:00
this.scaleMode = ScaleModes.DEFAULT;
2018-02-08 04:01:44 +00:00
/**
* Is the source image a Canvas Element?
*
* @name Phaser.Textures.TextureSource#isCanvas
* @type {boolean}
* @since 3.0.0
*/
2019-10-18 04:03:11 +00:00
this.isCanvas = (source instanceof HTMLCanvasElement);
2017-09-20 23:15:31 +00:00
/**
* Is the source image a Video Element?
*
* @name Phaser.Textures.TextureSource#isVideo
* @type {boolean}
* @since 3.20.0
*/
this.isVideo = (window.hasOwnProperty('HTMLVideoElement') && source instanceof HTMLVideoElement);
2018-08-02 11:34:57 +00:00
/**
* Is the source image a Render Texture?
*
* @name Phaser.Textures.TextureSource#isRenderTexture
* @type {boolean}
* @since 3.12.0
*/
2022-09-27 22:39:23 +00:00
this.isRenderTexture = (source.type === 'RenderTexture' || source.type === 'DynamicTexture');
2018-08-02 11:34:57 +00:00
2019-06-21 15:34:47 +00:00
/**
* Is the source image a WebGLTexture?
*
* @name Phaser.Textures.TextureSource#isGLTexture
* @type {boolean}
* @since 3.19.0
*/
this.isGLTexture = (window.hasOwnProperty('WebGLTexture') && source instanceof WebGLTexture);
2019-06-21 15:34:47 +00:00
2018-02-08 04:01:44 +00:00
/**
* Are the source image dimensions a power of two?
*
* @name Phaser.Textures.TextureSource#isPowerOf2
* @type {boolean}
* @since 3.0.0
*/
this.isPowerOf2 = IsSizePowerOfTwo(this.width, this.height);
2018-02-08 04:01:44 +00:00
/**
* The WebGL Texture of the source image. If this TextureSource is driven from a WebGLTexture
* already, then this is a reference to that WebGLTexture.
2018-02-08 04:01:44 +00:00
*
* @name Phaser.Textures.TextureSource#glTexture
* @type {?WebGLTexture}
2018-02-08 04:01:44 +00:00
* @default null
* @since 3.0.0
*/
this.glTexture = null;
/**
* Sets the `UNPACK_FLIP_Y_WEBGL` flag the WebGL Texture uses during upload.
*
* @name Phaser.Textures.TextureSource#flipY
* @type {boolean}
* @since 3.20.0
*/
this.flipY = flipY;
this.init(game);
},
2017-07-04 12:23:58 +00:00
2018-02-08 04:01:44 +00:00
/**
* Creates a WebGL Texture, if required, and sets the Texture filter mode.
*
* @method Phaser.Textures.TextureSource#init
* @since 3.0.0
*
* @param {Phaser.Game} game - A reference to the Phaser Game instance.
*/
init: function (game)
{
2020-07-23 15:23:14 +00:00
var renderer = this.renderer;
if (renderer)
2017-07-04 12:23:58 +00:00
{
2020-07-23 15:23:14 +00:00
if (renderer.gl)
{
if (this.isCanvas)
{
2020-07-23 15:23:14 +00:00
this.glTexture = renderer.createCanvasTexture(this.image, false, this.flipY);
}
else if (this.isVideo)
{
2020-07-23 15:23:14 +00:00
this.glTexture = renderer.createVideoTexture(this.image, false, this.flipY);
}
else if (this.isRenderTexture)
{
2022-09-27 22:39:23 +00:00
// this.image = this.source.canvas;
2020-07-23 15:23:14 +00:00
this.glTexture = renderer.createTextureFromSource(null, this.width, this.height, this.scaleMode);
}
2019-06-21 15:34:47 +00:00
else if (this.isGLTexture)
{
2019-06-21 15:34:47 +00:00
this.glTexture = this.source;
}
else if (this.compressionAlgorithm)
{
this.glTexture = renderer.createTextureFromSource(this.source);
}
else
{
2020-07-23 15:23:14 +00:00
this.glTexture = renderer.createTextureFromSource(this.image, this.width, this.height, this.scaleMode);
}
}
2018-08-02 11:34:57 +00:00
else if (this.isRenderTexture)
{
this.image = this.source.canvas;
}
2017-07-04 12:23:58 +00:00
}
2018-06-27 14:27:16 +00:00
if (!game.config.antialias)
2017-07-04 12:23:58 +00:00
{
this.setFilter(1);
}
},
2018-02-08 04:01:44 +00:00
/**
* Sets the Filter Mode for this Texture.
*
* The mode can be either Linear, the default, or Nearest.
*
* For pixel-art you should use Nearest.
*
* @method Phaser.Textures.TextureSource#setFilter
* @since 3.0.0
*
2018-03-29 15:42:20 +00:00
* @param {Phaser.Textures.FilterMode} filterMode - The Filter Mode.
2018-02-08 04:01:44 +00:00
*/
2017-07-04 12:23:58 +00:00
setFilter: function (filterMode)
2017-05-20 01:16:45 +00:00
{
if (this.renderer.gl)
{
this.renderer.setTextureFilter(this.glTexture, filterMode);
}
this.scaleMode = filterMode;
},
2017-07-04 12:23:58 +00:00
/**
* Sets the `UNPACK_FLIP_Y_WEBGL` flag for the WebGL Texture during texture upload.
*
* @method Phaser.Textures.TextureSource#setFlipY
* @since 3.20.0
*
* @param {boolean} [value=true] - Should the WebGL Texture be flipped on the Y axis on texture upload or not?
*/
setFlipY: function (value)
{
if (value === undefined) { value = true; }
this.flipY = value;
return this;
},
/**
* If this TextureSource is backed by a Canvas and is running under WebGL,
* it updates the WebGLTexture using the canvas data.
*
* @method Phaser.Textures.TextureSource#update
2018-05-04 17:51:02 +00:00
* @since 3.7.0
*/
update: function ()
{
var gl = this.renderer.gl;
if (gl && this.isCanvas)
2017-07-04 12:23:58 +00:00
{
this.glTexture = this.renderer.updateCanvasTexture(this.image, this.glTexture, this.flipY);
2017-07-04 12:23:58 +00:00
}
else if (gl && this.isVideo)
{
this.glTexture = this.renderer.updateVideoTexture(this.image, this.glTexture, this.flipY);
}
},
2018-02-08 04:01:44 +00:00
/**
* Destroys this Texture Source and nulls the references.
2018-02-08 04:01:44 +00:00
*
* @method Phaser.Textures.TextureSource#destroy
* @since 3.0.0
*/
destroy: function ()
{
if (this.glTexture)
{
this.renderer.deleteTexture(this.glTexture, true);
}
if (this.isCanvas)
{
CanvasPool.remove(this.image);
}
this.renderer = null;
this.texture = null;
this.source = null;
this.image = null;
this.glTexture = null;
2017-05-20 01:16:45 +00:00
}
2017-07-04 12:23:58 +00:00
});
2017-05-20 01:16:45 +00:00
module.exports = TextureSource;