Inconsistent behaviour of SIkuli code run

Asked by ONG YI CHONG on 2018-12-17

I am getting inconsistent results when i try running the following code.

Basically what happens is observe_and_click(..) method is called, which will cause the region to observe for changes. Once region detects changes, the handler method will be called.

def observe_and_click(self,phone_region, pixel_region, handler, observe_time):
        pixel_region.click() # make pixel click on region
        print("after click")
        phone_region.observe(observe_time) # how long to observe for

 def handler(self,event):
        global i
        r = event.getRegion() # get the observing region for this event
        wait(0.5)
        found = False
        for j in range(i):
            print("j: " + str(j))
            try:
                match = r.find(base_path + str(j))
                found = True
                break
            except FindFailed:
                print("ignore")
        print(found)
        if (found == False):
            print("whY")
            path = capture(r,"/Users/ongyichong/SikuliX/Scripts",str(i))
            i += 1
            print(str(i))

Problem is sometimes when i go into the handler code, the print(found) code does not get executed. I expect the handler code to run to completion before exiting when it detects a change. At other times, i am able to see the print(found) on my terminal. Not sure why I am getting inconsistency in results ?

I could post more details about the debug logs if needed.

Question information

Language:
English Edit question
Status:
Answered
For:
Sikuli Edit question
Assignee:
No assignee Edit question
Last query:
2018-12-17
Last reply:
2018-12-19
RaiMan (raimund-hocke) said : #1

Yes, if the handler is entered, it should run to the end and should either print True or False, WhY and path.

Is the observe_and_click called from inside a try--except?

Are only True cases missing or only False cases or even both?

Are the prints before (j: 0 ...) and after in case of False (Why + path) always visible?

To make it clearer, add a print to the start and the end.

def handler(self,event):
        global i
        print "Starting handler:", i
        r = event.getRegion() # get the observing region for this event
        wait(0.5)
        found = False
        for j in range(i):
            print("j: " + str(j))
            try:
                match = r.find(base_path + str(j))
                found = True
                break
            except FindFailed:
                print("ignore")
        print(found)
        if (found == False):
            print("whY")
            path = capture(r,"/Users/ongyichong/SikuliX/Scripts",str(i))
            i += 1
            print(str(i))
       print "Ending Handler:", i

ONG YI CHONG (calveeen) said : #2

1) The observe and click is not called within a try catch

2) for print(found), True cases are missing. I have not seen a false case which causes a crash. However, some True cases do not cause crashes

3) all the lines of code within the for loop get executed, only the line at print(found) and afterwards does not get executed.

4) The Ending handler does not get printed when my code does not work as intended.

This is what happens before the crash, after j = 0 is printed

[debug] Image: reused: /Users/ongyichong/SikuliX/Scripts/0.png (file:/Users/ongyichong/SikuliX/Scripts/0.png)
[debug] Region: find: waiting 0 secs for /Users/ongyichong/SikuliX/Scripts/0.png to appear in R[20,101 267x429]@S(0)
[debug] Finder2: makeMat: INT_RGB (267x429)
[debug] Finder2: makeMat: 3BYTE_BGR (265x430)
[debug] Finder2: doFind: start (stdDev: 275.3149 mean: 503.153366)
[debug] Observer: update result: Changes: true
[debug] Region: observe: stopped due to timeout in R[20,101 267x429]@S(0) for 0.2 seconds

I realise that for successful attempts at running the whole handler code there is a similarity percentage that will be shown

This is what happens when it is successful, after j = 0 is printed

[debug] Image: reused: /Users/ongyichong/SikuliX/Scripts/0.png (file:/Users/ongyichong/SikuliX/Scripts/0.png)
[debug] Region: find: waiting 0 secs for /Users/ongyichong/SikuliX/Scripts/0.png to appear in R[20,101 266x430]@S(0)
[debug] Finder2: makeMat: INT_RGB (266x430)
[debug] Finder2: makeMat: 3BYTE_BGR (265x430)
[debug] Finder2: doFind: start (stdDev: 275.3149 mean: 503.153366)
[debug] Finder2: doFind: in original: %15.7534 (?95) 9 msec
[debug] Finder2: doFind: end 9 msec
[debug] Region: find: /Users/ongyichong/SikuliX/Scripts/0.png did not appear [28 msec]
[debug] Region: handleFindFailed: /Users/ongyichong/SikuliX/Scripts/0.png

ONG YI CHONG (calveeen) said : #3

Also another one of my unsuccessful attempts.

[debug] Region: observe: starting in R[18,101 269x431]@S(0) for 0.2 seconds
[debug] Observer: resetting observe states for R[18,101 269x431]@S(0)
[debug] Observing: add observer: now running 2 observer(s)
[debug] Observer: update result: Patterns: false
[debug] Finder2: makeMat: INT_RGB (269x431)
[debug] Image: BufferedImage: (269, 431)
[debug] Finder2: makeMat: INT_RGB (269x431)
[debug] Observer: changes: 19 in: R[18,101 269x431]@S(0) E:Y, T:3.0
[debug] Observer: running call back
('Starting Handler', 1)
j :0
[debug] Observer: update result: Changes: true
[debug] Region: observe: stopped due to timeout in R[18,101 269x431]@S(0) for 0.2 seconds

ONG YI CHONG (calveeen) said : #4

It seems like the handler code was cut off because the observation timed out or something

RaiMan (raimund-hocke) said : #5

A general comment (I think I already mentioned before):
print is a statement and not a function, so the list of items to be printed have to be given WITHOUT brackets:

so not
print ("Starting handler:", i) #prints ('Starting Handler', 1)

but
print "Starting handler:", i #prints Starting Handler: 1
... as intended

RaiMan (raimund-hocke) said : #6

Your problem:
I am sorry, but I do not understand your logic, since I do not know you intention.

To come out of the trap, you have to design each step and make it running.

... and then you have to put things together.

ONG YI CHONG (calveeen) said : #7

What i wanted to do was every time the region changes in pixel, indicating a change in screen page, the handler code would run and compare with the previous screenshots taken to see if the current page matches any of the previous screen shots taken. If there are no similar screenshots to the current screen page, then it takes a screenshot of the current screen page. This is controlled by the "found" variable.

The problem i have is that it works sometimes and it doesn't work at times and I cant identify the differences between the two situations through the logs.

ONG YI CHONG (calveeen) said : #8

After adding a print before

match = r.find(....)

and a print after, it seems that the handler function exits at the match statement because the print before match = r.find(...) gets printed while the print after match = r.find(...) does not.

RaiMan (raimund-hocke) said : #9

test this

...
        print("j: " + str(j))
        match = r.exists(base_path + str(j), 0)
        if (match):
            found = True
            break
        else:
            print("ignore")
        print(found)
...

ONG YI CHONG (calveeen) said : #10

The handler is still not getting executed completely. I have changed my code to this
def handler(self,event):
        print "Starting Handler",i
        global i
        r = event.getRegion() # get the observing region for this event
        #for ch in event.getChanges():
        # ch.highlight() # highlight all changes
        # wait(0.1)
        #for ch in event.getChanges():
        # ch.highlight() # turn off the highlights
        base_path = "/Users/ongyichong/SikuliX/Scripts/"
        self.hasChanged = True # screenPage has changed
        #path = capture(r,"/Users/ongyichong/SikuliX/Scripts",str(i))
        #i += 1
        wait(2) # ensure UI elements transition fully before taking screen shot
        found = False
        j = 0
        similar_screenShot = None
        for screenShot in self.screenshot_list:
            print("j :" + str(j))
            print "zzz"
            match = r.exists(screenShot.image_path)
            if (match):
                similar_screenShot = screenShot
                print("match") # each screenshot object stores a path to the image
                found = True
                break
            else:
                print("ignore")
        j += 1
        print("yes:")
        print(found)
        if (similar_screenShot is None):
            print("whY")
            path = capture(r,"/Users/ongyichong/SikuliX/Scripts",str(i))
            self.changedScreenshot = ScreenPage(path,Region(self.start_pixel_region)) # new screen page so pixel region should be a new one
            self.screenshot_list.insert(0,self.changedScreenshot) # append screenShot to screenshot list
            i += 1
            print(str(i))
        else: # similar screenshot
            self.changedScreenshot = similar_screenShot
        print "Ending handler",i

Sorry its kinda messy but basically my screenShot is an object now. Handler code still doesnt run to full completion sometimes as well still.

[debug] Region: observe: starting in R[30,98 259x431]@S(0) for 0.5 seconds
[debug] Observer: resetting observe states for R[30,98 259x431]@S(0)
[debug] Observing: add observer: now running 1 observer(s)
[debug] Observer: update result: Patterns: false
[debug] Observer: update result: Changes: true

[debug] Observer: update result: Patterns: false
[debug] Finder2: makeMat: INT_RGB (259x431)
[debug] Image: BufferedImage: (259, 431)
[debug] Finder2: makeMat: INT_RGB (259x431)
[debug] Observer: changes: 18 in: R[30,98 259x431]@S(0) E:Y, T:3.0
[debug] Observer: running call back
Starting Handler 1
j :0
zzz
[debug] Image: reused: /Users/ongyichong/SikuliX/Scripts/0.png (file:/Users/ongyichong/SikuliX/Scripts/0.png)
[debug] Region: exists: waiting 3.0 secs for /Users/ongyichong/SikuliX/Scripts/0.png to appear in R[30,98 259x431]@S(0)
[debug] Finder2: makeMat: INT_RGB (259x431)
[debug] Finder2: makeMat: 3BYTE_BGR (263x429)
[debug] Finder2: doFind: start (stdDev: 277.3886 mean: 504.141340)
[debug] Observer: update result: Changes: true
[debug] Region: observe: stopped due to timeout in R[30,98 259x431]@S(0) for 0.5 seconds

ONG YI CHONG (calveeen) said : #11

Is there a way to change the Region.exists() timing to be shorter?

RaiMan (raimund-hocke) said : #12

The search speed for one search try

1. gets faster the smaller the search region

2. gets faster the smaller the difference of size between search region and image to be searched

where 1. has the most effect.

Search trials are repeated until waittime (standard 3 secs) has elapsed.

find() and has() do only one search trial (do not wait)

exists() and wait() have a second parameter to specify the waittime, which can be set to 0 (no wait, only one trial)

Can you help with this problem?

Provide an answer of your own, or ask ONG YI CHONG for more information if necessary.

To post a message you must log in.