Stereoscopic Vision in JavaScript How to Create A JavaScript Web Page Screen Saver | 2 | WebReference

Stereoscopic Vision in JavaScript How to Create A JavaScript Web Page Screen Saver | 2

To page 1current page
[previous]

Stereoscopic Vision in JavaScript

Readers familiar with 3D rendering may wonder why I have not chosen a painter's algorithm here (where objects in the distance are painted first and then nearer ones painted over the farther ones). The problem with using the painter's algorithm is that the stereoscopic rendering is quite sensitive to being re-painted. A pixel in a stereoscopic image is not an independent entity like the ones in a flat image. Stereoscopic pixels are matched with other pixels to create the 3D effect; it's a kind of pixel entanglement. If a stereoscopic pixel is then changed, any entanglement it might have had is destroyed and the 3D effect is lost.

 

// choose a suitable base depth factor.

var dx = 6;

var s = new Array();

for ( i = 0; i < nHeight; i++ )

{

   aLine = new Array();

   for ( j = 0; j < nWidth; j++ )

   {

      aLine.push('.');

   }

First, a suitable base depth factor must be defined. If matching pixels are too close together, the 3D effect will be difficult to see. Too far apart and the eyes would need to diverge to find matching patterns and this is a skill that very few people have. In the example code I have chosen a base depth factor of 6.

 

Each scan line is initialized to contain a special character so it's easy to tell whether a pixel has been painted in or not.

 

   for ( var iPass = 0; iPass < 3; iPass++ )

   {

      var c1, c2;

      var bMatch = true;

      // matching scan

      while ( bMatch )

      {

         bMatch = false;

         for ( j1 = 0, j2 = dx+iPass; j2 < nWidth; j1++,j2++ )

         {            

            if ( iPass == aScene[i][j1] )

            {

               c1 = aLine[j1];

               c2 = aLine[j2];

              

               if ( (c1 == '.') && (c2 != '.') ) { aLine[j1] = c2; bMatch = true; }

               if ( (c1 != '.') && (c2 == '.') ) { aLine[j2] = c1; bMatch = true; }

            }

         }

      }

 

For each scan line, a separate pass is run for each depth factor, iterating from nearest to furthest. Matching pairs of pixels are related according to a simple formula; for a given pixel coordinate j1, a matching pixel can be found at j1 + dx + df, where dx is the base depth factor (set to 8 above) and df is the depth factor taken from the scene.

 

Each pass is divided into three scans; a matching scan, a matching finishing scan and a finishing scan. The matching scan is run so that where two matching pixels are found where one has already been assigned by an earlier pass, the unassigned pixel is given the value of the other. The matching finishing scan (below) is run to fill in all the gaps with matching pixels that were missed by the matching scan.

 

      // matching finishing scan

      for ( j1 = 0, j2 = dx+iPass; j2 < nWidth; j1++,j2++ )

      {          

         if ( iPass == aScene[i][j1] )

         {

            c1 = aLine[j1];

            c2 = aLine[j2];

            if ( (c1 == '.') && (c2 == '.') )

            {

               c1 = c2 = randomElement();

               aLine[j1] = c1;

               aLine[j2] = c2;    

            }

            if ( (c1 != '.') && (c2 == '.') ) aLine[j2] = c1;

         }

      }       

   }

 

A final finishing scan fills in any gaps that could not be filled with matching pixels… 

 

   // finishing scan

   for ( j1 = 0; j1 < nWidth; j1++ )

   {

      if ( aLine[j1] == '.' ) aLine[j1] = randomElement(bUseColor);  

   }

 

Finally, at the end of each line a line break is added and finally the whole image can be displayed…

 

   // convert the scanline to HTML

   s.push(aLine.join('') + '<br>');

}

 

// after all scanlines have been rendered, display it on the page.

document.getElementById('theDiv').innerHTML = s.join('');

 

Conclusion

In this article I've shown how to generate stereoscopic images dynamically on a web page using nothing but JavaScript and simple HTML text elements. The algorithm described above takes advantage of the sophisticated visual recognition circuitry in the brain to generate images. When viewed in a particular way this displays objects in three dimensions. The algorithm works by placing matching characters at various distances apart to control the apparent depth seen by the viewer.

 

Guyon Roche is a freelance web developer in London, Great Britain. He specializes in Windows platforms with an interest in bridging the gaps between different technologies, visit http://www.silver-daggers.co.uk for more details. He can be reached via e-mail at guyonroche@silver-daggers.co.uk.

To page 1current page
[previous]

Created: March 27, 2003
Revised: December 2, 2004

URL: http://webreference.com/programming/javascript/gr/column10/1