Re: Convert NSOpenGLView pixel coordinates to OpenGL world coordinates

  • I think that I was unclear about my intentions. I have
    a two dimensional grid of 3D objects (each object is
    at the same Z coordinate). Sorry if I was misleading.
    Picking actually turned out to be the solution. I
    found the following code to work. It's not optimized,
    but does the job of returning the selected object.

    - (void)clickedPoint:(NSPoint)p
    {
    NSRect  viewBounds = [myView bounds];
    Scene  *myScene = [myView clientScene];
    NSArray  *sceneObjects = [myScene sceneObjects];
    GLsizei  bufferSize = (GLsizei)[sceneObjects count];
    GLint          viewport[4];
    GLuint        nameBuffer[bufferSize];


    glSelectBuffer( bufferSize, nameBuffer );
    glRenderMode( GL_SELECT );

    glMatrixMode( GL_PROJECTION );

    glPushMatrix();
    glLoadIdentity();

    glGetIntegerv( GL_VIEWPORT, viewport );
    gluPickMatrix( (GLdouble)p.x, (GLdouble)p.y, 3.0,
    3.0, viewport );
    gluPerspective( 70.0,
    viewBounds.size.width/viewBounds.size.height, 0.2,
    100.0 );

    glMatrixMode( GL_MODELVIEW );
    glInitNames();

    [myScene render];  // Draw all objects.

            // NOTE: each object should have a glPushName(
    (GLuint)name or ID ); before it gets rendered and a
    GLPopName(); after it gets rendered.


    glMatrixMode( GL_PROJECTION );
    gluPerspective( 70.0,
    viewBounds.size.width/viewBounds.size.height, 0.2,
    100.0 );
    glPopMatrix();


    GLint  numberOfHits = glRenderMode( GL_RENDER );
    GLuint *ptr = (GLuint *)nameBuffer;
    int  i;

    for ( i = 0; i < numberOfHits; i++ )
    {
      NSLog( @"%d", *(ptr + 3) );

      ptr += 4; // Go to next record.
    }
    }

    Thanks for all your help Dave.

    --- David Spooner <dave...> wrote:

    >
    > I hadn't put enough thought into my first response.
    > When your initial
    > post said you weren't concerned with the z-value, I
    > thought you were
    > using an orthographic projection.  Generally a point
    > on the screen is
    > the image of a line in world coordinates, so the
    > z-value supplied to
    > gluUnProject is significant and the arbitrarily
    > chosen zero won't do.
    > You will likely need to use your view-coordinate
    > point to construct a
    > line/ray in world coordinates and perform
    > intersection testing on your
    > geometry...
    >
    > You can use gluUnProject with two different z-values
    > (say 0 and 1) to
    > obtain two world coordinate points from which you
    > form your world-
    > coordinate line.  Regarding intersection testing, I
    > have found a
    > number of useful algorithms in "Geometric Tools for
    > Computer Graphics"
    > by Schneider and Eberly, and also in the usenet
    > comp.graphics.algorithms faq
    >
    > Another alternative is to use GL's selection mode,
    > which you can learn
    > about in the chapter 'Selection and Feedback' of the
    > Red book...
    >
    > dave
    >
    > On 7-Oct-07, at 2:25 PM, Ian was here wrote:
    >
    >>> From within the NSOpenGLView subclass...
    >>
    >>
    >>
    >> - (void)reshape
    >> {
    >> NSSize        viewSize = [self bounds].size;
    >>
    >> glViewport( 0.0, 0.0, viewSize.width,
    > viewSize.height
    >> );
    >>
    >> glMatrixMode( GL_PROJECTION );
    >> glLoadIdentity();
    >> gluPerspective( 70.0,
    > viewSize.width/viewSize.height,
    >> 0.2, 100.0 );
    >> }
    >>
    >
    >

          ____________________________________________________________________________________
    Fussy? Opinionated? Impossible to please? Perfect.  Join Yahoo!'s user panel and lay it on us. http://surveylink.yahoo.com/gmrs/yahoo_panel_invite.asp?a=7
previous month october 2007 next month
MTWTFSS
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        
Go to today