From b1bac1dda07ff3118dabf105f736b1c180681ea7 Mon Sep 17 00:00:00 2001 From: Huy Pham <42948410+hpham@users.noreply.github.com> Date: Thu, 26 Sep 2019 16:05:57 -0700 Subject: [PATCH] progress on core toolbar --- coretk/coretk/OVS.gif | Bin 0 -> 744 bytes coretk/coretk/app.py | 176 +------- coretk/coretk/coretoolbar.py | 602 ++++++++++++++++---------- coretk/coretk/document-properties.gif | Bin 0 -> 635 bytes coretk/coretk/host.gif | Bin 0 -> 1189 bytes coretk/coretk/mdr.gif | Bin 0 -> 1276 bytes coretk/coretk/observe.gif | Bin 0 -> 1149 bytes coretk/coretk/pc.gif | Bin 0 -> 1300 bytes coretk/coretk/plot.gif | Bin 0 -> 265 bytes coretk/coretk/router_green.gif | Bin 0 -> 753 bytes coretk/coretk/run.gif | Bin 0 -> 324 bytes coretk/coretk/stop.gif | Bin 0 -> 1204 bytes coretk/coretk/toolbaraction.py | 17 + coretk/coretk/twonode.gif | Bin 0 -> 220 bytes 14 files changed, 393 insertions(+), 402 deletions(-) create mode 100755 coretk/coretk/OVS.gif create mode 100644 coretk/coretk/document-properties.gif create mode 100644 coretk/coretk/host.gif create mode 100644 coretk/coretk/mdr.gif create mode 100644 coretk/coretk/observe.gif create mode 100644 coretk/coretk/pc.gif create mode 100644 coretk/coretk/plot.gif create mode 100644 coretk/coretk/router_green.gif create mode 100644 coretk/coretk/run.gif create mode 100644 coretk/coretk/stop.gif create mode 100644 coretk/coretk/toolbaraction.py create mode 100644 coretk/coretk/twonode.gif diff --git a/coretk/coretk/OVS.gif b/coretk/coretk/OVS.gif new file mode 100755 index 0000000000000000000000000000000000000000..38fcbb2ea684f2cb3724f55bb668d66dd952ee4d GIT binary patch literal 744 zcmVJ9wZvc%wRbpgMV>J9(izdZ9gfp+0+}KYOA*e5OBqqdk75L4Bk` zeWOBtq(FhHMS!M3gR4h^r$~aQNrI?Dg|0+}u0w{dOogdTg{n`7s!xckMvAgji>+0Q zu1SuzRgA7lkGD#Xw@Q$=SB#%r9qZk@Ytp1W|LyjZ2mSf$H#qQ6_I&0DF?cci~~ zrNDcq!F#8|eW=5Ks>Fe;#fPuQh_T6uvdNFN%aggzn!VDVz|)|@)uF=GrpDN($JnUI z*{jOhtjpW3%-prm-?-G_xzypg)Z)9<;=R}7%*@Qp%*@Qp%*@QpA^8LW3IKlqEC2ui z03ZMs000O6fPaF6goTEOh=dv*jE#jucwYQHYIwy=OOkz4Hj~p>W&4i3Z zU|?EVaBDeOZhEkLdR2@d7~9=~8y-G!bar@qcWq-WUF1-iLJ&x!2p8np`UC026(iCh zJzDS}A-9DYGIZ!5v5|<6A4!l-8|AaEc70|*i*d`R)429F;{oItU%<%@ul z7Q3Zf+45z~nKf_b+}ZP|Np6FNvUCYkCQX|-b@KEHbQ>Y5MXMskx^$~ki(gevHEK0! zR;ET=O%?)6_2^ZlTAP-%V2Cc;v3TMBba2S8*t>7d8bD;&uG_Lr69G_J06~HV5GGUz aLDL40AWED>vBKp`qSL5Tt6ohg5CA)88DCBS literal 0 HcmV?d00001 diff --git a/coretk/coretk/app.py b/coretk/coretk/app.py index 37e51aff..43273462 100644 --- a/coretk/coretk/app.py +++ b/coretk/coretk/app.py @@ -17,15 +17,7 @@ class Application(tk.Frame): self.create_widgets() def load_images(self): - # Images.load("switch", "switch.png") Images.load("core", "core-icon.png") - Images.load("start", "start.gif") - Images.load("switch", "lanswitch.gif") - Images.load("marker", "marker.gif") - Images.load("router", "router.gif") - Images.load("select", "select.gif") - Images.load("link", "link.gif") - Images.load("hub", "hub.gif") def setup_app(self): self.master.title("CORE") @@ -41,176 +33,14 @@ class Application(tk.Frame): core_menu.create_core_menubar() self.master.config(menu=self.menubar) - # TODO clean up this code - def create_network_layer_node( - self, edit_frame, radio_value, hub_image, switch_image - ): - menu_button = tk.Menubutton( - edit_frame, - direction=tk.RIGHT, - image=hub_image, - width=32, - height=32, - relief=tk.RAISED, - ) - # menu_button.grid() - menu_button.menu = tk.Menu(menu_button) - menu_button["menu"] = menu_button.menu - - menu_button.menu.add_radiobutton( - image=hub_image, variable=radio_value, value=7, indicatoron=False - ) - menu_button.menu.add_radiobutton( - image=switch_image, variable=radio_value, value=8, indicatoron=False - ) - menu_button.pack(side=tk.TOP, pady=1) - self.master.update() - print(menu_button.winfo_rootx(), menu_button.winfo_rooty()) - # print(menu_button.winfo_width(), menu_button.winfo_height()) - # print(self.master.winfo_height()) - option_frame = tk.Frame(self.master) - - switch_button = tk.Button(option_frame, image=switch_image, width=32, height=32) - switch_button.pack(side=tk.LEFT, pady=1) - hub_button = tk.Button(option_frame, image=hub_image, width=32, height=32) - hub_button.pack(side=tk.LEFT, pady=1) - print("Place the button") - print(menu_button.winfo_rootx(), menu_button.winfo_rooty()) - option_frame.place( - x=menu_button.winfo_rootx() + 33, y=menu_button.winfo_rooty() - 117 - ) - self.update() - - print("option frame: " + str(option_frame.winfo_rooty())) - print("option frame x: " + str(option_frame.winfo_rootx())) - - print("frame dimension: " + str(option_frame.winfo_height())) - print("button height: " + str(hub_button.winfo_rooty())) - - # TODO switch 177 into the rooty of the selection tool, retrieve image in here - def draw_options(self, main_button, radio_value): - hub_image = Images.get("hub") - switch_image = Images.get("switch") - option_frame = tk.Frame(self.master) - - switch_button = tk.Radiobutton( - option_frame, - image=switch_image, - width=32, - height=32, - variable=radio_value, - value=7, - indicatoron=False, - ) - switch_button.pack(side=tk.LEFT, pady=1) - hub_button = tk.Radiobutton( - option_frame, - image=hub_image, - width=32, - height=32, - variable=radio_value, - value=8, - indicatoron=False, - ) - hub_button.pack(side=tk.LEFT, pady=1) - self.master.update() - option_frame.place( - x=main_button.winfo_rootx() + 35 - self.selection_button.winfo_rootx(), - y=main_button.winfo_rooty() - self.selection_button.winfo_rooty(), - ) - - def create_network_layer_node_attempt2(self, edit_frame, radio_value): - hub_image = Images.get("hub") - main_button = tk.Radiobutton( - edit_frame, image=hub_image, width=32, height=32, indicatoron=False - ) - main_button.pack(side=tk.TOP, pady=1) - self.draw_options(main_button, radio_value) - def create_widgets(self): - - """ - select_image = Images.get("select") - start_image = Images.get("start") - link_image = Images.get("link") - router_image = Images.get("router") - hub_image = Images.get("hub") - switch_image = Images.get("switch") - marker_image = Images.get("marker") - """ - edit_frame = tk.Frame(self) edit_frame.pack(side=tk.LEFT, fill=tk.Y, ipadx=2, ipady=2) - core_editbar = CoreToolbar(self.master, edit_frame) + exec_frame = tk.Frame(edit_frame) + exec_frame.pack(side=tk.TOP) + core_editbar = CoreToolbar(self.master, edit_frame, exec_frame, self.menubar) core_editbar.create_toolbar() - """ - radio_value = tk.IntVar() - self.selection_button = tk.Radiobutton( - edit_frame, - indicatoron=False, - variable=radio_value, - value=1, - width=32, - height=32, - image=select_image, - ) - self.selection_button.pack(side=tk.TOP, pady=1) - b = tk.Radiobutton( - edit_frame, - indicatoron=False, - variable=radio_value, - value=2, - width=32, - height=32, - image=start_image, - ) - b.pack(side=tk.TOP, pady=1) - b = tk.Radiobutton( - edit_frame, - indicatoron=False, - variable=radio_value, - value=3, - width=32, - height=32, - image=link_image, - ) - b.pack(side=tk.TOP, pady=1) - b = tk.Radiobutton( - edit_frame, - indicatoron=False, - variable=radio_value, - value=4, - width=32, - height=32, - image=router_image, - ) - b.pack(side=tk.TOP, pady=1) - - b = tk.Radiobutton( - edit_frame, - indicatoron=False, - variable=radio_value, - value=5, - width=32, - height=32, - image=hub_image, - ) - b.pack(side=tk.TOP, pady=1) - b = tk.Radiobutton( - edit_frame, - indicatoron=False, - variable=radio_value, - value=6, - width=32, - height=32, - image=marker_image, - ) - b.pack(side=tk.TOP, pady=1) - - #self.create_network_layer_node(edit_frame, radio_value, hub_image, switch_image) - self.create_network_layer_node_attempt2(edit_frame, radio_value) - """ self.canvas = CanvasGraph( self, background="#cccccc", scrollregion=(0, 0, 1000, 1000) ) diff --git a/coretk/coretk/coretoolbar.py b/coretk/coretk/coretoolbar.py index e66bbcc6..44b4f472 100644 --- a/coretk/coretk/coretoolbar.py +++ b/coretk/coretk/coretoolbar.py @@ -1,6 +1,7 @@ import logging import tkinter as tk +import coretk.toolbaraction as tbaction from coretk.images import Images @@ -9,8 +10,7 @@ class CoreToolbar(object): Core toolbar class """ - # TODO Temporarily have a radio_value instance here, might have to include the run frame - def __init__(self, master, edit_frame): + def __init__(self, master, edit_frame, exec_frame, menubar): """ Create a CoreToolbar instance @@ -18,15 +18,25 @@ class CoreToolbar(object): """ self.master = master self.edit_frame = edit_frame + self.execution_frame = exec_frame + self.menubar = menubar self.radio_value = tk.IntVar() + self.exec_radio_value = tk.IntVar() + + # button dimension + self.width = 32 + self.height = 32 # Used for drawing the horizontally displayed menu items for network-layer nodes and link-layer node self.selection_tool_button = None + # Reference to the option menus self.link_layer_option_menu = None self.marker_option_menu = None self.network_layer_option_menu = None + self.execution_frame = None + def load_toolbar_images(self): """ Load the images that appear in core toolbar @@ -47,23 +57,70 @@ class CoreToolbar(object): Images.load("oval", "oval.gif") Images.load("rectangle", "rectangle.gif") Images.load("text", "text.gif") + Images.load("host", "host.gif") + Images.load("pc", "pc.gif") + Images.load("mdr", "mdr.gif") + Images.load("prouter", "router_green.gif") + Images.load("ovs", "OVS.gif") + Images.load("editnode", "document-properties.gif") + Images.load("run", "run.gif") + Images.load("plot", "plot.gif") + Images.load("twonode", "twonode.gif") + Images.load("stop", "stop.gif") + Images.load("observe", "observe.gif") - def hide_all_option_menu_frames(self): + def destroy_previous_frame(self): """ - Hide any option menu frame that is displayed on screen so that when a new option menu frame is drawn, only - one frame is displayed + Destroy any extra frame from previous before drawing a new one :return: nothing """ - if self.marker_option_menu: - self.marker_option_menu.place_forget() - if self.link_layer_option_menu: - self.link_layer_option_menu.place_forget() - if self.network_layer_option_menu: - self.network_layer_option_menu.place_forget() + if ( + self.network_layer_option_menu + and self.network_layer_option_menu.winfo_exists() + ): + self.network_layer_option_menu.destroy() + if self.link_layer_option_menu and self.link_layer_option_menu.winfo_exists(): + self.link_layer_option_menu.destroy() + if self.marker_option_menu and self.marker_option_menu.winfo_exists(): + self.marker_option_menu.destroy() + + def create_buttons(self, img, func, frame, main_button): + """ + Create button and put it on the frame + + :param PIL.Image img: button image + :param func: the command that is executed when button is clicked + :param tkinter.Frame frame: frame that contains the button + :param tkinter.Radiobutton main_button: main button + :return: nothing + """ + button = tk.Button(frame, width=self.width, height=self.height, image=img) + button.pack(side=tk.LEFT, pady=1) + button.bind("", lambda mb: func(main_button)) + + def bind_widgets_before_frame_hide(self, frame): + """ + Bind the widgets to a left click, when any of the widgets is clicked, the menu option frame is destroyed before + any further action is performed + + :param tkinter.Frame frame: the frame to be destroyed + :return: nothing + """ + self.menubar.bind("", lambda e: frame.destroy()) + self.master.bind("", lambda e: frame.destroy()) + + def unbind_widgets_after_frame_hide(self): + """ + Unbind the widgets to make sure everything works normally again after the menu option frame is destroyed + + :return: nothing + """ + self.master.unbind("") + self.menubar.unbind("Button-1>") def click_selection_tool(self): - logging.debug("Click selection tool") + logging.debug("Click SELECTION TOOL") def create_selection_tool_button(self): """ @@ -77,13 +134,19 @@ class CoreToolbar(object): indicatoron=False, variable=self.radio_value, value=1, - width=32, - height=32, + width=self.width, + height=self.height, image=selection_tool_image, - command=self.click_selection_tool, + command=lambda: self.click_selection_tool(), ) self.selection_tool_button.pack(side=tk.TOP, pady=1) + def click_start_stop_session_tool(self): + logging.debug("Click START STOP SESSION button") + for i in self.edit_frame.winfo_children(): + i.destroy() + self.create_runtime_tool_bar() + def create_start_stop_session_button(self): """ Create start stop session button @@ -96,9 +159,10 @@ class CoreToolbar(object): indicatoron=False, variable=self.radio_value, value=2, - width=32, - height=32, + width=self.width, + height=self.height, image=start_image, + command=lambda: self.click_start_stop_session_tool(), ) start_button.pack(side=tk.TOP, pady=1) @@ -114,12 +178,100 @@ class CoreToolbar(object): indicatoron=False, variable=self.radio_value, value=3, - width=32, - height=32, + width=self.width, + height=self.height, image=link_image, + command=lambda: tbaction.click_link_tool(), ) link_button.pack(side=tk.TOP, pady=1) + def pick_router(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("router")) + logging.debug("Pick router option") + + def pick_host(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("host")) + logging.debug("Pick host option") + + def pick_pc(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("pc")) + logging.debug("Pick PC option") + + def pick_mdr(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("mdr")) + logging.debug("Pick MDR option") + + def pick_prouter(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("prouter")) + logging.debug("Pick prouter option") + + def pick_ovs(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("ovs")) + logging.debug("Pick OVS option") + + def pick_editnode(self, main_button): + self.network_layer_option_menu.destroy() + main_button.configure(image=Images.get("editnode")) + logging.debug("Pick editnode option") + + def draw_network_layer_options(self, network_layer_button): + """ + Draw the options for network-layer button + + :param tkinter.Radiobutton network_layer_button: network-layer button + :return: nothing + """ + # create a frame and add buttons to it + self.destroy_previous_frame() + option_frame = tk.Frame(self.master) + img_list = [ + Images.get("router"), + Images.get("host"), + Images.get("pc"), + Images.get("mdr"), + Images.get("prouter"), + Images.get("ovs"), + Images.get("editnode"), + ] + func_list = [ + self.pick_router, + self.pick_host, + self.pick_pc, + self.pick_mdr, + self.pick_prouter, + self.pick_ovs, + self.pick_editnode, + ] + for i in range(len(img_list)): + self.create_buttons( + img_list[i], func_list[i], option_frame, network_layer_button + ) + + # place frame at a calculated position as well as keep a reference of that frame + _x = ( + network_layer_button.winfo_rootx() + - self.selection_tool_button.winfo_rootx() + + 40 + ) + _y = ( + network_layer_button.winfo_rooty() + - self.selection_tool_button.winfo_rooty() + - 1 + ) + option_frame.place(x=_x, y=_y) + self.network_layer_option_menu = option_frame + + # destroy the frame before any further actions on other widgets + self.bind_widgets_before_frame_hide(option_frame) + option_frame.wait_window(option_frame) + self.unbind_widgets_after_frame_hide() + def create_network_layer_button(self): """ Create network layer button @@ -132,140 +284,86 @@ class CoreToolbar(object): indicatoron=False, variable=self.radio_value, value=4, - width=32, - height=32, + width=self.width, + height=self.height, image=router_image, + command=lambda: self.draw_network_layer_options(network_layer_button), ) network_layer_button.pack(side=tk.TOP, pady=1) - def pick_hub(self, frame, main_button): - frame.place_forget() + def pick_hub(self, main_button): + self.link_layer_option_menu.destroy() main_button.configure(image=Images.get("hub")) - if self.radio_value.get() != 5: - self.radio_value.set(5) logging.debug("Pick link-layer node HUB") - def pick_switch(self, frame, main_button): - frame.place_forget() + def pick_switch(self, main_button): + self.link_layer_option_menu.destroy() main_button.configure(image=Images.get("switch")) - if self.radio_value.get() != 5: - self.radio_value.set(5) logging.debug("Pick link-layer node SWITCH") - def pick_wlan(self, frame, main_button): - frame.place_forget() + def pick_wlan(self, main_button): + self.link_layer_option_menu.destroy() main_button.configure(image=Images.get("wlan")) - if self.radio_value.get() != 5: - self.radio_value.set(5) logging.debug("Pick link-layer node WLAN") - def pick_rj45(self, frame, main_button): - frame.place_forget() + def pick_rj45(self, main_button): + self.link_layer_option_menu.destroy() main_button.configure(image=Images.get("rj45")) - if self.radio_value.get() != 5: - self.radio_value.set(5) logging.debug("Pick link-layer node RJ45") - def pick_tunnel(self, frame, main_button): - frame.place_forget() + def pick_tunnel(self, main_button): + self.link_layer_option_menu.destroy() main_button.configure(image=Images.get("tunnel")) - if self.radio_value.get() != 5: - self.radio_value.set(5) logging.debug("Pick link-layer node TUNNEL") def draw_link_layer_options(self, link_layer_button): - # TODO if other buttons are press or nothing is pressed or the button is pressed but frame is forgotten/hidden + """ + Draw the options for link-layer button + + :param tkinter.RadioButton link_layer_button: link-layer button + :return: nothing + """ + # create a frame and add buttons to it + self.destroy_previous_frame() option_frame = tk.Frame(self.master) - current_choice = self.radio_value.get() - self.hide_all_option_menu_frames() - if ( - current_choice == 0 - or current_choice != 5 - or (current_choice == 5 and not option_frame.winfo_manager()) - ): - hub_image = Images.get("hub") - switch_image = Images.get("switch") - wlan_image = Images.get("wlan") - rj45_image = Images.get("rj45") - tunnel_image = Images.get("tunnel") + img_list = [ + Images.get("hub"), + Images.get("switch"), + Images.get("wlan"), + Images.get("rj45"), + Images.get("tunnel"), + ] + func_list = [ + self.pick_hub, + self.pick_switch, + self.pick_wlan, + self.pick_rj45, + self.pick_tunnel, + ] + for i in range(len(img_list)): + self.create_buttons( + img_list[i], func_list[i], option_frame, link_layer_button + ) - hub_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=7, - width=32, - height=32, - image=hub_image, - command=lambda: self.pick_hub( - frame=option_frame, main_button=link_layer_button - ), - ) - hub_button.pack(side=tk.LEFT, pady=1) - switch_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=8, - width=32, - height=32, - image=switch_image, - command=lambda: self.pick_switch( - frame=option_frame, main_button=link_layer_button - ), - ) - switch_button.pack(side=tk.LEFT, pady=1) - wlan_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=9, - width=32, - height=32, - image=wlan_image, - command=lambda: self.pick_wlan( - frame=option_frame, main_button=link_layer_button - ), - ) - wlan_button.pack(side=tk.LEFT, pady=1) - rj45_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=10, - width=32, - height=32, - image=rj45_image, - command=lambda: self.pick_rj45( - frame=option_frame, main_button=link_layer_button - ), - ) - rj45_button.pack(side=tk.LEFT, pady=1) - tunnel_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=11, - width=32, - height=32, - image=tunnel_image, - command=lambda: self.pick_tunnel( - frame=option_frame, main_button=link_layer_button - ), - ) - tunnel_button.pack(side=tk.LEFT, pady=1) + # place frame at a calculated position as well as keep a reference of the frame + _x = ( + link_layer_button.winfo_rootx() + - self.selection_tool_button.winfo_rootx() + + 40 + ) + _y = ( + link_layer_button.winfo_rooty() + - self.selection_tool_button.winfo_rooty() + - 1 + ) + option_frame.place(x=_x, y=_y) + self.master.update() + self.link_layer_option_menu = option_frame - _x = ( - link_layer_button.winfo_rootx() - - self.selection_tool_button.winfo_rootx() - + 33 - ) - _y = ( - link_layer_button.winfo_rooty() - - self.selection_tool_button.winfo_rooty() - ) - option_frame.place(x=_x, y=_y) - self.link_layer_option_menu = option_frame + # destroy the frame before any further actions on other widgets + self.bind_widgets_before_frame_hide(option_frame) + option_frame.wait_window(option_frame) + self.unbind_widgets_after_frame_hide() def create_link_layer_button(self): """ @@ -279,118 +377,70 @@ class CoreToolbar(object): indicatoron=False, variable=self.radio_value, value=5, - width=32, - height=32, + width=self.width, + height=self.height, image=hub_image, command=lambda: self.draw_link_layer_options(link_layer_button), ) link_layer_button.pack(side=tk.TOP, pady=1) - def pick_marker(self, frame, main_button): - frame.place_forget() + def pick_marker(self, main_button): + self.marker_option_menu.destroy() main_button.configure(image=Images.get("marker")) - if self.radio_value.get() != 6: - self.radio_value.set(6) - logging.debug("Pick marker") + logging.debug("Pick MARKER") + return "break" - def pick_oval(self, frame, main_button): - frame.place_forget() + def pick_oval(self, main_button): + self.marker_option_menu.destroy() main_button.configure(image=Images.get("oval")) - if self.radio_value.get() != 6: - self.radio_value.set(6) - logging.debug("Pick frame") + logging.debug("Pick OVAL") - def pick_rectangle(self, frame, main_button): - frame.place_forget() + def pick_rectangle(self, main_button): + self.marker_option_menu.destroy() main_button.configure(image=Images.get("rectangle")) - if self.radio_value.get() != 6: - self.radio_value.set(6) - logging.debug("Pick rectangle") + logging.debug("Pick RECTANGLE") - def pick_text(self, frame, main_button): - frame.place_forget() + def pick_text(self, main_button): + self.marker_option_menu.destroy() main_button.configure(image=Images.get("text")) - if self.radio_value.get() != 6: - self.radio_value.set(6) - logging.debug("Pick text") + logging.debug("Pick TEXT") def draw_marker_options(self, main_button): - # TODO if no button pressed, or other buttons being pressed, or marker button is being pressed but no frame is drawn - option_frame = tk.Frame(self.master) - current_choice = self.radio_value.get() - self.hide_all_option_menu_frames() - # TODO might need to find better way to write this, or might not - if ( - current_choice == 0 - or current_choice != 6 - or (current_choice == 6 and not option_frame.winfo_manager()) - ): - marker_image = Images.get("marker") - oval_image = Images.get("oval") - rectangle_image = Images.get("rectangle") - text_image = Images.get("text") + """ + Draw the options for marker button - marker_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=12, - width=32, - height=32, - image=marker_image, - command=lambda: self.pick_marker( - frame=option_frame, main_button=main_button - ), - ) - marker_button.pack(side=tk.LEFT, pady=1) - oval_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=13, - width=32, - height=32, - image=oval_image, - command=lambda: self.pick_oval( - frame=option_frame, main_button=main_button - ), - ) - oval_button.pack(side=tk.LEFT, pady=1) - rectangle_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=14, - width=32, - height=32, - image=rectangle_image, - command=lambda: self.pick_rectangle( - frame=option_frame, main_button=main_button - ), - ) - rectangle_button.pack(side=tk.LEFT, pady=1) - text_button = tk.Radiobutton( - option_frame, - indicatoron=False, - variable=self.radio_value, - value=15, - width=32, - height=32, - image=text_image, - command=lambda: self.pick_text( - frame=option_frame, main_button=main_button - ), - ) - text_button.pack(side=tk.LEFT, pady=1) - self.master.update() - _x = ( - main_button.winfo_rootx() - - self.selection_tool_button.winfo_rootx() - + 33 - ) - _y = main_button.winfo_rooty() - self.selection_tool_button.winfo_rooty() - option_frame.place(x=_x, y=_y) - self.marker_option_menu = option_frame + :param tkinter.Radiobutton main_button: the main button + :return: nothing + """ + # create a frame and add buttons to it + self.destroy_previous_frame() + option_frame = tk.Frame(self.master) + img_list = [ + Images.get("marker"), + Images.get("oval"), + Images.get("rectangle"), + Images.get("text"), + ] + func_list = [ + self.pick_marker, + self.pick_oval, + self.pick_rectangle, + self.pick_text, + ] + for i in range(len(img_list)): + self.create_buttons(img_list[i], func_list[i], option_frame, main_button) + + # place the frame at a calculated position as well as keep a reference of that frame + _x = main_button.winfo_rootx() - self.selection_tool_button.winfo_rootx() + 40 + _y = main_button.winfo_rooty() - self.selection_tool_button.winfo_rooty() - 1 + option_frame.place(x=_x, y=_y) + self.master.update() + self.marker_option_menu = option_frame + + # destroy the frame before any further actions on other widgets + self.bind_widgets_before_frame_hide(option_frame) + option_frame.wait_window(option_frame) + self.unbind_widgets_after_frame_hide() def create_marker_button(self): """ @@ -404,13 +454,30 @@ class CoreToolbar(object): indicatoron=False, variable=self.radio_value, value=6, - width=32, - height=32, + width=self.width, + height=self.height, image=marker_image, command=lambda: self.draw_marker_options(marker_main_button), ) marker_main_button.pack(side=tk.TOP, pady=1) + def create_selection_tool_button_for_exec(self): + for i in self.edit_frame.winfo_children(): + i.destroy() + selection_tool_image = Images.get("select") + for i in range(7): + button = tk.Radiobutton( + self.edit_frame, + indicatoron=False, + variable=self.radio_value, + value=1, + width=self.width, + height=self.height, + image=selection_tool_image, + command=lambda: tbaction.click_selection_tool(), + ) + button.pack(side=tk.TOP, pady=1) + def create_toolbar(self): self.load_toolbar_images() self.create_selection_tool_button() @@ -419,3 +486,80 @@ class CoreToolbar(object): self.create_network_layer_button() self.create_link_layer_button() self.create_marker_button() + + def create_radio_button(self, frame, image, func, value): + button = tk.Radiobutton( + frame, + indicatoron=False, + width=self.width, + height=self.height, + image=image, + value=value, + variable=self.exec_radio_value, + ) + button.pack(side=tk.TOP, pady=1) + + def create_regular_button(self, frame, image, func): + button = tk.Button( + frame, width=self.width, height=self.height, image=image, command=func + ) + button.pack(side=tk.TOP, pady=1) + + def create_observe_button(self): + menu_button = tk.Menubutton( + self.edit_frame, + image=Images.get("observe"), + width=self.width, + height=self.height, + direction=tk.RIGHT, + ) + menu_button.menu = tk.Menu(menu_button, tearoff=0) + menu_button["menu"] = menu_button.menu + menu_button.pack(side=tk.TOP, pady=1) + + menu_button.menu.add_command(label="None") + menu_button.menu.add_command(label="processes") + menu_button.menu.add_command(label="ifconfig") + menu_button.menu.add_command(label="IPv4 routes") + menu_button.menu.add_command(label="IPv6 routes") + menu_button.menu.add_command(label="OSPFv2 neighbors") + menu_button.menu.add_command(label="OSPFv3 neighbors") + menu_button.menu.add_command(label="Listening sockets") + menu_button.menu.add_command(label="IPv4 MFC entries") + menu_button.menu.add_command(label="IPv6 MFC entries") + menu_button.menu.add_command(label="firewall rules") + menu_button.menu.add_command(label="IPSec policies") + menu_button.menu.add_command(label="docker logs") + menu_button.menu.add_command(label="OSPFv3 MDR level") + menu_button.menu.add_command(label="PIM neighbors") + menu_button.menu.add_command(label="Edit...") + + def click_run_button(self): + logging.debug("Click on RUN button") + + def click_stop_button(self): + logging.debug("Click on STOP button ") + for i in self.edit_frame.winfo_children(): + i.destroy() + self.create_toolbar() + + def create_runtime_tool_bar(self): + self.create_radio_button( + self.edit_frame, Images.get("select"), self.click_selection_tool, 1 + ) + self.create_regular_button( + self.edit_frame, Images.get("stop"), self.click_stop_button + ) + self.create_observe_button() + self.create_radio_button( + self.edit_frame, Images.get("plot"), self.click_selection_tool, 2 + ) + self.create_radio_button( + self.edit_frame, Images.get("marker"), self.click_selection_tool, 3 + ) + self.create_radio_button( + self.edit_frame, Images.get("twonode"), self.click_selection_tool, 4 + ) + self.create_regular_button( + self.edit_frame, Images.get("run"), self.click_run_button + ) diff --git a/coretk/coretk/document-properties.gif b/coretk/coretk/document-properties.gif new file mode 100644 index 0000000000000000000000000000000000000000..732d8436455ba607ff30774ef83faa434789f775 GIT binary patch literal 635 zcmZ?wbhEHb6krfwI9A3`UtizZ-QL^V)6>`4+Ydxt6Z*URCUj4n)H`Wv|CDJHr_Go& zZN}v3v!=|LJ$2^nX|v}}pFMZR-1#%-Eu6hz(VT@#<}O+?Z}GAP%a$!&x_sgCm5Z0J zTCxI&Rxe$-dg-b)D^{&twiXE1tzNrs?b`LL*REf)X2YuWo7QaFym8yMZ98^v+r4}D z-hI3FAKZQ9*uj%$j-Nbx?EKkN7cQN-eEIUFs~4`{xO(Hp^_#bD+`N6`*6o|O?p(Wh z_u4HGx_egDy&`;YEE0HVit9zMSJ`0=BM zPwqW>djIj$2algUeDdt!vuDqqJb(1!`IDzF9=~}0?D@;5FJHcR`SRtfmoHwweE#Ou zi?^>|zJ2}b^_!P(-oASC_Vv5>Z$Eu}|LN1G&!0Yi`}Xzw_wPTxfBW&{`%fVH2}D1B z{`&dr*Uvvd@b}MOAo%z99|-;X_y6C25W)u(f3h%gG1N2YFaQB4P8is4G}PBC$jQn` zOH0W%^)$&PmQ9?P6RzIdBv~967UJ*YYhIu;UA!+K3@N%$caBBCo?vDZnK?>>} z4H6mGRzwyX@-nz_KC4-2cu1l_BwJ^i<gzK44%5h8Cn(&TO1gfn3+!O Kwon&fum%8seSYfz literal 0 HcmV?d00001 diff --git a/coretk/coretk/host.gif b/coretk/coretk/host.gif new file mode 100644 index 0000000000000000000000000000000000000000..5bd60ae3d34d9bcd8be206ba2a8a701b19aea319 GIT binary patch literal 1189 zcmb``30Kkw008hm262dT`d1VcH7ko8t5<8Y=8+H2yze8AmB-d>TJ62nYg4kad?v4& zM~5QL6hp;kPN#X`g=i`SsGx=l2;OM*vP`yphyA|8&&!8?{OcqFKn51n00031BLEHn zNC*Id0!Ap-3M58&meYM}^Nii1^A`;HUW+aDPOb$JlayBa^A~QAaVrt~&^ysVU zu~#pg$<9c~y!cbrrA)@p=L&u~%ef84YDQ6|53A zyOhN)Z>=og)RebX6*gBFKC7*0t$xCN#;)aZI%*#_*0XpGPkXscKDVf^?p}MtlfL?r z{)STi^M``Q$GuIDyP7#eFUp6TS;FS0!nVrczj^H)ZQ`~nQ9F0AF*Tvx5@_UB?C>0{ufgN&9cE}$zZ!w_;Nz{*UVt6WVly6 z(m6TOEfNXjqx|X7mt*2l#aPdzNccwFDU}Q)4o~IY1S8%i#nxVJG-+|;J&gZw=hEE2=`yIo!;s0j01%;ph13(4-_1_5q zu>%;8WN#j;`#OSvdLYVS@EK^2sT%CutgEd(_JPmM)a$tvWO-8!ZZMjb+;`VMC~55O zZ8Nu)t;HMEVqV7i7$TIA?NOFFUVpL&d_}6G;!tO9Hwt5&FH99hSJIbFigv>uofpWs zil%hc_f_o8f&6TSug$RC!irVvj|0^3kD=;Q-S+#9SWcSL6V#M4uup%lA`x$XVv5UD z|6pDlk~f#;>(=$uM(SdIU&W(eXoPydho|^6LAH- z5a8TqvnWKEOTGL2@5uXX*GJ%NS|CpVgB{s(IKY-cv>&v9ThKhI(04%|NGmAs4*3eV zF&DNkP4DBLKw}yiL%OoOERP)rdMHmXC1Xvn?aG|Pp=5wzTGz6H@;FVQb$gC}yVs literal 0 HcmV?d00001 diff --git a/coretk/coretk/mdr.gif b/coretk/coretk/mdr.gif new file mode 100644 index 0000000000000000000000000000000000000000..d6762f6500828ead06fb73c7a9061165ccdef85b GIT binary patch literal 1276 zcmb``jXTo`0KoCzh-N62mQF9`y{bhS8&Di5W%q3E|!j5ZXj{V1dP z7^69zTAohjVrksC>#Y$b%3K=zJhSp5qbmMJTLzOyzDB>y-XS*imde`bawS84 zmw2%6!-V0cL*B2(Jh`PG1(ilOjJz+z~L3DWyE~ zO;xt!+NFMoy%loArqJ-l_Jm(**X)msz`k|c5+7%ztE@5^S_rHsgwwkfx+OT=Z$;za z1?W%IUsZdN*kB!mhEtzXfV>X7ht>Edn=uv}N8`!@xG`X6rD(8m2lfq+q_=}^$LNJe zrch2W6c0TaQtZgz-JcRb=$y)|Wj z-BiLi_^0&q5I9?(v7Hx8apXh0#<03WyT?yj39`SYQ1$*P0GqVK6ELG(0k9Ks?dS+d z3pf%;4@qAVb9%@ro@T;!2e%9u$e;%Wd0%mEb+qw`b4TNcjXCa=mAQUIuzk0S85EZ* zBUtH@1DtHVzSAt$x4=OWCFxq)a-ePq&RPZ!3`gHsVKo}*{{&+f1UUU>gn=xwL|_AW r4z4Sh`#3ytbr^3Q6*$HAfFoFup6oRk3ar@WthBAq6&LC31nl__5JiQ; literal 0 HcmV?d00001 diff --git a/coretk/coretk/observe.gif b/coretk/coretk/observe.gif new file mode 100644 index 0000000000000000000000000000000000000000..6b66e7305f35484095a2182ed828c6507c72a746 GIT binary patch literal 1149 zcmd_pYfn=L0LJlylbbZAPQ->d0;0q*%+PGvh{hCQEG*WwP@oJp1|%#lOP0+=yD9^E zJMC#%P#A&~sl5%f$fdVaENf{gXltbuDYVeS>4mnZW77@Ay;;_Njy?H(f#=2lWZqG%4!O^wyx&OriRAmhAY&|RN9pvX;*32s2z+p0&S8&Q(U~J z`1HDh)T$s}R}x#5q*i6+PpZl`6}e4S)vl^;SJiZ=Yv^hUU0qAp)G{=mF*Nl|O&t@i zXTqPe;4j#41E_80z%3B`6)#3hlP=O(9c(TGgqR=%a(E!f5Ddi(3PnRA>5yz#qJh;~oqAfY1LaE{BhQ%km%&jd zZ)}wU1Re`@`9oJa7`GpO_2 znf6ZT%y*~P#QJrKeqCd6rkk^g3>#8|2exj&Pd3Cen=<33%!K@ELWXCN zky+%P*>~UUlh66(^ZwC!|AUxE{;{~g*yF%>j3qE(2~5TX71p5gNl<0m(mag`!3!a6 zj6F1E4?SEA|F#s-FGUP<7R!Rey5O)mJx^D>3o)zS8Hdlb>yO>g zpS$Rb*U=ZRf&bZZ{@I%V0OLSG{CB(wAmv}6G4)7z54#w5GAY0Qgx$RVR97jNeyk-K z!%n+IJ#Z+6-;>|?jPuv|H^lhNu21mKffLy5bD4QP?c|#|n0Jp8wco#gbTJ1jr?B#o zpwIZ0DDQaz=@LnV&pIoiXMa6!%xH2@H(fh#3yU%-1l+Ma#DMEE?9C(%k6MeqHBjI^ zNfj8@$s_i!;2S6J=`b1%yJ zjzYQTh5_ro()5X;@-#bkwK}khXSw%@jRar$%MOj@_Rb53* zLseZvO+&*#LsMN-TSG%fPg_?@Ti;MmUsumSSJ%+k(AdDh*umJu$k^1_)ZE0}(#*=* z(#pot+Sba}-p06XUk)~1%W z=GOL>_RhA>?vAdW&hFl>u1PZ|Pn|S<=Cnz(7R{J7eaf6Av**s7Id8$7C2Ll!TE1r8 z>UA5|uGz9@%eKuMb{yEe{n+-M+jj2Wv3bvtz5Dml;r#-+uDu;gbhD7>etiD&*~3?# zUc7q#==JB9uU|ZP^Xu`OFR$LbeE9ayleb@AzkBuk{f}4gKfQhb`t^s;?>@YJ`SI7A zk6+$@eE0U#*AJiGfBgL6)0dC$zkdJx_0xxMKfZkb{OSA8&p&)21O&UZ4U+dI^{!gd>D|h#E6iqaFl|zFQsMJyw=OWRyvJa6$Rl!U zR@l1ZMcNNJ3l}mw>9FJ}Z2q#Shs%CVOlO(ttDwnBECCWCiy96tj+>F9s9ci5+v~R4 zt(VKRlY^y$HMgRo`OM^{iN{KBDit4fo9;Yc%kk90LmM147@K$wKlQwB;JwN4(@H0| z)u(1i(xn6iz5D;z&8dl-$AS zrM*MM*<1JUic6;qwoFj+F)Y&%Z06!ucyvOES=E6-%8p~vY3;2Fi@SBUUUBj^*tDgo zN2{iU;jnU_h0_HN#u!6a(QXcBZ~bi#no@LkeR1MeOki2y)~_Pu;>N(uQq(MZ@J~>; z?!kZ+-HH+o4h+K6bT)OUvr9TM2owiQY?jkgTFfED&(h#5pQ+c>=_GGEv0Ye)C&`VO tJw%~hJ~@t1va|g8z`l6e8jtN{jVv^D?$ literal 0 HcmV?d00001 diff --git a/coretk/coretk/plot.gif b/coretk/coretk/plot.gif new file mode 100644 index 0000000000000000000000000000000000000000..3924adbf821d1cfeb34a0b9efc7e9d79041fd1df GIT binary patch literal 265 zcmV+k0rvh!Nk%w1VITk?0OJ7w0094gp6-C3?t-B1gQ4!&*x1wB`seBX=<5FI>i+8M z{_E`i?Ck#S?f&lW|9_tDA^saEV<{jqFflS9bZBKDLT_bhZf77vZ*6d4Zg~J9`2+z9 z01p5x00000AOIi$00fut$w{ldIO|=y|6nLmg=3y*s-^|GzOdO&Wo)CfRNr_0?7Wx{ z7<>(jwj&azT$&g-m(u|NL}|P#3J?fbWzrac;9XF=-EZ@i;HCisbU;vTDio=PTh2!- z4^;pSCRKfgT}KOh00w)9eM1P2UXPDMla-Z2nVfzkot>MYnWCeXpQfiYsj51xheIN= PvmP6^x45~wyAc38TK{^> literal 0 HcmV?d00001 diff --git a/coretk/coretk/router_green.gif b/coretk/coretk/router_green.gif new file mode 100644 index 0000000000000000000000000000000000000000..76e3ecd57c59ec99767f5641e701f908f09f0258 GIT binary patch literal 753 zcmV$ZwARvGsB7!0$gd`+|BqoR^Cx|C0iYY0J zDJqL9D~&5Hku5KgFE5iXF_tkhmNGJzGBlYqG@CRwn>IF_HaDF&IG;EPKS85GJf%E6r9DBULPDfMJ*GWE zq(eTZK0c^EMy5tVsX<4lNJytiLaIVQt3XMpN=&IvL#;zYu0u|$P(`stMzKamu}4#_ zRY$T%RIOG=vqwj?M@hCxSg=}Juw6^JOJB2LU$bIPyiQ`YWKF$IW3*;ZzE5SgXi&dU zP{2@9!BT3tZc@ThYq)P~xo>Q_Z*979RK-+pyK-^7bymn$R>@X$y?1rKd3C>eSj$*< zzk6EFT7krdfyIV|#)^%~l8(xhlg*iw&YG3ao0iX=n9!e@(Vw8yr=!)Xq}8jY*R816 zucz3rtJ<=#+_<#fy|v!Gw%@Eq<#>~vjA^8LW3IKlqEC2ui z03ZMs000O6fPaF6goTEOh=my(jE#=El$DGfh?9&+W>zhgGe=rwY)+0Jg^nay zZG3!fWM&|jQh9!Ub|jCOf|fFFeYa;FPI7*AUNAtGy_SqBI$bsnKeZk z1rZZ4K!FI3>S252fd&*X6#oDSAb`LD2Ng7J300IRJ9!Q{YVZ)>j z9!jK$fuo0!Bu}QqoGFqd0h>4*Jb*C40)`MMUew63L&%V$NtcEkS@R|XsZ_0E)ymZ? zSfx)g$2x_2c52nDS+{omiWDwWvQN#Ty}MSg+rDB4%@u4{ZQizg!^$i)AaK;ic-iiK ji-ij!x`Q2SKKvv~q(ODlW;XnF$?4M`P`G$4C=dWUiqcBu literal 0 HcmV?d00001 diff --git a/coretk/coretk/run.gif b/coretk/coretk/run.gif new file mode 100644 index 0000000000000000000000000000000000000000..71dcc67eddc7b829b3221ba4823a04e93c317ba9 GIT binary patch literal 324 zcmZ?wbhEHbRA5kGXkh>WMn*;!78X`kRv8%?d3kvQ0|P@tLt|rOQ&ZEBkdW~3@W#f* zzP`R`)22WfAZwX)2B~gy?XWL&6~Gx-+uY>JSuFtAW4$w*aj%1_PAOIL8t&n-yIt7K68$->CRAkUx!(gbo61M8v(>U}Ah^DZGE(+-Pd9n~wOxE_RahlU()Kf}#eGDh z*YY|kSclnhF*_f*ZL2LVvRih;gcu3Vl7L(W;oNF5dkLndh`{&>RXH)u)s9RO_M-ic zeWf|^96S<2Tyxsf7B~v9GqLh5uUZ+O;*@5-)iu^LcxTxBeY@PPj~q2OIdSsT=`&}~ Ko!3%ium%9#D0q7S literal 0 HcmV?d00001 diff --git a/coretk/coretk/stop.gif b/coretk/coretk/stop.gif new file mode 100644 index 0000000000000000000000000000000000000000..02c2866864fb955827b6af4d434a8ea03508b5a6 GIT binary patch literal 1204 zcmb```A?Gv9LMo*>GQOGO8fMnKq);bg%%10X@M4zBI6uI7|O(9f`)8t&J&IEhZ*K% z8p0H3vMt-(>;N^g83y9QrosRx$V4G+SB}zh6w0L>BIQtq|HD3c{rvguotmB!tKG*1 zE-VAE0ptL&09yeP015#11C#)q0w@Kz0PqdK&j3}M2!tvku^OOe6M=9I;5xuH0$ktZ z0aXZc!vk)j#99QYB_Y3{$So3DOF@67l5SyG9hK5R#Tq<48*uD4oq7+)?=tY;nACer z`X3y|eIItSz^mDxWAgMc(LBsFqM1&#;6w|9Xu{EdnM5lKv9ggqFQlJ?40xjhKIq^k zU)07$ZGPwwk7V~J+4&?BlVb6uTR9Y~H`eCk^}vVI%Hwnk{46}Cna4KqIA)QbgHIY3 zl1D`3zs1}xsegxz*BL5&94hP%6%9yzEn==&%crFW;+X`=Xnfd;p0S?9 zTz`wXu$@1jB>69icnv2A%1q*_d#8!8+C0 zTZrvD>>8Vox>4Mdm_Es^ZH+W4(mo!~Z1|$qT$^|IwxO%!+@-oJh{nC8;r*=WWA`-;QAzjtz^Ii7u|z=Wv2fXj#VN>!l;b z?mLBTO~!ZdvdioVmi{Zhp5ZE9)4|Gr^t?m#a)!v5$*HJ3Tk$2o=T;c6)t=K>yv+RC(pN0M-Dd-mC&;N5vlB2PJtvQ!1!r1BjF z+s~Ac1T8?_TUcM_wWIJ%I-4ebdPz@^w*X1zQv_`U~f{}rNg+fV2s)AE~YGz)#f^&Xu zL1JDdgW^vXMlJ>x1|5(AAfp(Vn>=>i`Dbv-A$vka-~r3C5f^&JB{~NwA;X2aQL-=@frKKWwv3( zs%b?M|9mdLmiXy?;63*j?HbL7MqLIbcP^&3j?Qk~UiW^@i7u0sr`k2mm^rJirgNbX HCxbNrD`Hob literal 0 HcmV?d00001