How do i add extra dimensions to a screenshot? - python

I currently have the code below.. and it takes the screenshot just fine.. but it cuts off the left and right side of the screenshot
How do i add another 10 pixels all around possible?
print "Taking SS..."
focusWindow = App.focusedWindow()
regionINFO = capture(App.focusedWindow())
shutil.move(regionINFO, os.path.join(r'C:\Screenshots', 'Dummy1.png'))
print "SS Done..."

It looks like you're taking a screenshot of a specific app. Try the whole screen.
import shutil # once at beginning of script
img = capture(SCREEN)
shutil.move(img, 'path')

The answer is present within your code itself. :)
focusWindow = App.focusedWindow()
Here, focusWindow stores the region of the App which the focus is upon. Either like Eugene has said above, you can go ahead to take the whole screenshot or you can append to the current of focusWindow and capture the region.
For eg.: Say you want to add 10 pixels on all sides, it would be like:
focusWindow.x -= 10
focusWindow.y -= 10
focusWindow.w += 20
focusWindow.h += 20
regionINFO = capture(focusWindow)
shutil.move(regionINFO, os.path.join(r'C:\Screenshots', 'Dummy1.png'))
print "SS Done..."

Related

How can I make a delay in python without the camera video get affected and slowed?

Hope you are doing fine.
So my problem or question is actually more complicated than the title but I will try to keep it simple.
I have this code that runs on cam ( using OpenCV ) and will detect if a person wearing a mask or not, as far as detection go it performs very well ( I got the code from YouTube : https://www.youtube.com/watch?v=Ax6P93r32KU&t=73s ).
In short I want the program to see if the person(with confidence > 95%) is wearing a mask or not, if he is wearing the mask a pop-up message will appear thanking him then the program will close.
In theory I've done all that, The problem is that when the person wears a mask the pop-up message will immediately appear before even the cam catch up !
or if the person isn't wearing a mask then starts to wear one the pop-up message will immediately appear also while he is wearing.
Ideally I would like to check if he is wearing the mask for 2 or 3 continues seconds then the pop-up will appear.
I tried using delay but it slows the camera so much and don't see what is happening, I tried append the confidence of wearing a mask into a list then take the average of the list but still didn't work.
So ideally :
confidence of person wearing mask = M
If M > 95% for 3 seconds:
print(message(thank you))
exit()
Hope you have an idea how to solve this, and I'm sorry if my explanation isn't obvious. I can show it with a live stream (discord) for anyone who is interested and didn't understand my problem.
I was able to solve the issue by making an empty list and set t1 = time.time() ( before the while True loop )
mask_list=[]
t1 = time.time()
and inside the loop I would take the reading for 4 seconds
mask_list.append(mask)
if time.time() - t1 > 4: # when 4 seconds passes
mask_avg = sum(mask_list) / len(mask_list)
if mask_avg*100 > 90: # when the average of wearing a mask is > 90%
# code for wearing a mask then exit()
else :
# code for NOT wearing a mask then exit()
I'm not sure if I'm allowed but I will post the code on GitHub if anyone wants to see the full code : https://github.com/Dalsallum/Login-System-With-Mask-Detection
So if i understand properly, something like this should work. Let me know what happends or if you dont understand something. This code uses multiple threads as to not stop the video portion of code.
import time
import threading
wearingMaskBool = False
def checkPerson3Seconds():
global wearingMaskBool
#lets check the person 6 times we will use multiple threads so the camera and the 3 second check code can run simpltaniously
for i in range(6)
if (M > 95%):
#adding one if mask is worn
wearingMask += 1
else:
#subtracting one if mask isnt worn
wearingMask -= 1
#wait half a second
time.sleep(0.5)
#checking if wearingMask == 6
if wearingMask == 6:
#execute code for person that is wearing mask
#example
# we can define the "wearingMaskBool" as a global and use it in out main script
wearingMaskBool = True
else:
#execute code for person that isnt wearing mask
#example
# we can define the "wearingMaskBool" as a global and use it in out main script
wearingMaskBool = False
#start thread aka staring the checkPerson3Seconds script
threading.Thread(target=checkPerson3Seconds(), daemon=True).start()
#after the script is ran if they are wearing a mask with a certainty of 95 percent of 3 seconds the the wearingMaskBool will be equal to true
#if it fell below 95% it will be equal to false

Copy and paste Python functions in Emacs

I have a program that looks something like (this is a silly example to illustrate my point, what it does is not very important)
count = 0
def average(search_term):
average = 0
page = 0
current = download(search_term, page)
while current:
def add_up(downloaded):
results = downloaded.body.get_results()
count += len(results)
return sum(result.score for result in results)
total = average*count
total += add_up(current)
average = total/count
print('Average so far: {:2f}'.format(average))
page += 1
current = download(search_term, page)
If I have the cursor on any of the lines 8–11 and press a key combination I want Emacs to copy or kill the add_up function, and then I want to move the cursor to line 2 and press a key combination and paste the function there, with the correct level of indentation for the context it is pasted in.
Is this possible, and if so, how would I do that?
With python-mode.el py-kill-def and yank would do the job.
However, there are some restrictions. py-kill-def must be called from inside def in question. So needs to go upward from line 11 first.
Also indenting after insert poses some problems: as indent is syntax, sometimes Emacs can't know which indentation is wanted. In example below have an indent of 4 first and of 8 in add_up probably is not wanted - however it's legal code. After indenting first line in body of add_up, py-indent-and-forward should be convenient for the remaining.
def average(search_term):
average = 0
def add_up(downloaded):
results = downloaded.body.get_results()
count += len(results)
return sum(result.score for result in results)
page = 0
current = download(search_term, page)
while current:
total = average*count
total += add_up(current)
average = total/count
print('Average so far: {:2f}'.format(average))
page += 1
current = download(search_term, page)
For this type of thing I usually use expand-region, which I choose to bind to C-=.
Using your example I can select the add_up() function by pressing C-= once, kill the region normally (C-k), move to line 2, and yank as usual (C-y).
Depending on what else you have configured for Python you may have to clean up some whitespace, or it may get cleaned up for you. For example, aggressive-indent would be helpful.
One manual option would be to reindent the pasted code with something like C-x C-x M-\.
I've been using smart-shift (available in Melpa) for this sort of thing. global-smart-shift-mode to enable (beware, it binds keys). Select the block you want to move (I'd use expand-region like Chris), and the default keybind C-S-c <arrow> starts moving it. Once you're shifting, the arrows (without C-S-c) shift further. Horizontal shifts use the major mode's indent offset (python-indent-offset for python.el).

How to display an Image with python, without pyglet or similar?

So, what I am trying to do in detail:
I have a device that acts as a display, although is technically not one (that's not really important, it can be handled like a normal display) and I want to display a series of images on it. When each image is displayed i call a function that takes readings from another device. So far I have used pyglet for that and I can get it to display the images in the correct order and where I want them, but the readings taken seem not to correspond to the right image.
The simplest way to explain what I want to do is:
for a in range(10):
display('image%d'%a)
values(a) = measure()
Imagine values being initiated in the correct form.
What I tried so far was:
import pyglet
import numpy as np
size = 64
no = 512/size
a,b,c = (0,0,0)
values = np.zeros((no,no,3))
display = pyglet.window.get_platform().get_default_display()
screens = []
for screen in display.get_screens():
screens.append(screen)
window = pyglet.window.Window(screen = screens[1], fullscreen=1)
#here i choose the mentioned device, since it is connected to my computer via display port
#window.event
def update(dt):
global a,b,c
if a == no/2. and b == no/2.:
values[a,b,c] = 0
window.clear()
else:
image = pyglet.image.load('folder_%d/grating_%d_%d_%d.bmp' % (size,a,b,c))
window.clear()
print (a,b,c)
image.blit(0,0)
values[a,b,c] = measure()
c+=1
if c == 3:
b += 1
c = 0
if b == no:
a += 1
b = 0
if a == no:
pyglet.app.exit()
pyglet.clock.schedule_interval(update, .2)
pyglet.app.run()
where measure() is my own function. "no" is an index for my images, they range from (0,0,0),(0,0,1),(0,0,2),(0,1,0)... to (no,no,2) and are called to be called one by one. Also the case of a = b = no/2 is a special case that is of no special importance to my problem, I think.
first of all: I am pretty sure this is neither elegant nor efficient but I am not creating software that anyone else is ever likely to use. I am also aware that using global variables is bad practice but their use is due to me not knowing how to use eventloops correctly.
I am not happy with this solution, because the readings i take always seem to correspond to the previous image.
I guess I misuse the eventloop badly, but the pyglet documentation does not really help me here.
Also I feel like I am building a whole truck just to carry a bag across the street...
I have already looked into pyplot as an alternative, since the imshow() function works in the way I want, but the plotting libraries seem to display images in random sizes, which I cannot figure out how to control properly.
I appreciate any help on using pyglet correctly as well as alternative libraries that can help.
Thank you already,
Mopsi
An extra-long comment, that requires formatted code
From your example, you don't need a,b,c outside of the update function and all the global stuff is about having values that stay alive across invocations. If I'm correct this is better suited by a closure, like
...
def make_update(no, window):
from itertools import product
abcs = product(range(no),range(no),range(3))
#window.event
def _update(...):
try:
a, b, c = next(abcs)
except StopIteration:
... wind up ...
...
return _update
update = make_update(no, window)
...
Alright, I did not actually solve the problem but found a workaround:
I just flatten my image nomenclature, e.g
0_0_0 -> 000
0_0_1 -> 001
0_0_2 -> 002
0_1_0 -> 003
etc.
With values now being an array with dimensions [no*no*3,1]
And since for the n-th iteration and therefore n-th measurement I see the (n-1)th image, I simply add a dummy image and assign the n-th measured value to values[n-1].
The first measurement being useless is no problem here, since values[-1] is the last element, which gets overwritten with a meaningful measurement in the end.
Since the number of images is known and predetermined I can reshape my array of values afterwards.
If anyone cares to explain why no the displayed image is shifted by one iteration (with no image at all being displayed at the first iteration) please go ahead.

Trialhandler and time measuring in psychopy

For a go-NoGo Task I want to organize pictures with the data.TrialHandler class from psychopy:
trials = data.TrialHandler(ImageList, nReps=1, method='random')
Now I want to code a loop in which psychopy is going into the dictionary, is presenting the first set of pictures (e.g. A_n) and afterwards is going to the second set until the sixth set. I tried the following:
import glob, os, random, sys, time
import numpy.random as rnd
from psychopy import visual, core, event, monitors, gui, logging, data
im_a = glob.glob('./a*') # upload pictures of the a-type, gives out a List of .jpg-files
im_n = glob.glob('./n*') # n-type
im_e = glob.glob('./e*') # e-type
# combining Lists of Pictures
A_n = im_a + im_n
N_a = im_n + im_a
A_e = im_a + im_e
E_a = im_e + im_a
E_n = im_e + im_n
N_e = im_n + im_e
# making a Dictionary of Pictures and Conditions
PicList = [A_n, N_a, A_e, E_a, E_n, N_e] # just the six Combinations
CondList = [im_a,im_n,im_a,im_e,im_e,im_n] # images that are in the GO-Condition
ImageList = []
for imagelist, condition in zip(PicList, CondList):
ImageList.append({'imagelist':imagelist,'condition':condition}) # to associate the picturelist with the GO Conditionlist
for the header I ask an extra question: Combining and associating multiple dictionaries
# Set Experiment
win = visual.Window(color='white',units='pix', fullscr=False)
fixCross=visual.TextStim(win,text='+',color='black',pos=(0.0,0.0), height=40)
corrFb = visual.TextStim(win,text='O',height=40,color='green',pos=[0,0])
incorrFb = visual.TextStim(win,text='X',height=40, color='red',pos=[0,0])
# Start Experiement
trials = data.TrialHandler(ImageList, nReps=1, method='random')
rt_clock = core.Clock()
bitmap = visual.ImageStim(win)
for liste in ImageList[0:5]: # to loop through all 6 conditions
keys = []
for i,Pictures in enumerate(liste): # to loop through all pictures in each condition
bitmap.setImage(Pictures) # attribute error occurs, not if I use Pictures[0][0], even though in this case every pictures is the same
bitmap.draw()
win.flip()
rt_clock.reset()
resp = False
while rt_clock.getTime() < 2.0: # timelimit is defined 2 s
if not resp:
resp = event.getKeys(keyList=['space'])
rt = rt_clock.getTime()
if bool(resp) is (Pictures in CondList): # at this point python should have access to the Dictionary in which the associated GO Pictures are saved
corrFb.draw()
accu=1 # doesn't work yet
else:
incorrFb.draw()
accu=0
win.flip()
core.wait(0.5)
trials.addData('rt_'+str(i), rt) # is working well when loop: if trial in trials: ...; in this case trialHAndler is not used, therefor trials.addData is not working
trials.addData('accu_'+str(i), accu)
trials.saveAsExcel(datanames)
core.quit()
There are a few problems in this code: first it only presents one pictuere for six times, but not six different pictures [1]
and secondly a totally different problem [2] ist the time measuring and the saving of the accuracy which the trialhandler is doing, but for each trial. So it adds up all the RT's for each trial. I want to get the RT's for each image. I tried a few things like an extra stimulus.trialhandler for the stimuli and an extraloop in the end which gives me the last RT but not each. --> is answered below!!!
for stimuli in stimulus: stimulus.addData('rt', rt)
I know these four questions are a lot for one question, but maybe somebody can give me some good ideas of how I can solve these... Thanks everybody!
The reason for your problem labelled [1] is that you set the image to PicList[0][0] which never changes. As Mike is suggesting above you need::
for i,thisPic in enumerate(PicList):
bitmap.setImage(thisPic) #not PicList[0][0]
But maybe you need to go back to basics so that you actually use the trial handler to handle your trials ;-)
Create a single list of dictionaries where one dictionary represents one trial, and then run through those in order (tell the TrialHandler to use the list 'sequential' rather than 'random'). So the loops that you're currently using should just be to create your list of condition dicts, not to run the trials. Then pass that one list to the trial handler::
trials = TrialHandler(trialTypes = myCondsListInOrder, nReps=1, method='sequential')
for thisTrial in trials:
pic = thisTrial['pic']
stim.setImage(pic)
...
trials.addData('rt', rt)
trials.addData('acc',acc)
Also, I would output your data not using the excel format, but the 'long wide' format::
trials.saveAsWideText('mydataFile.csv')
best wishes,
Jon
(A) This isn't relevant to your question but will improve performance.
The line:
bitmap = visual.ImageStim(win)
Shouldn't occur within the loop. i.e. you should initialise each stimulus only once, then within a loop you just update that the properties of that stimulus, e.g. with bitmap.setImage(…). So shift this initialisation line to the top, where you create the TextStims.
(B) [deleted: I hadn't paid attention to the first code block.]
(C)
bitmap.draw(pictures)
This line doesn't take any arguments. It should just be bitmap.draw(). And anyway, it isn't clear what 'pictures' refers to. Remember that Python is case sensitive. This isn't the same thing as 'Pictures' defined in the loop above. I'm guessing that you want to update what picture is being shown? In that case, then you need to be doing the bitmap.setImage(…) line within this loop, not above, where you will always be drawing a fixed picture as that is the only one that gets set on each trial.
(D) Re the RTs, you are saving this only once per trial (check the indentation). If you want to save one per image, you need to indent these lines again. Also, you only get one line per trial in the data output. If you want to record multiple RTs per trial, you will need to give them unique names, e.g. rt_1, rt_2, …, rt_6 so they each appear in a separate column. e.g. you could use an enumerator for this loop:
for i, picture in enumerate(Piclist)
# lots of code
# then save data:
trials.addData('rt_'+str(i), rt)

How to changed colours of some pixels of an image?

I'm trying to leave one third of the image stock, change all the black to yellow in the middle, and change the bottom third black to blue. I know how to change the colours, the problem I'm facing is I'm unaware of how I can select only one third of the pixels to manipulate them. Here s what I have..
def changeSpots1():
file = pickAFile()
picture = makePicture(file)
show(picture)
pix = getAllPixels(picture)
for p in pix:
intensity = (getRed(p) + getGreen(p) + getBlue(p))
c = getColor(p)
if (intensity < 150):
newColour = setColor(p, yellow)
repaint(picture)
I am using a program called JES to write this, incase you're wondering about commands like pickAFile.
Thank you for any help!
I know nothing about JES, but I'm going to guess that getAllPixels returns the pixels in the usual order: the first row, then the next row, then the next, etc.
If so:
pix = getAllPixels(picture)
third = len(pix) // 3
for p in pix[:third]:
# do top-third stuff
for p in pix[third:third*2]:
# do middle-third stuff
for p in pix[third*2:]:
# do bottom-third stuff
This does assume that the picture s divisible perfectly into thirds. If it's not, you will need to know the picture's width so you can round to the nearest complete row (because otherwise the top third might actually be 250 complete rows and the first 47 pixels of the 251st, which won't look very good). I don't know what function JES has to get the width, but I'm sure it's simple.

Categories