is the heading of directional light in negative direction?

i found the heading of camera in Panda is “left-positive”, i assume every object in Panda has the same coordinate system.
but when i tested directional light on geomipterrain, the heading of the light seemed to be ‘right-positive’.

explanation: i didn’t use setH on the node, i called setDirection on the light.
for example, setDirection((0.7,0,-0.7)) should light the left side of mountains on the terrain, but i saw right side of mountains lit instead.

having multiple coordinate systems in a program is bear-able, but it’s just not so neat.

Hmm, perhaps GeoMipTerrain generates wrong normals in your case? Posting a test case might help us diagnose the issue.

these are test code and required heightmap and screenshot of test result:


from panda3d.core import GeoMipTerrain,DirectionalLight
from direct.showbase import ShowBase

base=ShowBase.ShowBase()

terrain=GeoMipTerrain('')
terrain.setHeightfield('land0.png')
terrainNode=terrain.getRoot()
terrainNode.reparentTo(render)
terrain.setBlockSize(32)
terrain.setNearFar(20000,30000)
terrainNode.setScale((8,8,64))
terrainNode.setPos((-500,-500,0))
terrain.setAutoFlatten(0)
terrain.setBruteforce(1)
terrain.setMinLevel(0)
terrain.generate()
base.cam.setZ(1500)
base.cam.setP(-90)
base.camLens.setFov(70)
base.camLens.setNearFar(100,3000)
light=DirectionalLight('')
lightNode=render.attachNewNode(light)
render.setLight(lightNode)
light.setColor((1,1,1,1))
light.setDirection((0.7,0,-0.7))

run()




I think I had this same sensation when using setDirection on some directional light.
At the time I thought I were just too tired (and maybe I were :stuck_out_tongue:) and that I just had made some silly mistake (which probably is still true :laughing:)

now i have other objects in the scene , and the lights seem correct. so the geomipterrain has wrong normals. why would that happen? is there anything wrong in my test code ?

today i found something strange about the geomipterrain. before run() , the 1st vertex ( vertex 0 referred by primitive) in a block is the bottom left vertex. but after run(), the 1st vertex is the top right vertex. why are the vertex data rearranged ?

Ugh, I could have sworn I’d already replied to this thread twice now. Yes, it does seem that GeoMipTerrain generates normals that seem to be flipped in the Y direction. I’ll look into what could be done about this. As a workaround, you could create a DirectionLight with flipped Y direction and set that on the terrain with an override value.

I’m not sure why you’re seeing the vertex data get rearranged; I thought the generation was fairly deterministic.

i asked the problem of terrain normals again because i didn’t know whether it was just me or the problem did exist in Panda. now i know my code is not wrong.

about the “rearrange” problem, i got the impression from this:
when i tried to find out how the vertex data are arranged, i ran this:

hdl=terrainNode.getChild(0).node().modifyGeom(0).modifyPrimitive(0).modifyVertices().modifyHandle()
hdl.setData( hdl.getData()[6 * x : ] )

if x triangles at bottom left(or top right) corner are removed, that means the 1st vertex is at bottom left(or top right) corner.

when i ran the code before calling run(), bottom left corner of a block was affected, but when i ran the code after run(), top right corner of a block was affected.
i didn’t think that rearranging vertex data was necessary, so i felt strange - maybe there is a mechanism in Panda which does this?

just now i tried to reproduce the behavior in minimal test code, but it didn’t happen - only bottom left corner was affected in test code. there must be something in my full program that caused it, but i don’t know where it is.

anyway, as long as i run the particular code before run(), i am certain about how the vertex data are arranged in memory. no need to worry.

I committed a fix to the terrain normal bug. In 1.9.1, the fix may be activated by setting the “geomipterrain-incorrect-normals” variable to “false” in Config.prc. In 1.10 or the latest master, this variable will be set to “false” by default.