Results 1 to 10 of 42

Thread: pascal and learning 3d

Hybrid View

Previous Post Previous Post   Next Post Next Post
  1. #1
    another headache.. object picking!
    I've read about different methods and looks like ray casting is a way to go in my case. But I'm having problems with gluUnProject , not sure what to feed to it.
    Samples I've seen are useing something like that to obtain values for it:
    glGetIntegerv(GL_VIEWPORT,@viewport);
    glGetDoublev(GL_PROJECTION_MATRIX,@projectionMatri x);
    glGetDoublev(GL_MODELVIEW_MATRIX,@modelMatrix);

    those get me identity matrices for projection and model. I guess it's because i'm doing all 'projection' computations in shaders only. I think I know how to fill projection and viewport matrices but every model has it's own model matrix. Should I just use any's model matrix for gluUnProject ? (tried and it didn't work ;p )

  2. #2
    Do you really need ray casting? If you only want to select objects at e.g. a given cursor position, just go for color selection. Especially with shaders that's pretty simple and fast. I'm using this technique for selection too (see here). It's easy to implement and extremly fast.

    It works like this :
    - Render your scene to the backbuffer (so it's not visible), but only with colors and basic geometry. E.g. one building red, another yellow
    - Limit the viewport to the cursor position (for performance)
    - Read the pixel under the cursor (glReadPixels)
    - Compare read colors with your color-to-object-table

    It's very fast and can be implemented in just a few minuts. Especially when using only shaders you just need a new shader the outputs selection colors to the fragment buffer.

  3. #3
    If you want to use ray casting, you can check nxPascal demos. Model and Picking demos both use that math. Doing it mathematically has the advantage of knowing exactly which model face the ray hits, and what is the normal vector at that point.

    There is also GL_SELECT based function on the works, but it's not working in my tests yet. I used that style many years ago, so at least there's some code left.

  4. #4
    @Sascha: I'd use color picking if i could but I'm not texturing voxels and I don't plan to. To do color picking in this scenario I guess I'd have to render geometry with unique colours and then change them to proper values from some reference texture?

    @User137: yeah, I'm using your engine as a reference from time to time but picking there is done in a way I've described in my previous post. Where do I get model matrix from if glGetDoublev(GL_MODELVIEW_MATRIX) doesn't seem to do it's job?
    Internet says GL_SELECT is obsolete and shouldn't be used anymore

    edit: another problem with color picking is that I have tons of cubes on the scene so
    lookup would be costly unless I encode cube coords into color..
    Last edited by laggyluk; 09-01-2013 at 06:37 PM.

  5. #5
    The old OpenGL-Selection (GL_SELECT) shouldn't be used anymore and as far as I know it isn't available in newer OpenGL-versions anyway. And even if it would, hardware vendors decided to drop hardware support for it some time ago, so rendering in selection mode is done in software and therefore often extremly slow.

    As for color selection via shaders : No, you don't need textures at all. Just assing a color to each voxel when creating it (you've got 24 Bits to encode your color, that should be sufficent), render with that color, pick it from the backbuffer and compare. If you render a lot of cubes you should have some kind of visibility check (e.g. an octree), so you can use that to speed up this process.

  6. #6
    what I ment is that voxel/cubes won't be covered with textures, vertex color is used to represent diferrent block types. With color picking I'd use vertex color to identify the cube and lose info about how this block should look like. Maybe if I could have 2 atributes passed to shader, one with 'block color' and another with 'id color' and then render to two different textures? one for picking and other for showing on screen.

    edit: i did it geometry picking that is. used some unprojecting functions from glscene
    Last edited by laggyluk; 10-01-2013 at 06:23 PM.

  7. #7
    PGD Staff / News Reporter phibermon's Avatar
    Join Date
    Sep 2009
    Location
    England
    Posts
    524
    Picking should absolutely not be used for a voxel engine (Please forgive me Sascha, I've got an awesome amount of respect for you) you're hitting the limits of the hardware (or at least eventually will) the last thing you want is to render an additional pass of the scene for only a single task. Regardless if you remove textures or not, that's a hell of a lot of geometry to render twice.

    You could alleviate much of the performance hit by using MRTs (Multiple render targets) and actually render the picking data to a back-buffer, whilst doing the normal rasterization on your main buffer (or a further back-buffer if you're aiming for a deferred renderer). If you were looking to do minecraft style rendering, IE Ambient Occlusion, there may be additional data you can store in this back-buffer that would make this method more attractive.

    However you're just not going to beat raycasting when you've got a lot geometry, especially as you're storing your data in an oct-tree, there are oct-tree optimized raycast algorithms that you really want to use and not just for ray-casting the view direction to select stuff etc. if you want to do oct-tree style ambient occlusion you'll need rays, if you want to do any form of path finding in a voxel terrain, you'll need rays.

    The math isn't too complex, Jink (my soon to be released game engine) has a full range of ray-casting functions and algorithms, optimised for oct-trees, kd-trees etc

    Ray-casting, is a requirement for rendering 3D graphics onto a 2D display (I didn't say Ray-tracing before anybody jumps on me). it's all happening in the API even if you don't use it yourself, projecting the 3D vertices into screen-space coordinates.

    You're just casting in the opposite direction to do picking, you cast a line from the position the mouse intersects the camera clipping plane, outwards, the combination of view and projection matricies associated with the camera determining the two intersecting planes the ray is defined by (or a vector and position, whatever is most useful for your spatial partitioning scheme)

    Once that is done you have a vector in 3D space, for raycasting, think of it as an infinite line.

    Then you're either finding the closest 3D object to that line, or doing line/BBox followed by line/triangle intersection tests to determine the 'hit' object.

    Obviously oct-tree optimizations come into play at this stage, testing the intersection of this line against the bounding boxes of your tree nodes, you then perform this test, traversing down towards the leaves like you would when you're testing your camera frustum against it, only line/bbox is a lot faster than Frustum/BBox intersection testing.

    You further optimize the traversal because you should have stored your visible nodes during the frustum test, so you only need to test against that set of nodes.
    When the moon hits your eye like a big pizza pie - that's an extinction level impact event.

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •