@@ -43,26 +43,10 @@ this.createjs = this.createjs||{};
4343 * @constructor
4444 * @param {StageGL } stage The default stage to use when none is supplied.
4545 */
46- function WebGLInspector ( stage ) {
47- this . EventDispatcher_constructor ( ) ;
48-
49- // public properties:
50-
51- // private properties:
52- /**
53- * The internal reference to the default stage this Inspector is for.
54- * @property _stage
55- * @protected
56- * @type {StageGL }
57- */
58- this . _stage = stage ;
59-
60- // and begin
61- this . _initializeWebGLInspector ( ) ;
62- }
46+ function WebGLInspector ( stage ) { }
6347 var p = createjs . extend ( WebGLInspector , createjs . EventDispatcher ) ;
6448
65- // static :
49+ // properties :
6650 /**
6751 * Alternate output for debugging situations where "console" is not available, i.e. Mobile or remote debugging.
6852 * Expects object with a "log" function that takes any number of params.
@@ -72,84 +56,101 @@ this.createjs = this.createjs||{};
7256 * @static
7357 * @protected
7458 */
75- p . alternateOutput = undefined ;
59+ WebGLInspector . alternateOutput = undefined ;
7660
77- // getter / setters:
78-
79- // ctor:
8061 /**
81- * @method _initializeWebGL
82- * @protected
62+ * Default stage to assume when non provided
63+ * @type {StageGL }
64+ * @private
8365 */
84- p . _initializeWebGLInspector = function ( ) { } ;
66+ WebGLInspector . stage = undefined ;
8567
8668// public methods:
69+ /**
70+ * Utility to call the right logging
71+ * @params *
72+ */
73+ WebGLInspector . log = function ( ) {
74+ ( WebGLInspector . alternateOutput ? WebGLInspector . alternateOutput . log : console . log ) . apply ( this , arguments ) ;
75+ } ;
76+
8777 /**
8878 * Perform all of the logging reports at once.
8979 * @method log
90- * @param {StageGL } [stage=this._stage ] The stage to log information for.
80+ * @param {StageGL } [stage=WebGLInspector.stage ] The stage to log information for.
9181 */
92- p . log = function ( stage ) {
93- if ( ! stage ) { stage = this . _stage ; }
82+ WebGLInspector . logAll = function ( stage ) {
83+ if ( ! stage ) { stage = WebGLInspector . stage ; }
9484
95- console . log ( "Batches Per Draw" , ( stage . _batchID / stage . _drawID ) . toFixed ( 4 ) ) ;
96- this . logContextInfo ( stage . _webGLContext ) ;
97- this . logDepth ( stage . children , "" ) ;
98- this . logTextureFill ( stage ) ;
85+ WebGLInspector . log ( "Batches Per Draw" , ( stage . _batchID / stage . _drawID ) . toFixed ( 4 ) ) ;
86+ WebGLInspector . logContextInfo ( stage . _webGLContext ) ;
87+ WebGLInspector . logDepth ( stage . children , "" ) ;
88+ WebGLInspector . logTextureFill ( stage ) ;
9989 } ;
10090
10191 /**
102- * Replace the stage's Draw command with an empty draw command. This is useful for testing performance, and ignoring
103- * rendering.
104- * @method toggleGPUDraw
105- * @param {StageGL } [stage=this._stage] The stage to log information for.
106- * @param {Boolean } enabled Force enabled. If left undefined, it will toggle.
92+ * Replace the stage's Draw command with a new draw command. This is useful for:
93+ * <ul>
94+ * <li> Testing performance, with no render cost. See `WebGLInspector.drawEmpty` </li>
95+ * <li> Troubleshooting and tracking loaded textures. See `WebGLInspector.drawTexOnBuffer` </li>
96+ * <li> Misc feature or troubleshooting injection </li>
97+ * </ul>
98+ * @method replaceRenderBatchCall
99+ * @param {StageGL } [stage=WebGLInspector.stage] The stage to log information for.
100+ * @param {Function } newFunc .
107101 */
108- p . toggleGPUDraw = function ( stage , enabled ) {
109- if ( ! stage ) { stage = this . _stage ; }
102+ WebGLInspector . replaceRenderBatchCall = function ( stage , newFunc ) {
103+ if ( ! stage ) { stage = WebGLInspector . stage ; }
110104
111- if ( enabled === undefined ) {
112- enabled = ! ! stage . _drawBuffers_ ;
105+ if ( newFunc === undefined && stage . _renderBatch_ ) {
106+ stage . _renderBatch = stage . _renderBatch_ ;
107+ stage . _renderBatch_ = undefined ;
108+ } else {
109+ if ( stage . _renderBatch_ === undefined ) {
110+ stage . _renderBatch_ = stage . _renderBatch ;
111+ }
112+ stage . _renderBatch = newFunc ;
113113 }
114+ } ;
114115
115- if ( enabled ) {
116- if ( stage . _drawBuffers_ ) {
117- stage . _drawBuffers = stage . _drawBuffers_ ;
118- stage . _drawBuffers_ = undefined ;
119- }
116+ /**
117+ * Identical to replaceRenderBatchCall, but affects the Cover command.
118+ * @method replaceRenderCoverCall
119+ * @param {StageGL } [stage=WebGLInspector.stage] The stage to log information for.
120+ * @param {Function } newFunc .
121+ */
122+ WebGLInspector . replaceRenderCoverCall = function ( stage , newFunc ) {
123+ if ( ! stage ) { stage = WebGLInspector . stage ; }
124+
125+ if ( newFunc === undefined && stage . _renderCover_ ) {
126+ stage . _renderCover = stage . _renderCover_ ;
127+ stage . _renderCover_ = undefined ;
120128 } else {
121- stage . _drawBuffers_ = stage . _drawBuffers ;
122- stage . _drawBuffers = function ( gl ) {
123- if ( this . vocalDebug ) {
124- var output = "BlankDraw[" + this . _drawID + ":" + this . _batchID + "] : " + this . batchReason ;
125- this . alternateOutput ?this . alternateOutput . log ( output ) :console . log ( output ) ;
126- }
127- } ;
129+ if ( stage . _renderCover_ === undefined ) {
130+ stage . _renderCover_ = stage . _renderCover ;
131+ }
132+ stage . _renderCover = newFunc ;
128133 }
129134 } ;
130135
131136 /**
132137 * Recursively walk the entire display tree, log the attached items, and display it in a tree view.
133138 * @method logDepth
134- * @param {Array } [children=this._stage .children] The children array to walk through.
139+ * @param {Array } [children=WebGLInspector.stage .children] The children array to walk through.
135140 * @param {String } prepend What to prepend to this output from this point onwards.
136141 * @param {Function } customLog Which logging function to use, mainly for filtering or formatting output.
137142 * Fallback hierarchy is customLog -> alternateOutput -> console.log.
138143 */
139- p . logDepth = function ( children , prepend , customLog ) {
140- if ( ! children ) { children = this . _stage . children ; }
141- if ( ! prepend ) { prepend = "" ; }
144+ WebGLInspector . logDepth = function ( children , prepend , customLog ) {
145+ if ( ! children ) { children = WebGLInspector . stage . children ; }
146+ if ( ! prepend ) { prepend = "" ; }
142147
143148 var l = children . length ;
144- for ( var i = 0 ; i < l ; i ++ ) {
149+ for ( var i = 0 ; i < l ; i ++ ) {
145150 var child = children [ i ] ;
146- if ( customLog !== undefined ) {
147- customLog ( prepend + "-" , child ) ;
148- } else {
149- this . alternateOutput ?this . alternateOutput . log ( prepend + "-" , child ) :console . log ( prepend + "-" , child ) ;
150- }
151- if ( child . children && child . children . length ) {
152- p . logDepth ( child . children , "|" + prepend , customLog ) ;
151+ ( customLog !== undefined ? customLog : WebGLInspector . log ) ( prepend + "-" , child ) ;
152+ if ( child . children && child . children . length ) {
153+ WebGLInspector . logDepth ( child . children , "|" + prepend , customLog ) ;
153154 }
154155 }
155156 } ;
@@ -159,8 +160,8 @@ this.createjs = this.createjs||{};
159160 * @method logContextInfo
160161 * @param {WebGLRenderingContext } gl The WebGL context to inspect.
161162 */
162- p . logContextInfo = function ( gl ) {
163- if ( ! gl ) { gl = this . _stage . _webGLContext ; }
163+ WebGLInspector . logContextInfo = function ( gl ) {
164+ if ( ! gl ) { gl = WebGLInspector . stage . _webGLContext ; }
164165 var data = "== LOG:\n" ;
165166 data += "Max textures per draw: " + gl . getParameter ( gl . MAX_TEXTURE_IMAGE_UNITS ) + "\n" ;
166167 data += "Max textures active: " + gl . getParameter ( gl . MAX_COMBINED_TEXTURE_IMAGE_UNITS ) + "\n" ;
@@ -171,50 +172,48 @@ this.createjs = this.createjs||{};
171172 data += "Max attributes per vertex: " + gl . getParameter ( gl . MAX_VERTEX_ATTRIBS ) + "\n" ;
172173 data += "WebGL Version string: " + gl . getParameter ( gl . VERSION ) + "\n" ;
173174 data += "======" ;
174- this . alternateOutput ? this . alternateOutput . log ( data ) : console . log ( data ) ;
175+ WebGLInspector . log ( data ) ;
175176 } ;
176177
177178 /**
178179 * Simulate renders and watch what happens for textures moving around between draw calls. A texture moving between
179180 * slots means it was removed and then re-added to draw calls. Performance may be better if it was allowed to stay
180- * in place .
181+ * on GPU, consider sprite sheeting it with something stable .
181182 * @method logTextureFill
182- * @param {StageGL } [stage=this._stage ] The stage to log information for.
183+ * @param {StageGL } [stage=WebGLInspector.stage ] The stage to log information for.
183184 */
184- p . logTextureFill = function ( stage ) {
185- if ( ! stage ) { stage = this . _stage ; }
185+ WebGLInspector . logTextureFill = function ( stage ) {
186+ if ( ! stage ) { stage = WebGLInspector . stage ; }
186187
187188 var dict = stage . _textureDictionary ;
188189 var count = stage . _batchTextureCount ;
189- console . log ( "textureMax:" , count ) ;
190+ WebGLInspector . log ( "textureMax:" , count ) ;
190191 var output = [ ] ;
191- for ( var n in dict ) {
192+ for ( var n in dict ) {
192193 var str = n . replace ( window . location . origin , "" ) ;
193194 var tex = dict [ n ] ;
194- var shifted = tex . _lastActiveInde ?tex . _lastActiveIndex == tex . _activeIndex :false ;
195+ var shifted = tex . _lastActiveIndex ?tex . _lastActiveIndex = == tex . _activeIndex :false ;
195196 output . push ( { src :str , element :tex , shifted :shifted } ) ;
196197 tex . _lastActiveIndex = tex . _activeIndex ;
197198 }
198199
199200 output . sort ( function ( a , b ) {
200- if ( a . element . _drawID == stage . _drawID ) { return 1 ; }
201+ if ( a . element . _drawID === stage . _drawID ) { return 1 ; }
201202 if ( a . element . _drawID < b . element . _drawID ) { return - 1 ; }
202203 return 0 ;
203204 } ) ;
204205
205206 var l = output . length ;
206- for ( var i = 0 ; i < l ; i ++ ) {
207+ for ( var i = 0 ; i < l ; i ++ ) {
207208 var out = output [ i ] ;
208- var active = out . element . _drawID == stage . _drawID ;
209- var output = "[" + out . src + "] " + ( active ?"ACTIVE" :"stale" ) + " " + ( out . shifted ?"steady" :"DRIFT" ) ;
210- this . alternateOutput ?this . alternateOutput . log ( output , out . element ) :console . log ( output , out . element ) ;
209+ var active = out . element . _drawID === stage . _drawID ;
210+ WebGLInspector . log ( "[" + out . src + "] " + ( active ?"ACTIVE" :"stale" ) + " " + ( out . shifted ?"steady" :"DRIFT" ) , out . element ) ;
211211 }
212212 } ;
213213
214-
215214// protected methods:
216215
217- // static methods:
216+ // utility methods:
218217 /**
219218 * Utility function for use with {{#crossLink "logDepth"))((/crossLink}}. Logs an item's position and registration.
220219 * Useful to see if something is being forced off screen or has an integer position.
@@ -224,16 +223,114 @@ this.createjs = this.createjs||{};
224223 * @static
225224 */
226225 WebGLInspector . dispProps = function ( prepend , item ) {
227- if ( ! prepend ) { prepend = "" ; }
226+ if ( ! prepend ) { prepend = "" ; }
228227
229228 var p = "\tP:" + item . x . toFixed ( 2 ) + "x" + item . y . toFixed ( 2 ) + "\t" ;
230229 var r = "\tR:" + item . regX . toFixed ( 2 ) + "x" + item . regY . toFixed ( 2 ) + "\t" ;
231230
232- if ( ! this . alternateOutput ) {
233- console . log ( prepend , item . toString ( ) + "\t" , p , r ) ;
231+ WebGLInspector . log ( prepend , item . toString ( ) + "\t" , p , r ) ;
232+ } ;
233+
234+ /**
235+ * Utility function for use with {{#crossLink "replaceRenderBatchCall"))((/crossLink}}.
236+ * Performs no GL draw command.
237+ */
238+ WebGLInspector . drawEmptyBatch = function ( ) {
239+ WebGLInspector . log ( "BlankBatch[" + this . _drawID + ":" + this . _batchID + "] : " + this . batchReason ) ;
240+ this . _batchVertexCount = 0 ;
241+ this . _batchID ++ ;
242+ } ;
243+
244+ /**
245+ * Utility function for use with {{#crossLink "replaceRenderCoverCall"))((/crossLink}}.
246+ * Performs no GL draw command.
247+ */
248+ WebGLInspector . drawEmptyCover = function ( ) {
249+ WebGLInspector . log ( "BlankCover[" + this . _drawID + ":" + this . _batchID + "] : " + this . batchReason ) ;
250+ this . _batchID ++ ;
251+ } ;
252+
253+ /**
254+ * Utility function for use with {{#crossLink "replaceRenderBatchCall"))((/crossLink}}.
255+ */
256+ WebGLInspector . drawTexBuffer = function ( ) {
257+ var gl = this . _webGLContext ;
258+ var texSize = 2048 ;
259+
260+ // backup
261+ var batchVertexCount = this . _batchVertexCount ;
262+ var projectionMatrix = this . _projectionMatrix ;
263+ var shader = this . _activeShader ;
264+ var vertices = this . _vertices ;
265+ var indices = this . _indices ;
266+ var uvs = this . _uvs ;
267+ var alphas = this . _alphas ;
268+ var reason = this . batchReason ;
269+
270+ // create
271+ if ( this . _inspectorFrame === undefined ) {
272+ this . _inspectorFrame = this . getRenderBufferTexture ( texSize , texSize ) ;
234273 } else {
235- this . alternateOutput . log ( prepend , item . toString ( ) + "\t" , p , r ) ;
274+ gl . bindFramebuffer ( gl . FRAMEBUFFER , this . _inspectorFrame . _frameBuffer ) ;
275+ gl . clear ( gl . COLOR_BUFFER_BIT ) ;
236276 }
277+
278+ // configure
279+ this . _activeShader = this . _mainShader ;
280+ gl . blendEquationSeparate ( gl . FUNC_ADD , gl . FUNC_ADD ) ;
281+ gl . blendFuncSeparate ( gl . ONE , gl . ONE_MINUS_SRC_ALPHA , gl . ONE , gl . ONE_MINUS_SRC_ALPHA ) ;
282+ gl . viewport ( 0 , 0 , texSize , texSize ) ;
283+
284+ this . _projectionMatrix = new Float32Array ( [ 2 / texSize , 0 , 0 , 0 , 0 , - 2 / texSize , 0 , 0 , 0 , 0 , 1 , 0 , - 1 , 1 , 0 , 1 ] ) ;
285+ this . _vertices = new Float32Array ( this . _batchTextureCount * 2 * createjs . StageGL . INDICIES_PER_CARD ) ;
286+ this . _indices = new Float32Array ( this . _batchTextureCount * 1 * createjs . StageGL . INDICIES_PER_CARD ) ;
287+ this . _uvs = new Float32Array ( this . _batchTextureCount * 2 * createjs . StageGL . INDICIES_PER_CARD ) ;
288+ this . _alphas = new Float32Array ( this . _batchTextureCount * 1 * createjs . StageGL . INDICIES_PER_CARD ) ;
289+ this . batchReason = "LoadedTextureDebug" ;
290+
291+ var squareBase = Math . ceil ( Math . sqrt ( this . _batchTextureCount ) ) ;
292+ for ( var i = 0 ; i < this . _batchTextureCount ; i ++ ) {
293+ var i1 = i * 6 , i2 = i1 * 2 ;
294+ var row = i % squareBase , col = Math . floor ( i / squareBase ) , size = ( 1 / squareBase ) * texSize ;
295+ this . _vertices [ i2 ] = ( row ) * size ; this . _vertices [ i2 + 1 ] = ( col ) * size ;
296+ this . _vertices [ i2 + 2 ] = ( row ) * size ; this . _vertices [ i2 + 3 ] = ( col + 1 ) * size ;
297+ this . _vertices [ i2 + 4 ] = ( row + 1 ) * size ; this . _vertices [ i2 + 5 ] = ( col ) * size ;
298+ this . _vertices [ i2 + 6 ] = this . _vertices [ i2 + 2 ] ; this . _vertices [ i2 + 7 ] = this . _vertices [ i2 + 3 ] ;
299+ this . _vertices [ i2 + 8 ] = this . _vertices [ i2 + 4 ] ; this . _vertices [ i2 + 9 ] = this . _vertices [ i2 + 5 ] ;
300+ this . _vertices [ i2 + 10 ] = ( row + 1 ) * size ; this . _vertices [ i2 + 11 ] = ( col + 1 ) * size ;
301+ this . _uvs [ i2 ] = 0 ; this . _uvs [ i2 + 1 ] = 1 ;
302+ this . _uvs [ i2 + 2 ] = 0 ; this . _uvs [ i2 + 3 ] = 0 ;
303+ this . _uvs [ i2 + 4 ] = 1 ; this . _uvs [ i2 + 5 ] = 1 ;
304+ this . _uvs [ i2 + 6 ] = 0 ; this . _uvs [ i2 + 7 ] = 0 ;
305+ this . _uvs [ i2 + 8 ] = 1 ; this . _uvs [ i2 + 9 ] = 1 ;
306+ this . _uvs [ i2 + 10 ] = 1 ; this . _uvs [ i2 + 11 ] = 0 ;
307+ this . _indices [ i1 ] = this . _indices [ i1 + 1 ] = this . _indices [ i1 + 2 ] = this . _indices [ i1 + 3 ] = this . _indices [ i1 + 4 ] = this . _indices [ i1 + 5 ] = i ;
308+ this . _alphas [ i1 ] = this . _alphas [ i1 + 1 ] = this . _alphas [ i1 + 2 ] = this . _alphas [ i1 + 3 ] = this . _alphas [ i1 + 4 ] = this . _alphas [ i1 + 5 ] = 1 ;
309+ }
310+
311+ // output
312+ this . _batchVertexCount = this . _batchTextureCount * createjs . StageGL . INDICIES_PER_CARD ;
313+ this . _renderBatch_ ( ) ;
314+ this . _batchID -- ;
315+
316+ // reset and perform
317+ gl . bindFramebuffer ( gl . FRAMEBUFFER , this . _batchTextureOutput . _frameBuffer ) ;
318+
319+ var shaderData = this . _builtShaders [ this . _renderMode ] ;
320+ gl . blendEquationSeparate ( shaderData . eqRGB , shaderData . eqA ) ;
321+ gl . blendFuncSeparate ( shaderData . srcRGB , shaderData . dstRGB , shaderData . srcA , shaderData . dstA ) ;
322+ gl . viewport ( 0 , 0 , this . _viewportWidth , this . _viewportHeight ) ;
323+
324+ this . _activeShader = shader ;
325+ this . _batchVertexCount = batchVertexCount ;
326+ this . _projectionMatrix = projectionMatrix ;
327+ this . _vertices = vertices ;
328+ this . _indices = indices ;
329+ this . _uvs = uvs ;
330+ this . _alphas = alphas ;
331+ this . batchReason = reason ;
332+
333+ this . _renderBatch_ ( ) ;
237334 } ;
238335
239336 createjs . WebGLInspector = createjs . promote ( WebGLInspector , "EventDispatcher" ) ;
0 commit comments