Algorithm of vegetation

Hello, I try to insert the 3d grass around the player and removed when the player is too far.
But my program is not optimized…

Are you there a more optimized way to do this ? Is there already a specialized API you ?
after I want to dynamically insert 3d grass, 3d tree…etc and remove when player is too far.

	def InitVegetations(self):
		VisibilityVegetation=100
		VegetationMatrice = [[0] * VisibilityVegetation for _ in range(VisibilityVegetation)]
		while 1:
				for i in range(0, VisibilityVegetation):
					for j in range(0, VisibilityVegetation):
						if VegetationMatrice[i][j]==0:
							
							m = loader.loadModel("resources/grass/grass.obj")
							m.setScale(.2)
							pos1=player.getPos()
							
							min, max = m.getTightBounds()
							size = max-min

							x=pos1[0]+size[0]*i
							y=pos1[1]+size[i]*j
							
							m.setHpr(0,90,0)
							m.reparentTo(render)
							m.setPos(x, y, 0)
							height=self.GetHeight(m)
							pos2=m.getPos()
							m.setPos(pos2[0], pos2[1], height)
							VegetationMatrice[i][j]=m

The most efficient method to render vegetation is probably using instancing combined with some LOD algorithm.
As for that, I also have some code lying arround, but its outdated and won’t work anymore, so it would be quite some work to make it running again.

My question is how optimize the load model, because in my code i load model in loop:

for i in range(0, 10):
   m = loader.loadModel("resources/grass/grass.obj")
   m.reparentTo(render)

I would not charge the same grass every iteration for example:

m = loader.loadModel("resources/grass/grass.obj")
for i in range(0, 10):
   m.reparentTo(render)

But with this code i load 1 object not 10.

Have a look at instancing: https://www.panda3d.org/manual/index.php/Instancing

This is not as efficient as instancing on the GPU, but should already improve the performace.

Can i instanciate on the gpu with panda3d ?

Yes, you can do so by calling model.set_instance_count(num_instances). However, you will have to write a shader then which positions your objects (since they otherwise will be all at the same position).

In your shader you can access the current instance id with gl_InstanceID. You would have to pass some sort of array (e.g. a PTALVecBase3f storing positions of the instances) as shader input, and use that in the shader then.