• Dear Cerberus X User!

    As we prepare to transition the forum ownership from Mike to Phil (TripleHead GmbH), we need your explicit consent to transfer your user data in accordance with our amended Terms and Rules in order to be compliant with data protection laws.

    Important: If you accept the amended Terms and Rules, you agree to the transfer of your user data to the future forum owner!

    Please read the new Terms and Rules below, check the box to agree, and click "Accept" to continue enjoying your Cerberus X Forum experience. The deadline for consent is April 5, 2024.

    Do not accept the amended Terms and Rules if you do not wish your personal data to be transferred to the future forum owner!

    Accepting ensures:

    - Continued access to your account with a short break for the actual transfer.

    - Retention of your data under the same terms.

    Without consent:

    - You don't have further access to your forum user account.

    - Your account and personal data will be deleted after April 5, 2024.

    - Public posts remain, but usernames indicating real identity will be anonymized. If you disagree with a fictitious name you have the option to contact us so we can find a name that is acceptable to you.

    We hope to keep you in our community and see you on the forum soon!

    All the best

    Your Cerberus X Team

miniB3D - request help with Camerapick

Ryan2003

New member
Tutorial Author
Joined
Jul 12, 2020
Messages
28
I am trying to use the camerapick function of miniB3D to pick an on screen entity.
When the camera is poistioned so that I have the view that I want, the pick does not work.
By changinging the camera position, I can get the pick to work, but now it does not
have the view that I want.
How can I have the view that I want and have picking work?

cam.PositionEntity 16, 8, 0 ' this is the view I want,but pick does not work
'cam.PositionEntity 0, 0, 0 ' this one pick works, but not the desired view
Cerberus:
Import minib3d

Function Main()
    New Game
End

Class Game Extends App
    
    Field cam:TCamera
    
    Field light:TLight
    
    Field hexcell:TEntity = CreateCylinder(6)

    Field yTiles:Int = 4' Number of tiles on the y axis
    Field xTiles:Int = 4' Number of tiles on the x axis
    Field totalTiles:Int
    Field length:Float = 1.025    'Length of the hexagon so we can calculate the spacing between tiles

    Field A:Float
    Field B:Float
    Field C:Float
    
    Field coord:Float[]
    
    Method OnCreate()
    
        SetUpdateRate 30
        SetRender()

        totalTiles = yTiles * xTiles
        C = length
        A = Sin(30) * C
        B = Sin(60) * C
        coord = coord.Resize(totalTiles * 2)
        
        cam = CreateCamera()
        cam.CameraClsColor(0, 0, 80)
        cam.PositionEntity 16, 8, 0    ' this is the view I want,but pick does not work
        'cam.PositionEntity 0, 0, 0    ' this one pick works, but not the desired view
        
        hexcell.PositionEntity(5, 0, 0)
        hexcell.ScaleEntity(1.0, 0.3, 1.0)
        cam.PointEntity(hexcell)
        
        light = CreateLight(1)
        light.PositionEntity(10, 0, 7)
        light.RotateEntity(90, 0, 0)
    
        'Wireframe(True)
    
        'Calculate tile positions
        Local k:Int = 0
        For Local i:= 1 To yTiles
            For Local j:= 1 To xTiles
        
                If (i Mod 2)  Then
                    'store the center pixel
                    coord[k] = j * (B * 2) + B
                    k = k + 1
                    coord[k] = C + i * (A + C) - 5
                    k = k + 1
                Else
            
                    'store the center pixel
                    coord[k] = j * (B * 2) + B + B
                    k = k + 1
                    coord[k] = C + i * (A + C) - 5
                    k = k + 1
                EndIf
            Next
        Next
        
        ' place the hexagons
        Local x:Float = 0
        Local z:Float = 0
        Local j:Int = 0
        For Local i:= 0 To totalTiles - 1
            Local tile:TEntity = CopyEntity(hexcell)
            tile.EntityPickMode(2)
            x = coord[j]
            j = j + 1
            z = coord[j]
            j = j + 1
            tile.PositionEntity(x, 0.0, z)
        Next
        
        hexcell.EntityAlpha(0)' hide the orginal hexagon
        
    End
    
    Method OnUpdate()
    
        If KeyHit(KEY_CLOSE) Or KeyHit(KEY_ESCAPE) Then Error ""
        
        
        If TouchDown(0)
            Local e:TEntity = cam.CameraPick(TouchX(), TouchY())
            If Not e Then Print "null pick" Else Print "hex picked"
        EndIf
        
        UpdateWorld()

    End
    
    Method OnRender()

        RenderWorld()   
        
    End

End
View I want:
1597186323942.png
But Picking does not work.
 
I just tried camerapick here as well and I have a similar problem. Using the code I posted here, I do a CameraPick on all die on screen.

The only one that gets picked is the one at 0,0,0. The others, won't. I looked at the 'pick' example on MiniB3D folder, and if you move the sphere from 0,0,0 (there is even a PositionEntity command commented out in the sample) it also stops working.

I can confirm that if I place camera at 0,0,0 and move my dice, then picking occurs correctly :/
 
Just found something out: changing the camera viewport or even using scaleentity on the camera can also mess camera picking, even if its @ 0,0,0 :(

And cameraviewport / camerazoom / scaleentity cam is needed to get everything into the correct aspect ratio on multiple resolutions :/
 
CameraProject breaks too :/

(I thought about doing the opposite of CameraPick, projecting every object to screen coordinates and comparing with the mouse position... but no luck there either)
 
I thought the problem was at GluUnProject function, the one responsible from projecting a 2D point in 3D space - so I found a implementation of it here and tried to port it to MiniB3D.

And, of course, it didn't work :p

This is way beyond me :(
I may have to go to #$%& Unity for this :(
 
I think the problem is in CameraPick itself. This is the code:
Code:
    Function CameraPick:TEntity(cam:TCamera,vx:Float,vy:Float)
        Local vec:Vector
        Local dvec:Vector
        
        vy=cam.viewport[3]-vy

        vec = cam.GluUnProject(vx,vy,0.0,cam)
        
        dvec = cam.GluUnProject(vx,vy,1.0,cam)

        Return Pick(vec.x,vec.y,-vec.z,dvec.x,dvec.y,-dvec.z,0.0)   
    End Function

As you can see, it doesn't take into account *at all* if the viewport isn't at screen 0,0 - it just 'flips' y coord (with vy=cam.viewport[3]-vy)
 
Why don't you try Vortex?
I'll have to rewrite, re-export models into different format (they're in B3D for now)... having to re-do everything I might as well learn a bit of Unity with it.

But, back in MiniB3D... I almost got it.

If your viewport keeps the width intact, just scaling the height, then changing to this will fix it:

Code:
vy=cam.viewport[3]-vy + cam.viewport[1]*2

(Which kind of makes sense? I'm adding the borders to the calculation)
But if the horizontal scaling is changed, I got no clue how to fix it yet.
 
Hmmm... Don't know what I did, but apparently now with this code its working on all aspect ratios I tested:

Code:
    Function CameraPick:TEntity(cam:TCamera,vx:Float,vy:Float)
        Local vec:Vector
        Local dvec:Vector
       
        vy=cam.viewport[3]-vy + cam.viewport[1]*2

        vec = cam.GluUnProject(vx,vy,0.0,cam)
       
        dvec = cam.GluUnProject(vx,vy,1.0,cam)

        Return Pick(vec.x,vec.y,-vec.z,dvec.x,dvec.y,-dvec.z,0.0)  
    End Function

(It still doesn't work if camera is not on 0,0,0 though)
 
Last edited:
Back
Top Bottom