~nch/glue

d611aba6519bc382b219328b621191234eccf360 — nc 2 months ago 6b1de61 master
...
1 files changed, 49 insertions(+), 15 deletions(-)

M drag_and_drop.py
M drag_and_drop.py => drag_and_drop.py +49 -15
@@ 6,7 6,7 @@ import rx
from rx import operators as ops
from rx.subject import Subject
from rx.scheduler.mainloop import PyGameScheduler
from pysm import StateMachine, Event, State
#from pysm import StateMachine, Event, State

from dataclasses import dataclass
from typing import *


@@ 16,6 16,7 @@ win = sdl2.ext.Window('drag and drop', size=(800, 600))
win.show()

boxes = pd.DataFrame(columns=['x', 'y', 'w', 'h'])
edges = pd.DataFrame(columns=['from', 'to'])

def insert_many(df, ts):
    n = len(ts[list(ts.keys())[0]])


@@ 32,6 33,8 @@ def insert(df, t):
    df.loc[id_] = t
    return id_

#insert(edges, (0, 1))

def in_bb(bb, pos):
    bx, by, bw, bh = bb
    x, y = pos


@@ 40,8 43,9 @@ def in_bb(bb, pos):
renderer = sdl2.ext.Renderer(win)

mouse_move = Subject()
mouse_down = Subject()
mouse_up = Subject()
click = Subject()
ctrl_click = Subject()
click_up = Subject()

scheduler = PyGameScheduler(None)



@@ 63,25 67,51 @@ def find_box_at(pos):
    else:
        return None

box_click = mouse_down.pipe(ops.map(find_box_at), ops.filter(lambda x: x is not None))
box_click = click.pipe(ops.map(find_box_at), ops.filter(lambda x: x is not None))

def move_box(id_, p):
    w, h = boxes.loc[id_, ['w', 'h']]
def move_target(table, id_, p):
    w, h = table.loc[id_, ['w', 'h']]
    boxes.loc[id_, ['x', 'y']] = p[0] - w // 2, p[1] - h // 2

drag = mouse_move.pipe(
        ops.combine_latest(box_click),
        ops.take_until(mouse_up),
        ops.repeat()).subscribe(lambda x: move_box(x[1], x[0]))
### states

def drag(table, target_id):
    mouse_move.pipe(ops.take_until(click_up)).subscribe(lambda p: move_target(table, target_id, p))

def connect(from_id):
    import uuid
    i = uuid.uuid4()
    def f(to_id):
        if from_id is not None and to_id is not None:
            insert(edges, (from_id, to_id))
    click_up.pipe(ops.map(find_box_at), ops.finally_action(lambda: print(i, 'completed'))).subscribe(f)

box_click.pipe(ops.repeat()).subscribe(lambda x: drag(boxes, x))
ctrl_click.pipe(ops.map(find_box_at), ops.repeat()).subscribe(lambda x: connect(x))

'''
click_up.pipe(
        ops.combine_latest(ctrl_click),
        ops.map(lambda x: (find_box_at(x[1]), find_box_at(x[0])))
        #ops.skip_until(click_up),
        #ops.map(lambda x: (find_box_at(x[0]), find_box_at(x[1]))),
        #ops.repeat()
        ).subscribe(print)
'''

#mouse_move.subscribe(lambda x: x)

### main loop

running = True
while running:
    renderer.clear()
    for id_, row in boxes.iterrows():
        x, y, w, h = row
        renderer.draw_rect([(x, y, w, h)], (255, 255, 255))
    renderer.draw_rect(list(zip(boxes.x, boxes.y, boxes.w, boxes.h)), (255, 255, 255))
    for _, (from_, to) in edges.iterrows():
        a, b = boxes.loc[from_], boxes.loc[to]
        renderer.draw_line((a.x, a.y, b.x, b.y), (255, 255, 255))
    #sdl2.ext.line(surface, (255, 255, 255), (10, 10, 20, 20, 30, 30, 40, 40))
    #sdl2.sdlgfx.lineRGBA(renderer,
    events = sdl2.ext.get_events()
    for event in events:
        if event.type == sdl2.SDL_QUIT:


@@ 89,9 119,13 @@ while running:
        if event.type == sdl2.SDL_MOUSEMOTION:
            mouse_move.on_next((event.motion.x, event.motion.y))
        if event.type == sdl2.SDL_MOUSEBUTTONDOWN:
            mouse_down.on_next((event.motion.x, event.motion.y))
            key_states = sdl2.SDL_GetKeyboardState(None)
            if key_states[sdl2.SDL_SCANCODE_LCTRL]:
                ctrl_click.on_next((event.motion.x, event.motion.y))
            else:
                click.on_next((event.motion.x, event.motion.y))
        if event.type == sdl2.SDL_MOUSEBUTTONUP:
            mouse_up.on_next((event.motion.x, event.motion.y))
            click_up.on_next((event.motion.x, event.motion.y))

    scheduler.run()