WorldViz User Forum

WorldViz User Forum (https://forum.worldviz.com/index.php)
-   Vizard (https://forum.worldviz.com/forumdisplay.php?f=17)
-   -   delaying proximity reaction makes sensor unresponsive for the time of delay (https://forum.worldviz.com/showthread.php?t=5897)

jelly 11-21-2016 03:32 AM

delaying proximity reaction makes sensor unresponsive for the time of delay
 
In a recent post I had a problem implementing a delay in the proximity manager and Jeff has suggested the solution of using "vizproximity.waitEnter" and a while loop:

Code:

def proximityTask():
        global handstate
        while True:
                yield vizproximity.waitEnter(SensorIndexFinger)
                print 'entered sensor'
                yield viztask.waitTime(2)
                print 'two seconds elapsed'
                handstate = 1

viztask.schedule(proximityTask())

However, with this code I have a new problem and I decided to open up a new thread:

What happens now is that, once the sensor is entered, the action (change of the variable handstate from 0 to 1), will be delayed by two seconds. However if I happen to enter the sensor again very quickly, before these two 2 seconds have elapsed, nothing happens, as it seems that it is not registered that the sensor has been entered, until the first action takes place.

I wonder if there is a way around this? I tried to to the following: I will change a new variable upon entry but then I will make a new function where I say that IF the new variable "condition" is equal to 1 then after 2 seconds the handstate should change to 1 (= delayed action). This way I am hoping that I am not delaying the action itself in the proximity manager, I am delaying it outside of that function so that the proximity manager can freely register all entries.

Code:


def EnterProximity_IndexFinger(e): # decide what happens on sensor entry
        global handstate, condition
        e.sensor == SensorIndexFinger
        condition = 1
        print condition
manager.onEnter(SensorIndexFinger,EnterProximity_IndexFinger)

with this I am just changing the variable condition and the I will try to use that in the following way:

Code:

def Handdelay():
        global handstate, condition
        print "now"
        if condition == 1:
                #yield vizproximity.waitEnter(SensorIndexFinger)
                yield viztask.waitTime(2)
                handstate = 1
                print "open hand"
        else:
                handstate = 0

viztask.schedule(Handdelay())

Unfortunately, the condition change is registered as soon as I enter the sensor, but the function which is supposed to call the delayed action (handstate changing to 1) is not working.

I would be very grateful for help!

Jeff 11-21-2016 11:22 AM

It sounds like you need to determine whether the sensor was exited before two seconds elapsed. If that's the case, use the viztask.waitAny command to help with this:

Code:

def proximityTask():
       
        waitEnter = vizproximity.waitEnter(SensorIndexFinger)
        waitExit = vizproximity.waitExit(SensorIndexFinger)
        waitTime = viztask.waitTime(2)
       
        while True:
                yield waitEnter
                print 'entered sensor'
                               
                d = yield viztask.waitAny( [ waitExit, waitTime ] )
               
                if d.condition is waitExit:
                        print 'Sensor exited before two seconds'
                else:
                        print '2 seconds elapsed'
               
viztask.schedule(proximityTask())


jelly 11-22-2016 10:02 AM

I have tried this code but what it does is, it triggers the action as long as the sensor is still entered, after 2 seconds and does not do that if the sensor is exited before 2 seconds have elapsed.

I actually think this might be a different issue:

I want an action to be triggered with a delay, every single time a sensor is entered. If I use waitEnter and waitTime what I achieve is that I "block" the sensor - nothing is registered until the action (and the 2 second delay) are carried out. So it cannot be that I trigger the action EVERY time a sensor is entered, because the 2 second delay creates a minimum of time that needs to have passed before another sensor entry is even registered. Basically, I want the sensor to be entered instantly, each time, and only the action - which is a consequence of the sensor entry - should be triggered with a delay.

Another illustration:

1) If I approach an object, I enter its sensor and I trigger an action of that object.
2) If I want a 2 second delay: I approach an object, I enter its sensor and I trigger an action of that object only after 2 seconds.
3) The problem comes now: If I approach an object a second time within one second of the first time, nothing will happen, because the program is still carrying out the action with delay scheduled as a response to the first approach.

Jeff 11-22-2016 11:07 AM

Try the following example. After the sensor enter event occurs in the proximity task another task is called that handles the delay:

Code:

import viz
import vizproximity
import viztask

viz.go()

dojo = viz.addChild('dojo.osgb')

#Create proximity manager
manager = vizproximity.Manager()
manager.setDebug(viz.ON)

#Add main viewpoint as proximity target
target = vizproximity.Target(viz.MainView)
manager.addTarget(target)

#Create sensor using static matrix
sensor = vizproximity.Sensor(vizproximity.Sphere(1.0),source=viz.Matrix.translate(0,1.5,3))
manager.addSensor(sensor)

def delayTask():
        yield viztask.waitTime(2)
        print '2 seconds elapsed'

def proximityTask():
        while True:
                yield vizproximity.waitEnter(sensor)
                print 'entered sensor'
                viztask.schedule(delayTask())

viztask.schedule(proximityTask())


jelly 11-23-2016 04:20 AM

Jeff, thank you very much! It works perfectly, I have adapted it for my script:

Code:

def delayTask():
        global handstate
        yield viztask.waitTime(2)
        handstate = 1
        print '2 seconds elapsed'
        yield viztask.waitTime(0.7)
        handstate = 0

def proximityTask():
        while True:
                yield vizproximity.waitEnter(SensorIndexFinger)
                print 'entered sensor'
                viztask.schedule(delayTask())

viztask.schedule(proximityTask())

I think I had a good intuition that I needed two steps or two functions to implement this, but I was stuck thinking that I needed the "manager.onEnter". Thanks again!


All times are GMT -7. The time now is 10:08 PM.

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