Search code examples
pythonpsychopy

Psychopy: Creating multiple line objects simultaneously


My code here works, but my current method is very inefficient and time consuming. I'm generating 4 Cartesian coordinates and appending them to a list. I'm then creating 4 Psychopy line objects (visual.Line) and assigning each object an x,y coordinate from my coordinates list (zdot_list). Currently, I'm creating 4 lines objects one after the other, and assigning an xy position to each 'start' parameter.

from psychopy import visual, core, event, sound
import random
import math

win = visual.Window([800,600],color=(0,0,0), colorSpace='rgb', rgb=None, allowGUI=True, monitor='testMonitor', units='deg', fullscr=True, screen=2)

# input polar, output cartesian coords
def pol_to_cart(distance, angle, x_origin=0, y_origin=0):

    x=distance*math.cos(math.radians(angle))
    y=distance*math.sin(math.radians(angle))

    return x +x_origin, y + y_origin


zdots = 4
zdot_list = []
j=(-8)

# generate 4 xy coordinates and append to list
for i in range(zdots):

    angle=0

    line_cart = pol_to_cart(j, angle)
    dotx = line_cart[0]
    doty = line_cart[1]
    zdot_list.append([dotx, doty])

    j += .2

# generate 4 lines, add xy coordinate (from list^) to 'start' argument of each
linea = visual.Line(win, start=(zdot_list[0]), end=(4,0), lineColor="white")
lineb = visual.Line(win, start=(zdot_list[1]), end=(4,0), lineColor="white")
linec = visual.Line(win, start=(zdot_list[2]), end=(4,0), lineColor="white")
lined = visual.Line(win, start=(zdot_list[3]), end=(4,0), lineColor="white")

lines = [linea, lineb, linec, lined]

# display lines
for line in lines:
    line.draw()
    win.flip()
    core.wait(3)
    win.close()

Is there a more efficient way to create line (or any shape) objects using a loop? I'd like to auto-generate the objects I need, adding my xy coordinate to each objects 'start' argument respectively. There are only 4 line objects in the image, but in reality I will need 80+, each with a different xy start coordinate.

Cheers, Jon


Solution

  • You can try and explore Polygon from visual module. Sample of Polygon usage below

    from psychopy import visual, core, event, sound
    win = visual.Window([680,480],color=(0,0,0), colorSpace='rgb', rgb=None, allowGUI=True, monitor='testMonitor', units='deg', fullscr=False, screen=2)
    pgon = visual.Polygon(win, edges=4)
    pgon.draw()
    win.flip()
    

    You can explore vertices and other options by going through psychophy documentation.

    An optimisation to your code would be:

    zdots=40
    zdot_list = []
    
    for i in range(zdots):
        angle=0
        line_cart = pol_to_cart(j, angle)
        zdot_list.append(visual.Line(win, start=([line_cart[0], line_cart[1]]), end=(4,0), lineColor="white"))
        j += .2
    
    for i in zdot_list:
        i.draw()
    
    win.flip()
    core.wait(3)
    win.close()