Responding to clicks and other code bits
Handling System Events
In the current version of GUESS you can add an event handler to respond to a number of user actions (left-clicks, shift-left-clicks, and the mouse entering or leaving a node).
For example, we can define a couple of simple event handler methods:
def sc1(_node):
print “node ” + _node.name + “ was clicked”
def sc2(_edge):
print “edge ” + _edge.toString() + “ was clicked”
graphevents.shiftClickNode = sc1
graphevents.shiftClickEdge = sc2
Similarly we can add events to mouse events:
graphevents.mouseEnterNode = …
graphevents.mouseEnterEdge = …
graphevents.mouseLeaveNode = …
graphevents.mouseLeaveEdge = …
To capture click events:
graphevents.clickNode = sc1 graphevents.clickEdge = sc2
You can use these methods to implement your own behaviors in the visualization. In order to override the existing mechanisms (left-click causes a zoom, mouse over causes a highlight) by using the following commands:
vf.defaultNodeHighlights(state) vf.defaultEdgeHighlights(state) vf.defaultNodeZooming(state) vf.defaultEdgeZooming(state)
where state is true or false
Here is a little piece of code that highlights neighboring edges and nodes when we mouse over a specific node. It also changes the zoom behavior to zoom to a node and all its neighbors (also available as newhighlight.py in the samples directory).
import java
class newhighlight(java.lang.Object):
# so we can "unhighlight" nodes
_toFix = {}
def __init__(self):
# add the listeners
graphevents.mouseEnterNode = self.mouseEnter
graphevents.mouseLeaveNode = self.mouseLeave
graphevents.clickNode = self.mouseClick
# remove default behaviors
vf.defaultNodeHighlights(false)
vf.defaultNodeZooming(false)
def mouseEnter(self,_node):
# when we enter the node we should
# track all current colors, make the node
# yellow, the edges orange, and the neighbors red
self._toFix[_node] = _node.color
StatusBar.setStatus(str(_node))
_node.color = yellow
for _e in _node.getOutEdges():
self._toFix[_e] = _e.color
_e.color = orange
for _n in _node.getNeighbors():
if (_n != _node):
self._toFix[_n] = _n.color
_n.color = red
def mouseLeave(self,_node):
# put back all the original colors
for _elem in self._toFix.keys():
_elem.color = self._toFix[_elem]
self._toFix.clear();
def mouseClick(self,_node):
# zoom to the node AND its neighbors
_toCenter = [_node]
_toCenter += _node.getNeighbors()
center(_toCenter)
Although it is not possible (at the moment) to capture events to the underlying canvas the command:
coord = v.getLastClickedPosition()
will return a coordinate (call coord.getX() and coord.getY() to get the x and y values) with the last placed the user left-clicked on.
Contextual Menus
Finally, GUESS now supports contextual menus. Right clicking on graph elements in the GUI console, or in the graph, pulls up a menu. You can modify the content of these menus by adding items to the NodeEditorPopup, EdgeEditorPopup, or GraphElementPopup (contextual when there is a mixture of nodes and edges selected). Note that multiple graph elements can be submitted if more than one element is selected in the various interfaces.
# create a new menu item
newMenuItem = NodeEditorPopup.addItem("Print node name")
# define an action for that menu item
def action(_target):
print _target
# map the events produced by the click events to the action function
newMenuItem.menuEvent = action
Background Images
GUESS allows you to set your own background images. This is useful, for example, if you want to have a map or floorplan in the background. The two commands for this are:
v.setBackgroundImage(image_file_name) and v.setBackgroundImage(image_file_name,xcoord,ycoord)
The second places the image at the specified coordinate. An example of this is illustrated below:
The sample program in dockexample5.py loads up an image and asks you to click on the location of two nodes on the background. Using these coordinates the program will translate and rescale your graph to fit. Creating a dockexample5 object with no parameters (e.g. dockexample5()) will use the sample map file. Alternatively you can use your own image files (e.g. dockexample5(“foo.jpg”)) instead.
Other Functions
In the Functions.py file in the scripts directory there are a number of additional demonstrations that implement various common functions. These include:
-
removeLeaves() which iteratively removes all nodes with totaldegree <= 1
-
shortcutNodes() which iteratively removes nodes that have a degree of 2 and draws a new connection between the two nodes (i.e. a–b–c will become a-c).
-
condenseGraph() will remove disconnected nodes and then iterate between removing leaves and shortcutting until the graph stops changing
-
skitter(field) generates a skitter plot (see:
http://www.caida.org/analysis/topology/as_core_network/ )
-
averageEdgeColor(edge) will color the edge by the average color of its two endpoints
-
distance(node1,node2) will calculate the distance between two nodes



