[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Public WebGL] WebKit 20-50% slower than Chrome/Minefield using large Float32Array Arrays



Cool demo. I'd like to second Steve's suggestion to use the GPU for
your processing. Check out Evgeny Demidov's simulations at
http://www.ibiblio.org/e-notes/webgl/gpu/contents.htm , most of which
use the OES_texture_float extension via WebGL to hold the simulation's
state.

-Ken

On Thu, Feb 17, 2011 at 6:22 AM, Steve Baker <steve@sjbaker.org> wrote:
>
> If there was ever a job for the GPU, this is it!
>
> I've done this kind of thermal simulation in the GPU in the past - and
> the results were pretty good.  (I used to do simulation of thermal
> imaging in military IR cameras - and we needed to simulate the thermal
> consequences of an explosion).
>
> Make the grid into a texture map - write a shader that takes the last
> iteration's raw data as a texture map and generates one cell of the
> output from it...that would require porting your thermal calculations
> into GLSL - but I'd be surprised if that was hard.   Then you can
> compute the entire update by drawing a single quadrilateral to a second
> texture/FBO.   If the calculation part is really complex, you might need
> to break it into several stages and do each one in a separate rendering
> pass...but it's hard to imagine that this would be difficult.
>
> If you need to do it in 3D then pass a number of adjacent 2D slices as
> textures into a shader that computes a 2D slice as output...you then
> draw one 2D slice with each quadrilateral you draw - but you can do all
> of that in a single draw call.
>
> When you have the calculated result, you can do the false-color
> rendering of the resulting raw data with a second shader that uses a 1D
> texture map to convert temperature to color.
>
> The trick is to make sure that the data never leaves the GPU - do all of
> your storage with textures/FBO's and all of your calculations and
> display in GLSL.
>
> Because the S-L-O-W JavaScript code is now running as a GLSL program in
> the mind-blowingly fast GPU, I bet you could get the raw frame rate for
> a 3D case up to maybe a hundred hertz...much faster than you can display
> it.   This enables you to use much smaller time-steps - which reduces
> the velocities and that drastically improves the parts of the
> calculation that tend towards numerical instability (advection was the
> worst culprit IIRC).
>
>  -- Steve
>
>
> On 02/17/2011 04:23 AM, Thatcher Ulrich wrote:
>> Cool demo.
>>
>> One thing you should try, without even going to WebGL, is filling the
>> canvas using context.putImageData() instead of lots of fillRect calls.
>>  Perhaps also best to render into a 100x100 canvas, and have the
>> browser scale it onto the correct size on the page, instead of doing
>> that in your paint routine.  Though I think the scaling will be smooth
>> instead of blocky; not sure if you want that.
>>
>> The other thing you should definitely do is make a color table instead
>> of making and parsing "hsl(...)" strings for every pixel.
>>
>> Code (untested, edited from yours) would look something like:
>>
>> model2d.displayTemperature = function(canvas, model) {
>>     var ctx = canvas.getContext('2d');
>>     ctx.fillStyle = "rgb(0,0,0)";
>>     ctx.globalCompositeOperation = "destination-atop";
>>
>>     // Set the CSS width/height to the desired display height.
>>     // Better to just do this in the HTML on the page using the
>>     // style attribute.
>>     canvas.style.width = canvas.clientWidth + 'px';
>>     canvas.style.height = canvas.clientHeight + 'px';
>>
>>     // Force the actual source pixel data to be 100x100.
>>     canvas.width = 100;
>>     canvas.height = 100;
>>
>>     var hue;
>>     var rgb;
>>
>>     var columns = model.nx;
>>     var rows = model.ny;
>>     var ycols, ycols_plus_x;
>>
>>     var t = model.t;
>>     var min = model2d.getMinTypedArray(t);
>>     var max = model2d.getMaxTypedArray(t);
>>     var scale = 255/(max - min);
>>     var temp;
>>     var imdata = ctx.getImageData(0, 0, 100, 100);
>>     var data = imdata.data;
>>     for (y = 0; y < rows; y++) {
>>         ycols = y * rows;
>>         var pix_index = y * 100;
>>         for (x = 0; x < columns; x++) {
>>             ycols_plus_x = ycols + x;
>>             temp = model.t[ycols_plus_x];
>>             hue =  Math.abs(Math.round(scale * temp - min) - 255);
>>             // Assume a pre-computed color table!
>>             rgb = color_table[Math.min(Math.floor(hue + 0.5), 255)];
>>             data[pix_index] = rgb.r;
>>             data[pix_index + 1] = rgb.g;
>>             data[pix_index + 2] = rgb.b;
>>             data[pix_index + 3] = rgb.a;
>>             pix_index += 4;
>>         }
>>     }
>>     ctx.putImageData(imdata, 0, 0);
>> }
>>
>> -T
>>
>> On Thu, Feb 17, 2011 at 6:42 AM, Stephen Bannasch
>> <stephen.bannasch@deanbrook.org> wrote:
>>
>>> Here's a test using large Float32Array Typed Arrays (many sized 100x100)
>>> where WebKit ends up 20-50% slower than Chrome and Minefield. In these tests
>>> Minefield edges out Chrome but not by much.
>>>
>>> I found that 90% of the time was spent rendering the false-color thermal map
>>> graphics.
>>>
>>> Suggestions for how to speed this up would be great.
>>>
>>> I created an initial port of our Java Energy2D application running in
>>> JavaScript. The backing model is doing a thermal simulation of conductivity,
>>> convection, and radiation with 10,000 cells.
>>>
>>>  http://visual-demos.dev.concord.org/seasons/earth/model2d.html
>>>
>>> The JavaScript implementation uses JavaScript Typed Arrays so it only works
>>> with browsers that supports WebGL (Chrome 9, recent FireFox betas, and
>>> WebKit nightlies).
>>>
>>> The original Java version of Energy2D can be seen here:
>>> http://energy.concord.org/energy2d/index.html
>>>
>>> The JavaScript simulation model starts with a fixed high-temperature spot in
>>> the middle.
>>>
>>> The basic model simulation space is a 100x100 grid, 10,000 cells the same as
>>> the Java version of Energy2D.
>>>
>>> The JavaScript code is here:
>>> https://github.com/stepheneb/seasons/blob/master/earth/model2d.js
>>>
>>> I'm getting about 4 model iterations/s on Chrome and FF betas, and about 3
>>> on WebKit/Safari.
>>>
>>> I wondered how much of the time was doing graphics and how much was running
>>> the model ... turns out a huge bottleneck is rendering the graphics.
>>>
>>> The demo page renders the false-color thermal map with one of two
>>> techniques: using HTML5 Canvas, or stuffing 10,000 styled divs using
>>> innerHTML. I was surprised when the two methods ended up practically
>>> equivalent in time.
>>>
>>> I'd like to find a much quicker way to render the graphics ... perhaps using
>>> WebGL.
>>>
>>> I'm very impressed at how fast the model calculation runs.
>>>
>>> My tests below run the model for 15s on my MacOS X 10.6.6 PowerBook Pro with
>>> a 2.66 GHz Intel Core i7.
>>>
>>>
>>> Rendering to both the canvas visualization and the table of data:
>>>
>>> Browser                            model steps      model steps/s
>>> --------------------------------------------------------------------
>>> Chrome v9.0.597.102                  59              3.9
>>> Minefield 4.0b12pre (2011-02-16)     60              4.0
>>> WebKit v5.0.3 (6533.19.4, r78685)    48              3.2
>>>
>>>
>>> Rendering just to the canvas visualization:
>>>
>>> Browser                            model steps      model steps/s
>>> --------------------------------------------------------------------
>>> Chrome v9.0.597.102                  68              4.5
>>> Minefield 4.0b12pre (2011-02-16)     84              5.6
>>> WebKit v5.0.3 (6533.19.4, r78685)    64              4.3
>>>
>>>
>>> With rendering to the canvas and the table of data disabled:
>>>
>>> Browser                            model steps      model steps/s
>>> --------------------------------------------------------------------
>>> Chrome v9.0.597.102                 489             32.6
>>> Minefield 4.0b12pre (2011-02-16)    507             33.8
>>> WebKit v5.0.3 (6533.19.4, r78685)   220             14.7
>>>
>>> What is speeding this up is the use of JavaScript Typed Arrays:
>>>
>>>  http://www.khronos.org/registry/typedarray/specs/latest/
>>>
>>> This capability is associated with browsers that have implemented WebGL but
>>> none of the JavaScript Energy2D code is actually running on the GPU. The
>>> speedup is because of optimizations the JavaScript engines can make with
>>> math when working with fixed length arrays and one kind of number.
>>>
>>>
>>> -----------------------------------------------------------
>>> You are currently subscribed to public_webgl@khronos.org.
>>> To unsubscribe, send an email to majordomo@khronos.org with
>>> the following command in the body of your email:
>>> unsubscribe public_webgl
>>> -----------------------------------------------------------
>>>
>>>
>>>
>> -----------------------------------------------------------
>> You are currently subscribed to public_webgl@khronos.org.
>> To unsubscribe, send an email to majordomo@khronos.org with
>> the following command in the body of your email:
>> unsubscribe public_webgl
>> -----------------------------------------------------------
>>
>>
>
> -----------------------------------------------------------
> You are currently subscribed to public_webgl@khronos.org.
> To unsubscribe, send an email to majordomo@khronos.org with
> the following command in the body of your email:
> unsubscribe public_webgl
> -----------------------------------------------------------
>
>

-----------------------------------------------------------
You are currently subscribed to public_webgl@khronos.org.
To unsubscribe, send an email to majordomo@khronos.org with
the following command in the body of your email:
unsubscribe public_webgl
-----------------------------------------------------------