- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
- 82
- 83
- 84
- 85
- 86
- 87
- 88
- 89
- 90
- 91
- 92
- 93
- 94
- 95
- 96
- 97
- 98
- 99
- 100
- 101
- 102
- 103
- 104
- 105
- 106
- 107
- 108
- 109
- 110
- 111
- 112
- 113
- 114
- 115
- 116
- 117
- 118
import { IRenderableObject, IRendererRenderOptions, Renderer } from '@pixi/core';
import { Container } from '@pixi/display';
import { LayersTreeSearch } from './LayersTreeSearch';
import { generateLayerContainerRenderMethod } from './DisplayMixin';
import type { Stage } from './Stage';
import type { Layer } from './Layer';
/**
* Mixin applied on {@link PIXI.Renderer} when using @pixi/layers.
*/
export interface ILayeredRenderer
{
/** Order/index of last rendered object */
_lastDisplayOrder: number;
/** {@link Layer} currently being rendered */
_activeLayer: Layer;
/** **Internal** method for updating {@link ILayeredRenderer#_lastDisplayOrder} */
incDisplayOrder(): number;
/** **Internal** reference to old render method */
_oldRender(displayObject: IRenderableObject, options?: IRendererRenderOptions): void;
}
/**
* @internal
* @ignore
*/
function generateLayerRendererMethod(_oldRender: any)
{
return function render(displayObject: IRenderableObject, options: any, arg1?: any, arg2?: any, arg3?: any)
{
if (!options || (!options.renderTexture && !options.baseTexture))
{
this._lastDisplayOrder = 0;
}
this._activeLayer = null;
if ((displayObject as Stage).isStage)
{
(displayObject as Stage).updateStage();
}
if (this.plugins.interaction && !this.plugins.interaction.search.worksWithLayers)
{
this.plugins.interaction.search = new LayersTreeSearch();
}
_oldRender.call(this, displayObject, options, arg1, arg2, arg3);
};
}
/**
* Mixes {@link ILayeredRenderer} into {@link PIXI.Renderer}.
*
* This is automatically done on importing @pixi/layers.
*/
export function applyRendererMixin(rendererClass: typeof Renderer): void
{
const RendererProto = rendererClass.prototype as (Renderer & Partial<ILayeredRenderer>);
// Skip if mixin already applied.
if (RendererProto._oldRender)
{
return;
}
Object.assign(RendererProto, {
_lastDisplayOrder: 0,
_activeLayer: null,
incDisplayOrder()
{
return ++this._lastDisplayOrder;
},
_oldRender: Renderer.prototype.render,
});
RendererProto._oldRender = RendererProto.render;
RendererProto.render = generateLayerRendererMethod(RendererProto.render);
}
/**
* Mixes renderer mixin + container mixin for canvas.
*
* If you are using PixiJS' canvas renderer, you'll need to invoke this manually.
*
* @example
* import { CanvasRenderer } from '@pixi/canvas-renderer';
* import { applyCanvasMixin } from '@pixi/layers';
*
* applyCanvasMixin(CanvasRenderer);
*/
// eslint-disable-next-line @typescript-eslint/explicit-module-boundary-types
export function applyCanvasMixin(canvasRenderClass: any): void
{
if (!canvasRenderClass)
{
// eslint-disable-next-line max-len,no-console
console.log('@pixi/layers: Canvas mixin was called with empty parameter. Are you sure that you even need this line?');
return;
}
applyRendererMixin(canvasRenderClass);
const ContainerProto = Container.prototype as any;
if (ContainerProto.containerRenderCanvas)
{
return;
}
ContainerProto.containerRenderCanvas = ContainerProto.renderCanvas;
ContainerProto.renderCanvas = generateLayerContainerRenderMethod(ContainerProto.renderCanvas);
}