Merge branch 'coretk' of https://github.com/coreemu/core into coretk

This commit is contained in:
Blake Harnden 2019-12-11 16:22:01 -08:00
commit 0372e43cc5
4 changed files with 130 additions and 13 deletions

View file

@ -421,8 +421,8 @@ class CoreClient:
mobility_configs = self.get_mobility_configs_proto() mobility_configs = self.get_mobility_configs_proto()
emane_model_configs = self.get_emane_model_configs_proto() emane_model_configs = self.get_emane_model_configs_proto()
hooks = list(self.hooks.values()) hooks = list(self.hooks.values())
service_configs = self.get_service_config_proto() service_configs = self.get_service_configs_proto()
file_configs = self.get_service_file_config_proto() file_configs = self.get_service_file_configs_proto()
if self.emane_config: if self.emane_config:
emane_config = {x: self.emane_config[x].value for x in self.emane_config} emane_config = {x: self.emane_config[x].value for x in self.emane_config}
else: else:
@ -512,6 +512,11 @@ class CoreClient:
:return: nothing :return: nothing
""" """
try: try:
if self.state != core_pb2.SessionState.RUNTIME:
logging.debug(
"session state not runtime, send session data to the daemon..."
)
self.send_data()
response = self.client.save_xml(self.session_id, file_path) response = self.client.save_xml(self.session_id, file_path)
logging.info("saved xml(%s): %s", file_path, response) logging.info("saved xml(%s): %s", file_path, response)
except grpc.RpcError as e: except grpc.RpcError as e:
@ -586,6 +591,52 @@ class CoreClient:
) )
logging.debug("create link: %s", response) logging.debug("create link: %s", response)
def send_data(self):
"""
send to daemon all session info, but don't start the session
:return: nothing
"""
self.create_nodes_and_links()
for config_proto in self.get_wlan_configs_proto():
self.client.set_wlan_config(
self.session_id, config_proto.node_id, config_proto.config
)
for config_proto in self.get_mobility_configs_proto():
self.client.set_mobility_config(
self.session_id, config_proto.node_id, config_proto.config
)
for config_proto in self.get_service_configs_proto():
self.client.set_node_service(
self.session_id,
config_proto.node_id,
config_proto.service,
config_proto.startup,
config_proto.validate,
config_proto.shutdown,
)
for config_proto in self.get_service_file_configs_proto():
self.client.set_node_service_file(
self.session_id,
config_proto.node_id,
config_proto.service,
config_proto.file,
config_proto.data,
)
for hook in self.hooks.values():
self.client.add_hook(self.session_id, hook.state, hook.file, hook.data)
for config_proto in self.get_emane_model_configs_proto():
self.client.set_emane_model_config(
self.session_id,
config_proto.node_id,
config_proto.model,
config_proto.config,
config_proto.interface_id,
)
if self.emane_config:
config = {x: self.emane_config[x].value for x in self.emane_config}
self.client.set_emane_config(self.session_id, config)
def close(self): def close(self):
""" """
Clean ups when done using grpc Clean ups when done using grpc
@ -762,7 +813,7 @@ class CoreClient:
configs.append(config_proto) configs.append(config_proto)
return configs return configs
def get_service_config_proto(self): def get_service_configs_proto(self):
configs = [] configs = []
for node_id, services in self.service_configs.items(): for node_id, services in self.service_configs.items():
for name, config in services.items(): for name, config in services.items():
@ -776,7 +827,7 @@ class CoreClient:
configs.append(config_proto) configs.append(config_proto)
return configs return configs
def get_service_file_config_proto(self): def get_service_file_configs_proto(self):
configs = [] configs = []
for (node_id, file_configs) in self.file_configs.items(): for (node_id, file_configs) in self.file_configs.items():
for service, file_config in file_configs.items(): for service, file_config in file_configs.items():

View file

@ -11,7 +11,7 @@ from coretk.graph.enums import GraphMode, ScaleOption
from coretk.graph.linkinfo import LinkInfo, Throughput from coretk.graph.linkinfo import LinkInfo, Throughput
from coretk.graph.node import CanvasNode from coretk.graph.node import CanvasNode
from coretk.graph.shape import Shape from coretk.graph.shape import Shape
from coretk.graph.shapeutils import is_draw_shape from coretk.graph.shapeutils import ShapeType, is_draw_shape
from coretk.nodeutils import NodeUtils from coretk.nodeutils import NodeUtils
SCROLL_BUFFER = 25 SCROLL_BUFFER = 25
@ -32,6 +32,7 @@ class CanvasGraph(tk.Canvas):
self.mode = GraphMode.SELECT self.mode = GraphMode.SELECT
self.annotation_type = None self.annotation_type = None
self.selection = {} self.selection = {}
self.select_box = None
self.selected = None self.selected = None
self.node_draw = None self.node_draw = None
self.context = None self.context = None
@ -137,6 +138,13 @@ class CanvasGraph(tk.Canvas):
self.tag_lower(self.grid) self.tag_lower(self.grid)
def add_wireless_edge(self, src, dst): def add_wireless_edge(self, src, dst):
"""
add a wireless edge between 2 canvas nodes
:param CanvasNode src: source node
:param CanvasNode dst: destination node
:return: nothing
"""
token = tuple(sorted((src.id, dst.id))) token = tuple(sorted((src.id, dst.id)))
x1, y1 = self.coords(src.id) x1, y1 = self.coords(src.id)
x2, y2 = self.coords(dst.id) x2, y2 = self.coords(dst.id)
@ -249,6 +257,7 @@ class CanvasGraph(tk.Canvas):
:param event: mouse event :param event: mouse event
:return: nothing :return: nothing
""" """
logging.debug("click release")
if self.context: if self.context:
self.context.unpost() self.context.unpost()
self.context = None self.context = None
@ -260,6 +269,19 @@ class CanvasGraph(tk.Canvas):
shape = self.shapes[self.selected] shape = self.shapes[self.selected]
shape.shape_complete(x, y) shape.shape_complete(x, y)
self.shape_drawing = False self.shape_drawing = False
elif self.mode == GraphMode.SELECT:
self.focus_set()
if self.select_box:
x0, y0, x1, y1 = self.coords(self.select_box.id)
inside = [
x
for x in self.find_enclosed(x0, y0, x1, y1)
if "node" in self.gettags(x) or "shape" in self.gettags(x)
]
for i in inside:
self.select_object(i, True)
self.select_box.disappear()
self.select_box = None
else: else:
self.focus_set() self.focus_set()
self.selected = self.get_selected(event) self.selected = self.get_selected(event)
@ -445,6 +467,10 @@ class CanvasGraph(tk.Canvas):
self.select_object(node.id) self.select_object(node.id)
self.selected = selected self.selected = selected
else: else:
logging.debug("create selection box")
if self.mode == GraphMode.SELECT:
shape = Shape(self.app, self, ShapeType.RECTANGLE, x, y)
self.select_box = shape
self.clear_selection() self.clear_selection()
def ctrl_click(self, event): def ctrl_click(self, event):
@ -486,6 +512,7 @@ class CanvasGraph(tk.Canvas):
return return
# move selected objects # move selected objects
if len(self.selection) > 0:
for selected_id in self.selection: for selected_id in self.selection:
if selected_id in self.shapes: if selected_id in self.shapes:
shape = self.shapes[selected_id] shape = self.shapes[selected_id]
@ -494,6 +521,9 @@ class CanvasGraph(tk.Canvas):
if selected_id in self.nodes: if selected_id in self.nodes:
node = self.nodes[selected_id] node = self.nodes[selected_id]
node.motion(x_offset, y_offset, update=self.core.is_runtime()) node.motion(x_offset, y_offset, update=self.core.is_runtime())
else:
if self.select_box and self.mode == GraphMode.SELECT:
self.select_box.shape_motion(x, y)
def click_context(self, event): def click_context(self, event):
logging.info("context event: %s", self.context) logging.info("context event: %s", self.context)
@ -681,3 +711,23 @@ class CanvasGraph(tk.Canvas):
def is_selection_mode(self): def is_selection_mode(self):
return self.mode == GraphMode.SELECT return self.mode == GraphMode.SELECT
def create_edge(self, source, dest):
"""
create an edge between source node and destination node
:param CanvasNode source: source node
:param CanvasNode dest: destination node
:return: nothing
"""
if tuple([source.id, dest.id]) not in self.edges:
pos0 = source.core_node.position
x0 = pos0.x
y0 = pos0.y
edge = CanvasEdge(x0, y0, x0, y0, source.id, self)
edge.complete(dest.id)
self.edges[edge.token] = edge
self.nodes[source.id].edges.add(edge)
self.nodes[dest.id].edges.add(edge)
link = self.core.create_link(edge, source, dest)
edge.link_info = LinkInfo(self, edge, link)

View file

@ -3,6 +3,7 @@ from tkinter import font
import grpc import grpc
from core.api.grpc import core_pb2
from core.api.grpc.core_pb2 import NodeType from core.api.grpc.core_pb2 import NodeType
from coretk import themes from coretk import themes
from coretk.dialogs.emaneconfig import EmaneConfigDialog from coretk.dialogs.emaneconfig import EmaneConfigDialog
@ -193,7 +194,9 @@ class CanvasNode:
label="Mobility Config", command=self.show_mobility_config label="Mobility Config", command=self.show_mobility_config
) )
if NodeUtils.is_wireless_node(self.core_node.type): if NodeUtils.is_wireless_node(self.core_node.type):
context.add_command(label="Link To All MDRs", state=tk.DISABLED) context.add_command(
label="Link To Selected", command=self.wireless_link_selected
)
context.add_command(label="Select Members", state=tk.DISABLED) context.add_command(label="Select Members", state=tk.DISABLED)
context.add_command(label="Select Adjacent", state=tk.DISABLED) context.add_command(label="Select Adjacent", state=tk.DISABLED)
context.add_command(label="Create Link To", state=tk.DISABLED) context.add_command(label="Create Link To", state=tk.DISABLED)
@ -235,3 +238,13 @@ class CanvasNode:
self.canvas.context = None self.canvas.context = None
dialog = NodeService(self.app.master, self.app, self) dialog = NodeService(self.app.master, self.app, self)
dialog.show() dialog.show()
def wireless_link_selected(self):
self.canvas.context = None
for canvas_nid in [
x for x in self.canvas.selection if "node" in self.canvas.gettags(x)
]:
core_node = self.canvas.nodes[canvas_nid].core_node
if core_node.type == core_pb2.NodeType.DEFAULT and core_node.model == "mdr":
self.canvas.create_edge(self, self.canvas.nodes[canvas_nid])
self.canvas.clear_selection()

View file

@ -132,6 +132,9 @@ class Shape:
s = ShapeDialog(self.app, self.app, self) s = ShapeDialog(self.app, self.app, self)
s.show() s.show()
def disappear(self):
self.canvas.delete(self.id)
def motion(self, x_offset, y_offset): def motion(self, x_offset, y_offset):
self.canvas.move(self.id, x_offset, y_offset) self.canvas.move(self.id, x_offset, y_offset)
self.canvas.move_selection(self.id, x_offset, y_offset) self.canvas.move_selection(self.id, x_offset, y_offset)