Can a LinePick be null yet return coords?

Blitz3D Forums/Blitz3D Programming/Can a LinePick be null yet return coords?

puki(Posted 2007) [#1]
CameraPick is handy as you can pick empty space with it - ie:

If MouseHit(1) And entity=0
cube=CreateCube()
PositionEntity cube,world_pos_x, 1,world_pos_z
EndIf

You can calculate the 3D world coordiates via use of CameraProject, ProjectedX() and ProjectedY().

However, this is great if you don't move the overhead camera - as soon as you do you lose position accuracy. You can zoom in and out and preserve accuaracy - but as soon as you scroll the camera, bang goes the accuracy.

CameraPick is great for picking an entity as it works with the perspective of the camera - so it is great at what it does.

So, LinePick is surely the saviour as it couldn't care less about the perspective when picking a world position. However, I don't want to pick anything - I want to pick a position in 3D space.

How can I achieve this with LinePick? CameraPick can pick null (I'm not sure if it was designed to pick null, but you can force it).


big10p(Posted 2007) [#2]
Eh? What's the point of picking 'a position in 3D space' if you already know the coords of that point.

I don't really understand what you're trying to do, TBH.


Ross C(Posted 2007) [#3]
CameraPick is designed to be used with the mouse in mind. Or for any other reason you'd need to choose the pick from a 2d location on the screen. Line pick is really for blind picking. When you want to find out if something is actually there.

For example, a platformer. You'd do a pick below the character to find out if he has something below his feet, but not yet touched the ground. Many uses :o)


big10p(Posted 2007) [#4]
oops - wrong thread


puki(Posted 2007) [#5]
The coords are skewed by perspective - ie you can move a mouse pointer overhead and place a cube - but it doesn't appear at the point of the mouse pointer:

 Graphics3D 800,600,16,2

Global entity
Global ent
Global world_pos_x#
Global world_pos_z#


ground=CreatePlane()
EntityColor ground,0,200,0


Global cube1=CreateCube()
ScaleEntity cube1,.5,.5,.5
PositionEntity cube1,-2,1,-2
EntityPickMode cube1,2

Global cube2=CreateCube()
ScaleEntity cube2,.5,.5,.5
PositionEntity cube2,2,1,-2
EntityPickMode cube2,2

Global cube3=CreateCube()
ScaleEntity cube3,.5,.5,.5
PositionEntity cube3,0,1,0
EntityPickMode cube3,2

Global cube4=CreateCube()
ScaleEntity cube4,.5,.5,.5
PositionEntity cube4,-2,1,2
EntityPickMode cube4,2

Global cube5=CreateCube()
ScaleEntity cube5,.5,.5,.5
PositionEntity cube5,2,1,2
EntityPickMode cube5,2


light=CreateLight()
PositionEntity light,100,100,-100
PointEntity light,cube1


Global cam=CreateCamera()
CameraViewport cam,10,90,500,500
CameraProjMode cam,1
CameraZoom cam,2.5
CameraRange cam,.01,1000

PositionEntity cam,0,10,0 
RotateEntity cam,90,0,0


Repeat

	Cls
	
	If MouseHit(1) And entity<>0 ; something had to have been picked

	End If
	
	If MouseDown(1) And entity=0 ; basically picking empty space
		cube=CreateSphere()
		ScaleEntity cube,.25,.25,.25
		PositionEntity cube,world_pos_x,1,world_pos_z
	EndIf 
		
	If entity
		EntityColor entity,255,0,0
	EndIf	
		

; overhead camera
If KeyDown(16) Then TurnEntity cam,0,0,1 ; rotate cam left
If KeyDown(18) Then TurnEntity cam,0,0,-1 ; rotate cam right
If KeyDown(12) Then MoveEntity cam,0,0,.1 ; zoom in
If KeyDown(13) Then MoveEntity cam,0,0,-.1 ; zoom out
If KeyDown(17) Then MoveEntity cam,0,.1,0 ; forward
If KeyDown(31) Then MoveEntity cam,0,-.1,0 ; back
If KeyDown(30) MoveEntity cam,-.1,0,0 ; strafe left
If KeyDown(32) MoveEntity cam,.1,0,0 ; strafe right


UpdateWorld()

RenderWorld()

Project2DTo3DOrtho( MouseX() , MouseY() )

Text 10,10,"Entity Highlighted: "+entity
	
Flip

Until KeyDown(1)=1
ClearWorld()
End



Function Project2DTo3DOrtho(mx,my)

	;Check the mouse is in the 3d window 
	If mx>=10 And mx<=509 And my=>90 And my<=589
	
		;Get mouse position in relation to the 3d viewport
		vx=mx-10; 100
		vy=my-90; 100
		
		; draw the rectangle here as it relies on the mx and my coords
		Rect mx,my-3,1,7	
		Rect mx-3,my,7,1	
		
		;Get the 2d position of the origin
		CameraProject cam,0,0,0
		xx#=ProjectedX()
		yy#=ProjectedY()

				
		;Get the 2d position of 1,1,1
		CameraProject cam,1,1,1
		xx2#=ProjectedX()
		yy2#=ProjectedY()


		;Take one from the other to find the distance
		dx#=xx2-xx
		dy#=yy2-yy

		;World position is :
		world_pos_x#=(vx-xx)/dx
		world_pos_z#=(vy-yy)/dy
		
			
		ent=CameraPick(cam,vx,vy)
		If ent<>entity
		If entity Then EntityColor entity,255,255,255
			entity=ent
		EndIf
	
		Text 10,50,"Cursor is at World position X : "+world_pos_x
		Text 10,60,"                            Z : "+world_pos_z

	EndIf
End Function 



puki(Posted 2007) [#6]
Click left mouse to insert a sphere.

This is fine when zooming in and out. It goes plop if you move the camera.

So I thought a sneaky LinePick would be great.


Stevie G(Posted 2007) [#7]
Changing this line from ...

CameraProject cam, 0,0,0


to

CameraProject cam,0,1,0


Fixes the problem. Your scaling is borked otherwise as you are positioning the sphere at y=1.

This kind of thing is what camerapick is designed to do - why aren't you using it?

Stevie


puki(Posted 2007) [#8]
Ooooh.

I was pretty close though.

I have been out all day and was faffing about with this thing this morning - changing between Modes 1 and 2 - trying different things.

The reason why in this thread (and the other one) I seem caught in between two systems is because I am. I'm sort of trying to blend two methods into one.

The bog-standard CameraPick is ideal for selecting an entity - I like it - nothing wrong with it for my needs.

However, I also need to pick thin air - I'm not checking for a collision or checking for a mesh/surface/entity.

I'll admit, it is all somewhat advanced - considering, I am not showing exactly what I am doing - I've sort of dumbed it down a bit to make it more clear.

I have continue to reintegrate what I want to do into how Blitz3D will allow me to do what I want.

Still, I feel I will reach the promised land.


big10p(Posted 2007) [#9]
Pick thin air?


Stevie G(Posted 2007) [#10]
Why do you need to pick thin air? Why not just have a pickable plane?

ThinAir = createplane()
Entitypickmode ThinAir, 2
entityalpha ThinAir, 0

If pickedentity = ThinAir
etc......

Can you explain what your doing?


puki(Posted 2007) [#11]
Yeh, I said it was advanced.

I already achieved what I want with banks of surfaces that do the job quite nicely. However, I pulled them out because it worked and I knew I wanted to do it differently.

The fact that I can already pick thin air is what drives me forward - dominance dripping all over the place - it's just great - picking thin air - awesome - it's total picking dominance - it is some kind of picking super-string - an event horizon of such Largeness that only the dominant will complete the journey.

Plus, this is just the first part of what I am doing - this is a building block.


big10p(Posted 2007) [#12]
OK, I think I'm done here...


Stevie G(Posted 2007) [#13]
Agreed, we'll leave you to do it the hard way.