Hi,

I can't get to solve my problem and need help. 

I am simulating a bunch of particules (which are sphere). Each time I want 
to add a sphere, I call the function new_sphere which return me the 
vertex_list after it has been added to the batch (called b_sphere). I store 
each vertex list object in a list (sphere[ ] ) so I can access it later. 
When two particules touch themselves, I first delete the vertex_list from 
the batch them the object from the list :

sphere[update.todel[i]].delete()
sphere.pop(update.todel[i])

Then I add another bigger sphere to simulate the "fusion" of the two 
previous ones :

primitive.new_phere(sphere, b_sphere, int(update.new[j][0]), 2,
                                    update.new[j][1][0],
                                    update.new[j][1][1],
                                    update.new[j][1][2], (1.,0.3,0.2) )

But when I do that, sometimes it works, sometimes it creates artefacts. For 
example, one of the sphere will stop moving (instead of disappear) and be 
partially deleted, while only one quarter of the new sphere will appear and 
continue to move as expected.

Here is a larger view of my code :

def init():
        print("___ primitive initialization ___")
        # The Axis (z is reverse with OpenGL)
        axis_x = primitive.Box(b_axis, 1000,0.1,0.1, 
color=('c3f',(1.,0.,0.)*4))
        axis_y = primitive.Box(b_axis, 0.1,1000,0.1, 
color=('c3f',(0.,1.,0.)*4))
        axis_z = primitive.Box(b_axis, 0.1,0.1,-1000, 
color=('c3f',(0.,0.,1.)*4))

        global nb_sphere
        global sphere
        global b_sphere

        nb_sphere = 3

        random.seed(a=None) # initial random seed

        for i in range(nb_sphere):
            primitive.new_phere(sphere, b_sphere, d_min, 2,
                            random.gauss(0, sparsity),
                            random.gauss(0, sparsity),
                            random.gauss(0, sparsity))

@window.event
def on_draw():
    global b_sphere

    window.set2d()
    fps_display.draw()

    window.set3d()
    window.push(window.player.pos,window.player.rot)

    b_sphere.draw()
    b_axis.draw()

    glPopMatrix()


# called every frame
def update(dt):

    global nb_sphere
    global sphere
    global b_sphere

    test = 0
    update = Object()
    todel_sorted = []
    sparsity = 0.1

    for i in range(nb_sphere): # update every sphere from the batch

        move = (random.gauss(0, sparsity), random.gauss(0, sparsity), 
random.gauss(0, sparsity))
        primitive.translate( sphere[i], move )

    # detect collisions between particules
    if nb_sphere > 1:

        #cg_engine.gravity()
        update = cg_engine.collision(sphere, b_sphere, nb_sphere)

        # delete olds particules
        for i in range(len(update.todel)):
            print("delete sphere index %d" %update.todel[i])
            sphere[update.todel[i]].delete()
            sphere.pop(update.todel[i])
            nb_sphere -= 1

        # append new particules
        for j in range(len(update.new)):

            primitive.new_phere(sphere, b_sphere, int(update.new[j][0]), 2,
                                update.new[j][1][0],
                                update.new[j][1][1],
                                update.new[j][1][2], (1.,0.3,0.2) )

            nb_sphere += 1

    window.update(dt) # update player & view


# detect a collision between two sphere and return and object containing 
info to delete and create new ones
def collision(sphere, b_sphere, nb_sphere):

    nb_collision = 0

    update = Object()

    update.todel = []
    update.new = []

    for i in range(nb_sphere):
        for j in range(i+1, nb_sphere):

            # first find center of the sphere 1 and radius
            c_sphere_i = numpy.array([
                ( sphere[i].vertices[0]+sphere[i].vertices[3] ) / 2,
                ( sphere[i].vertices[1]+sphere[i].vertices[4] ) / 2,
                ( sphere[i].vertices[2]+sphere[i].vertices[5] ) / 2])
            r_sphere_i = sphere[i].vertices[0] - c_sphere_i[0]

            # first find center of the sphere 2 and radius
            c_sphere_j = numpy.array([
                ( sphere[j].vertices[0]+sphere[j].vertices[3] ) / 2,
                ( sphere[j].vertices[1]+sphere[j].vertices[4] ) / 2,
                ( sphere[j].vertices[2]+sphere[j].vertices[5] ) / 2])
            r_sphere_j = sphere[j].vertices[0] - c_sphere_j[0]

            # get distance between them
            d = numpy.square(
                ( c_sphere_i[0] - c_sphere_j[0] )**2 +
                ( c_sphere_i[1] - c_sphere_j[1] )**2 +
                ( c_sphere_i[2] - c_sphere_j[2] )**2 )

            # get sum of the radius
            sum_radius = round(r_sphere_i + r_sphere_j, 0)

            # if two particules are close enough
            if( d < sum_radius ):
                ++nb_collision
                print("=== new collision !")

                # store index of the particules to delete
                update.todel.append(i)
                update.todel.append(j)

                new_radius = round( ( 2 * (( r_sphere_i + r_sphere_j )**3) 
)**(1./3) )
                print(new_radius)

                # ponderated by the respective radius of the particules
                influ_i = r_sphere_i / d
                influ_j = r_sphere_j / d
                new_center = numpy.array([
                    (c_sphere_i[0]*influ_i) + (c_sphere_j[0]*influ_j),
                    (c_sphere_i[1]*influ_i) + (c_sphere_j[1]*influ_j),
                    (c_sphere_i[2]*influ_i) + (c_sphere_j[2]*influ_j) ])

                # store info about the new particules we should create
                update.new.append( [sum_radius, new_center] )

                nb_collision += 1

    update.todel = sorted(update.todel, reverse=True)
    update.todel = [ii for n,ii in enumerate(update.todel) if ii not in 
update.todel[:n]]

    return update


I am still learning python so this is probably not a very good code. I know 
I shouldn't be using global variable, I will fix this later.
Do you have any idea about what is causing this problem ? Here are some 
photos :

<https://lh3.googleusercontent.com/-jS_o6sROgB4/Wm4YYJRP9NI/AAAAAAAAAoo/F40em5d4PtQNtCSXHJexK8JqAw7kdtBewCLcBGAs/s1600/Screenshot%2Bfrom%2B2018-01-28%2B13-35-52.png>

<https://lh3.googleusercontent.com/-1Gm8VE20P7M/Wm4YcKrWOHI/AAAAAAAAAos/DevBy5WxpMoTKbxG0zM7ogqc-ktO1pkYgCLcBGAs/s1600/Screenshot%2Bfrom%2B2018-01-28%2B13-35-49.png>

<https://lh3.googleusercontent.com/-22Pkcrv26UM/Wm4YftbNtMI/AAAAAAAAAow/HaWsGkRALuotbT1mKHpbA7YQoTmPnJMHACLcBGAs/s1600/Screenshot%2Bfrom%2B2018-01-28%2B13-34-57.png>

Thank you,

Victor

-- 
You received this message because you are subscribed to the Google Groups 
"pyglet-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to pyglet-users+unsubscr...@googlegroups.com.
To post to this group, send email to pyglet-users@googlegroups.com.
Visit this group at https://groups.google.com/group/pyglet-users.
For more options, visit https://groups.google.com/d/optout.

Reply via email to