Hi,

   There are several problem in your test program:
   
 (1) stereo surface did not request
 //        canvas = new Canvas3D(config);
        canvas = new Canvas3D(SimpleUniverse.getPreferredConfiguration());
  The first line is comment out.
  
 (2)  gc.setBufferOverride(boolean bufferOverride) 
      did not set to true.
      So only one surface is display.
 (3) Should NOT invoke swap() twice, only once.
 (4) The order is wrong:
  
        gc.setModelTransform(cmt);
        gc.clear();
        gc.setStereoMode(GraphicsContext3D.STEREO_LEFT);
        gc.draw(new ColorCube(0.2));
        canvas.swap();
        gc.clear();
        gc.setStereoMode(GraphicsContext3D.STEREO_RIGHT);
        gc.setModelTransform(cmtemp);
        gc.draw(new ColorCube(0.35));
        canvas.swap();

In the first pass to render STEREO_LEFT, the surface
is clear BEFORE setting to STEREO_LEFT. same for another pass.
Correct order is:
          gc.setStereoMode(GraphicsContext3D.STEREO_LEFT);
          gc.clear();
          gc.setModelTransform(cmt);
          gc.draw(new ColorCube(0.2));
          gc.setStereoMode(GraphicsContext3D.STEREO_RIGHT);
          gc.clear()
          gc.setModelTransform(cmtemp);
          gc.draw(new ColorCube(0.2));
          canvas.swap();

 (5) No need to set the following every frame,
     view.setMinimumFrameCycleTime(0)       
 
Please refer to the attach example to see how to correctly use
PureImmediate mode stereo.

Thanks.

- Kelvin
---------------
Java 3D Team
Sun Microsystems Inc.
 
>X-Unix-From: [EMAIL PROTECTED]  Tue Feb 19 16:43:15 2002
>Date: Wed, 20 Feb 2002 08:43:04 +0800 (CST)
>From: Guang Bin Liu <[EMAIL PROTECTED]>
>Subject: Re: [JAVA3D] How to render to a fixed eye again
>To: Kelvin Chung <[EMAIL PROTECTED]>
>Cc: [EMAIL PROTECTED]
>MIME-version: 1.0
>
>I am using OpenGL version.  Yes, I did set the OpenGL
>setting-> Vertical Sync to on.  In addition, I set the
>card driver to be 'enable stereo' and tried the
>resolution 640X480. They all did not fix the problem.
>Also, if I have only one swap, I could view only one
>image which was rendered to both eyes. 
>
>I am wondering whether you can test my demo to see
>whether you also see the same result as I saw:  The
>image rendered to each eye is switching to the other
>eye sometimes.  If you do not see this problem, then
>obviously there is some fault on my machine.  If you
>also see the problem, then it might be due to the bug
>in J3D (am I right?).  
>
> --- Kelvin Chung <[EMAIL PROTECTED]> 寫道:> Hi,
>> 
>>   Did you set the driver option
>>   Display Properties->GeForce2->Additional
>> Properties
>>   ->OpenGL Setting->Vertical sync
>>   
>>   to On ? (by default it is Off).
>> 
>>   Also, there is no need to have 2 swap(), one
>>   is good enough at the end for both left and right
>> eye.
>> 
>> Thanks.
>>   
>> - Kelvin
>> ----------------
>> Java 3D Team
>> Sun Microsystems Inc.  
>>   
>> >X-Unix-From: [EMAIL PROTECTED]  Mon Feb 18
>> 23:09:53 2002
>> >Date: Tue, 19 Feb 2002 15:09:37 +0800
>> >From: Guang Bin Liu <[EMAIL PROTECTED]>
>> >Subject: [JAVA3D] How to render to a fixed eye
>> again 
>
>> >I am sorry for asking the same question again as I
>> >have not got a solution yet.  Solving this problem
>> is cruicial for my experiment!
>> >
>> >The attached is a simple demo showing my problems.
>> >I am rendering two ColorCubes.  The smaller one to
>> the left eye and the bigger one to the right eye.
>> > When this demo runs, by defination the images
>> should be rendered to the allocated eye
>consistently.
>> >However, intermittently each eye's allocated images
>> is switched to the other one (each eye can see the
>> other eye's image some times), which is not what I
>want. Can any one give me a suggestion how I can keep
>> each eye viewing its allocated image only?
>> > I changed the refresh rate of the display
>settings.
>>  I found that the higher is the rate, the quicker is
>> the image switching between eyes.  The 60Hz give a
>> lowest switching.  I assume that an even lower rate
>> (<60Hz) might fix the problem.  However, my Geforce
>card's lowest rate is 60Hz.  If this is the nature of
>the Immediate Mode of J3D, then Immediate mode is
>> >absolutely useless as it can't render an image to
>> an eye consistently.  I sincerely appreciate it if
>> some one can offer me a clue about how to solve this
>> >problem. 
>
>
> 
>
>=====
>Guang Bin Liu
>VTHRC
>University of Queensland
>Australia
>Phone:  61 7 3365 4072
>Fax: 61 7 3800 5268
>
>_________________________________________________________
>Do You Yahoo!?
>登記免費的 @yahoo.com 中文電子郵件 @ http://chinese.mail.yahoo.com
>Get your free @yahoo.com address at http://chinese.mail.yahoo.com
/*
 *
 *    "@(#)PureImmediateStereo.java 1.2 01/12/05"
 *
 * Copyright (c) 1996-1998 Sun Microsystems, Inc. All Rights Reserved.
 *
 * Sun grants you ("Licensee") a non-exclusive, royalty free, license to use,
 * modify and redistribute this software in source and binary code form,
 * provided that i) this copyright notice and license appear on all copies of
 * the software; and ii) Licensee does not utilize the software in a manner
 * which is disparaging to Sun.
 *
 * This software is provided "AS IS," without a warranty of any kind. ALL
 * EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES, INCLUDING ANY
 * IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR
 * NON-INFRINGEMENT, ARE HEREBY EXCLUDED. SUN AND ITS LICENSORS SHALL NOT BE
 * LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING
 * OR DISTRIBUTING THE SOFTWARE OR ITS DERIVATIVES. IN NO EVENT WILL SUN OR ITS
 * LICENSORS BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT,
 * INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER
 * CAUSED AND REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF
 * OR INABILITY TO USE SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGES.
 *
 * This software is not designed or intended for use in on-line control of
 * aircraft, air traffic, aircraft navigation or aircraft communications; or in
 * the design, construction, operation or maintenance of any nuclear
 * facility. Licensee represents and warrants that it will not use or
 * redistribute the Software for such purposes.
 */


import java.applet.Applet;
import java.awt.*;
import java.util.*;
import java.awt.event.*;
import com.sun.j3d.utils.applet.MainFrame;
import com.sun.j3d.utils.universe.*;
import com.sun.j3d.utils.geometry.*;
import javax.media.j3d.*;
import javax.vecmath.*;

/**
 * Pure immediate mode stereo example program for stereo. In pure
 * immediate mode, the renderer must be stopped on the Canvas being
 * rendered into. In our example, this is done immediately after the
 * canvas is created. A separate thread is started up to do the
 * immediate mode rendering.
 */
public class PureImmediateStereo extends Applet implements Runnable {

    // Set this to true when the graphics card use shared z buffer
    // in stereo mode.
    public static String defaultSharedStereoZbuffer = Boolean.TRUE.toString();

    private boolean sharedStereoZbuffer;
    private boolean stereoSupport;
    private Canvas3D canvas;
    private GraphicsContext3D gc;
    private Shape3D leftConeBody, rightConeBody;
    private Shape3D leftConeCap, rightConeCap;
    private Transform3D cmt = new Transform3D();
    private Vector3f leftTrans, rightTrans;

    // One rotation (2*PI radians) every 6 seconds
    private Alpha rotAlpha = new Alpha(-1, 6000);
    private SimpleUniverse u = null;
    private double angle;

    // Compute data which is common for both
    // left and right eye
    void computeSharedData() {
        // Compute angle of rotation based on alpha value
        angle = rotAlpha.value() * 2.0*Math.PI;
        cmt.rotY(angle);
    }

    // Render the geometry in right eye
    void renderLeft() {
        cmt.setTranslation(leftTrans);
        gc.setModelTransform(cmt);

        if (sharedStereoZbuffer) {
            // Graphics card shared same z buffer in stereo mode,
            // in this case we have to explicitly clearing both
            // frame buffers.
            gc.clear();
        }
        gc.draw(leftConeBody);
        gc.draw(leftConeCap);
    }

    // Render the geometry for right eye
     void renderRight() {
        cmt.setTranslation(rightTrans);
        gc.setModelTransform(cmt);

        if (sharedStereoZbuffer) {
            // Graphics card shared same z buffer in stereo mode,
            // in this case we have to explicitly clearing both
            // frame buffers.
            gc.clear();
        }
        gc.draw(rightConeBody);
        gc.draw(rightConeCap);
    }

    //
    // Run method for our immediate mode rendering thread.
    //
    public void run() {
        // Set up Graphics context
        gc = canvas.getGraphicsContext3D();

        // We always need to set this for PureImmediate
        // stereo mode
        gc.setBufferOverride(true);

        Color3f lightColor = new Color3f(1, 1, 1);
        Vector3f lightDir = new Vector3f(0, 0, -1);
        DirectionalLight light = new DirectionalLight(lightColor,
                                                      lightDir);

        gc.addLight(light);

        Appearance redApp = new Appearance();
        Appearance greenApp = new Appearance();
        Color3f ambientColor = new Color3f(0, 0, 0);
        Color3f emissiveColor = new Color3f(0, 0, 0);
        Color3f diffuseColor =  new Color3f(1, 0, 0);
        Color3f specularColor =  new Color3f(1, 1, 1);
        redApp.setMaterial(new Material(ambientColor, emissiveColor,
                                        diffuseColor, specularColor, 5));
        diffuseColor =  new Color3f(0, 1, 0);

        greenApp.setMaterial(new Material(ambientColor, emissiveColor,
                                          diffuseColor, specularColor, 5));

        // Set up geometry
        Cone leftCone = new Cone(0.4f, 0.6f,
                                 Primitive.GENERATE_NORMALS, redApp);
        Cone rightCone = new Cone(0.4f, 0.6f,
                                  Primitive.GENERATE_NORMALS, greenApp);
        leftConeBody  = leftCone.getShape(Cone.BODY);
        leftConeCap   = leftCone.getShape(Cone.CAP);

        rightConeBody = rightCone.getShape(Cone.BODY);
        rightConeCap  = rightCone.getShape(Cone.CAP);
        leftTrans = new Vector3f(-0.6f, 0, 0);
        rightTrans = new Vector3f(0.6f, 0, 0);


        while (true) {
            // compute data which is can be used
            // for both left and right eye
            computeSharedData();

            if (stereoSupport) {
                if (!sharedStereoZbuffer) {
                    gc.setStereoMode(GraphicsContext3D.STEREO_BOTH);
                    // This clear both left and right buffers, we
                    // must set STEREO_BOTH before it. Otherwise
                    // it only clear LEFT or RIGHT buffer unless
                    // this is invoke twice for each buffer.
                    gc.clear();
                }

                gc.setStereoMode(GraphicsContext3D.STEREO_LEFT);
                renderLeft();

                gc.setStereoMode(GraphicsContext3D.STEREO_RIGHT);
                renderRight();
            } else {
                gc.clear();
                renderLeft();
            }

            // This swap both left and right buffers so
            // there is no need to set STEREO_BOTH before it
            canvas.swap();

            // Be polite to other threads !
            Thread.yield();
        }
    }


    public PureImmediateStereo() {
    }

    //
    // init: create the canvas, stop the renderer,
    // create the universe, and start the drawing thread.
    //
    public void init() {
        setLayout(new BorderLayout());

        // Preferred to use Stereo
        GraphicsConfigTemplate3D gct = new GraphicsConfigTemplate3D();
        gct.setStereo(GraphicsConfigTemplate3D.PREFERRED);

        GraphicsConfiguration config =
            
GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice().getBestConfiguration(gct);

        canvas = new Canvas3D(config);
        Map map = canvas.queryProperties();

        stereoSupport = canvas.getStereoAvailable();

        if (stereoSupport) {
            System.out.println("This machine support stereo, you should see a red cone 
on the left and green cone on the right.");
            // User can overide the above default behavior using
            // java3d property.
            String str = System.getProperty("j3d.sharedstereozbuffer",
                                            defaultSharedStereoZbuffer);
            sharedStereoZbuffer = (new Boolean(str)).booleanValue();
        } else {
            System.out.println("Stereo is not support, you should only see the left 
red cone.");
        }

        if (!canvas.getDoubleBufferAvailable()) {
            System.out.println("Double buffer is not support !");
        }

        // we must stop the Renderer in PureImmediate mode
        canvas.stopRenderer();
        add("Center", canvas);

        // Create the universe and viewing branch
        u = new SimpleUniverse(canvas);

        // This will move the ViewPlatform back a bit so the
        // objects in the scene can be viewed.
        u.getViewingPlatform().setNominalViewingTransform();

        // Start a new thread that will continuously render
        (new Thread(this)).start();
    }

    // Cleanup all Java3D threads and memory when this applet exit
    public void destroy() {
        u.removeAllLocales();
    }

    //
    // The following allows PureImmediateStereo to be run as an application
    // as well as an applet
    //
    public static void main(String[] args) {
        new MainFrame(new PureImmediateStereo(), 512, 256);
    }
}

Reply via email to