Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/344.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何让程序知道两个项目相互接触?Python/tkinter_Python_Tkinter - Fatal编程技术网

如何让程序知道两个项目相互接触?Python/tkinter

如何让程序知道两个项目相互接触?Python/tkinter,python,tkinter,Python,Tkinter,我希望能够在画布上添加许多门,但当它们触摸输出或输入行时,程序知道它们正在触摸并输出消息,例如“and gate连接到and gate”。 这是将门插入画布的代码。我曾尝试将输入/输出行制作成不同的标签,可以相互识别,但没有成功。有什么建议吗 from tkinter import * canvas=Canvas(width=600,height=600) canvas.grid() gate_id = 0 def andGATE(): global gate_id gate

我希望能够在画布上添加许多门,但当它们触摸输出或输入行时,程序知道它们正在触摸并输出消息,例如“and gate连接到and gate”。 这是将门插入画布的代码。我曾尝试将输入/输出行制作成不同的标签,可以相互识别,但没有成功。有什么建议吗

from tkinter import *

canvas=Canvas(width=600,height=600)
canvas.grid()

gate_id = 0
def andGATE():
    global gate_id
    gate_id += 1
    gate_tag = "andgate-%s" % gate_id
    tags = ("andgate", gate_tag)

    canvas.create_line(150, 50, 150, 150, width=5, tags=tags)
    canvas.create_arc(150, 50, 200, 150, start=90, extent=-180, width=5, fill="black", tags=tags)

    canvas.create_line(150, 75, 120, 75, width=5, tags=tags)
    canvas.create_line(150, 120, 120, 120, width=5, tags=tags)
    canvas.create_line(200, 100, 250, 100, width=5, tags=tags)
    canvas.create_rectangle(150, 50, 180, 150, width=5, fill="black", tags=tags)

    canvas.tag_bind(gate_tag, "<B1-Motion>", lambda event, tag=gate_tag: moveANDGate(event, tag))

def gateSelected():
    sf=var.get()
    if sf=='AND':
        andGATE()


def moveANDGate(event, tag):
    x=event.x
    y=event.y
    coords=canvas.coords(tag)
    movex=x-coords[0]
    movey=y-coords[1]
    canvas.move(tag, movex, movey)

root = Tk()
root.geometry("500x500")
var = StringVar(root)
var.set('AND')
choices = ['AND']
option = OptionMenu(root, var, *choices)
option.pack(side="left",padx=10,pady=10)
button = Button(root, text="Add Gate", command=gateSelected)
button.pack(side="left",padx=10,pady=10)
clearButton = Button(root,text="Clear",command=lambda:clearScreen())
clearButton.pack(side="left",padx=30,pady=10)
root.mainloop()
从tkinter导入*
画布=画布(宽度=600,高度=600)
canvas.grid()
门id=0
def和gate():
全局门id
门id+=1
gate\u tag=“andgate-%s”%gate\u id
标签=(“andgate”,gate_标签)
画布。创建线(150,50,150,150,宽度=5,标签=标签)
canvas.create_弧(150,50,200,150,开始=90,范围=180,宽度=5,fill=“black”,tags=tags)
画布。创建线(150,75,120,75,宽度=5,标签=标签)
画布。创建线(150、120、120、120,宽度=5,标记=标记)
画布。创建线(200100250100,宽度=5,标签=tags)
画布。创建一个矩形(150,50,180,150,宽度=5,fill=“black”,tags=tags)
canvas.tag_bind(gate_tag,“”,lambda事件,tag=gate_tag:moveANDGate(事件,标记))
def gateSelected():
sf=var.get()
如果sf=='和':
andGATE()
def moveANDGate(事件、标记):
x=事件.x
y=事件。y
coords=canvas.coords(标记)
movex=x-coords[0]
movey=y坐标[1]
canvas.move(标记、movex、movey)
root=Tk()
根几何(“500x500”)
var=StringVar(根)
var.set('和')
选项=['和']
选项=选项菜单(根、变量、*选项)
选项包(side=“left”,padx=10,pady=10)
按钮=按钮(根,text=“添加门”,命令=门已选定)
按钮包(side=“left”,padx=10,pady=10)
clearButton=Button(root,text=“Clear”,command=lambda:clearScreen())
clearButton.pack(side=“left”,padx=30,pady=10)
root.mainloop()

这不是一个完整的答案,而是朝着正确方向迈出的可行的一步

from tkinter import *

gate_id = 0
def andGATE():
    global gate_id
    gate_id += 1
    gate_tag = "andgate-%s" % gate_id
    tags = ("andgate", gate_tag)
    inputs = ("andgate", gate_tag, "input")
    outputs = ("andgate", gate_tag, "output")

    canvas.create_line(150, 50, 150, 150, width=5, tags=tags)
    canvas.create_arc(150, 50, 200, 150, start=90, extent=-180, width=5, fill="black", tags=tags)

    canvas.create_line(150, 75, 120, 75, width=5, tags=tags)
    canvas.create_line(150, 120, 120, 120, width=5, tags=tags)

    canvas.create_line(200, 100, 250, 100, width=5, tags=tags)
    #End of output
    canvas.create_line(250,100,245,100, width=5, fill="red", tags=outputs)
    #End of inputs
    canvas.create_line(150, 75, 120, 75, width=5, tags=tags)
    canvas.create_line(120, 75, 125, 75, width=5, fill="blue", tags=inputs)
    canvas.create_line(120, 120, 125, 120, width=5, fill="blue", tags=inputs)

    canvas.create_rectangle(150, 50, 180, 150, width=5, fill="black", tags=outputs)

    canvas.tag_bind(gate_tag, "<B1-Motion>", lambda event, tag=gate_tag: moveANDGate(event, tag))

def gateSelected():
    sf=var.get()
    if sf=='AND':
        andGATE()


def moveANDGate(event, tag):
    x=event.x
    y=event.y
    coords=canvas.coords(tag)
    movex=x-coords[0]
    movey=y-coords[1]
    canvas.move(tag, movex, movey)
    #print("Move")

    #Determine if we have an overlap between an input and an output
    for item in canvas.find_all():
        tags = canvas.gettags(item)
        if tag in tags:
            if 'input' in tags:
                #current item is an input of the moved object
                #Get the items coordinates
                coords = canvas.coords(item)
                #Find if we overlap with other objects
                closest = canvas.find_overlapping(coords[0],coords[1],coords[2],coords[3])
                for closest_items in closest:
                    closest_tags = canvas.gettags(closest_items)
                    if 'output' in closest_tags:
                        #If we overlap with another object, print connected and the appropriate tags
                        print("connected", closest_tags, "-", tag)




root = Tk()
root.geometry("500x500")
canvas=Canvas(root,width=300,height=300)
canvas.pack()
var = StringVar(root)
var.set('AND')
choices = ['AND']
option = OptionMenu(root, var, *choices)
option.pack(side="left",padx=10,pady=10)
button = Button(root, text="Add Gate", command=gateSelected)
button.pack(side="left",padx=10,pady=10)
#clearButton = Button(root,text="Clear",command=calculate)
#clearButton.pack(side="left",padx=30,pady=10)
root.mainloop()

如果端口之间的距离在5像素以内,则它们将对齐。(对于超过两个闸门的情况,这一点目前并不十分有效。)

我没有完整的答案,但我有一个可行的概念。在每个与门输入/输出端口的末端创建一个额外的画布行项目(1像素大小)。给这些项目一个类似“输入”“输出”的标记。移动闸门时,检查闸门的任何输入是否接近另一闸门的输出。如果两者之间的距离为零,则有一个连接。如果项目与另一个项目的距离在几个像素以内,也可以进行项目“捕捉”。
#Determine if we have an overlap between an input and an output
for item in canvas.find_all():
    tags = canvas.gettags(item)
    if tag in tags:
        if 'input' in tags:
            #current item is an input of the moved object
            #Get the items coordinates
            coords = canvas.coords(item)
            #Find if we overlap with other objects
            closest = canvas.find_overlapping(coords[0]-5,coords[1]-5,coords[2]+5,coords[3]+5)
            for closest_item in closest:
                closest_tags = canvas.gettags(closest_item)
                if 'output' in closest_tags:
                    #If we overlap with another object, print connected and the appropriate tags
                    print("connected", closest_tags, "-", tag)
                    connected_coords = canvas.coords(closest_item)
                    snapx = coords[0] - connected_coords[0]
                    snapy = coords[1] - connected_coords[1]
                    canvas.move(tag, -snapx, -snapy)