WorldViz User Forum

WorldViz User Forum (
-   Vizard (
-   -   Having objects avoid one another (

hannahapz 08-13-2018 08:25 PM

Having objects avoid one another
I made an environment that involves cars traveling at random speeds. At times, certain cars overlap. I want to avoid this by introducing proximity sensors so that when two cars get close to one another, the car in front speeds up.

Right now, the location of my sensors are identical to the location of my targets (i.e. the same car). What can I do to have all the cars be targets for one another AND have their own self sensors, but only involve the front car accelerate when the car behind it gets too close (as opposed to all cars accelerating, which is what my code is doing right now)?

Looking for a solution to my flawed logic.

kennethkarthik 08-15-2018 08:50 AM

Since you're going to have a stream of cars, maybe you could declare your cars as an array of 3D objects and set the callback for the proximity to be the car next accordingly.
Refer to the
proximity sensors section of the documentation for examples of how to use proximity callbacks.
Also if you don't want your objects to overlap you can turn on collision.

hannahapz 08-23-2018 11:05 AM

So it's not so much a single stream of cars as it is three streams of cars, where the cars' positions are randomly generated. These cars are in an array already, but they're not organized based on which lane they're in. I guess I should do that first ? Is there an easier way?

hannahapz 08-23-2018 12:11 PM

Also, I forgot to mention that the x-positions of the cars change so I'm wondering if there's a way to take that into account and still have the cars avoid one another without having their sensors interfere with the identical target assignment.

hannahapz 08-26-2018 03:58 PM

Here is the code AFTER I've created a list of positions. Here I create an array of 3D cars:


obs_cars_array = []
for c_set in obs_pos: # for every coordinate set in the list of positions
obs_car = viz.add('mini.osg') # assign a car avatar
obs_car.setPosition([c_set[0], 0.8, c_set[1]]) # set the position of each car avatar
obs_cars_total.append(obs_car) # create array of 3D car objects
Then I create a sensor and target within same block of code:


obs_car_target = vizproximity.Target(obs_car) # make each car a target
manager.addTarget(obs_car_target) # add it to the target manager
sensor = vizproximity.addBoundingSphereSensor(obs_car,scale =1) # make same car a sensor
manager.addSensor(sensor) # update sensor manager
I need to find a solution that will help me prevent any of the cars in the array from getting too close to another another.

Jeff 09-01-2018 01:06 AM

It maybe easier to use the vizmat.Distance command in this case. If each lane of cars is arranged in its own list, you could loop through the list and for each car check the distance of the cars both in front and in back.

hannahapz 09-05-2018 05:40 PM

Thanks Jeff! This is what I ended up doing coincidentally. Cheers

hannahapz 10-07-2018 07:50 PM

So I've managed to use the distance function to inform me of when my cars get too close to one another, and I've managed to speed up the lead car/slow down the tailing car to simulate realistic driving, but the problem I'm having is with my nested if loops.


# function that has cars move at a trajectory of, in this example, 10 m/s)
def moving_cars():
        global elapsedTime, z, obs_car
        for i, item in enumerate(my_entire_car_list):
                item.add(vizact.move(0, 0, 10)

# function ensures cars adjust speeds if they get within a certain distance of one another (lead car speed up and tail slows)                       
def track_A_moving_cars():
        global track_A, track_B, track_C
        for i in range(len(track_A)):
                for a in track_A[i+1:]:
                        if vizmat.Distance(track_A[i].getPosition(), a.getPosition()) < 30.0:
                                if track_A[i].getPosition()[2] < a.getPosition()[2]:
                                        a.add(vizact.move(0, 0, 3, 1), 0)
                                        track_A[i].add(vizact.move(0, 0, -10, 2), 1)
                                elif track_A[i].getPosition()[2] > a.getPosition()[2]:
                                        a.add(vizact.move(0, 0, -10, 2), 2)
                                        track_A[i].add(vizact.move(0, 0, 3, 1), 3)

EXAMPLE OF MY PROBLEM: targeted tail car will slow down, then resume regular speed, slow down again, resume regular speed, etc. I'm assuming this is because o fmy nested if within nested for loop. I've set the function to run every frame. How do I restart the function?

Any help would be greatly appreciated.

All times are GMT -7. The time now is 11:07 AM.

Powered by vBulletin® Version 3.8.7
Copyright ©2000 - 2021, vBulletin Solutions, Inc.
Copyright 2002-2018 WorldViz LLC