Mondrian: An Agile Information Visualization Framework - PDF

Please download to get full document.

View again

of 10
All materials on our website are shared by users. If you have any questions about copyright issues, please report us to resolve them. We are always happy to assist you.
Information Report
Category:

Recipes/Menus

Published:

Views: 3 | Pages: 10

Extension: PDF | Download: 0

Share
Related documents
Description
Mondrian: An Agile Information Visualization Framework In Proceedings of ACM Symposium on Software Visualization (SoftVis 2006) Michael Meyer Software Composition Group University of Bern, Switzerland
Transcript
Mondrian: An Agile Information Visualization Framework In Proceedings of ACM Symposium on Software Visualization (SoftVis 2006) Michael Meyer Software Composition Group University of Bern, Switzerland Tudor Gîrba Software Composition Group University of Bern, Switzerland Mircea Lungu Faculty of Informatics University of Lugano, Switzerland Abstract Data visualization is the process of representing data as pictures to support reasoning about the underlying data. For the interpretation to be as easy as possible, we need to be as close as possible to the original data. As most visualization tools have an internal metamodel, which is different from the one for the presented data, they usually need to duplicate the original data to conform to their metamodel. This leads to an increase in the resources needed, increase which is not always justified. In this work we argue for the need of having an engine that is as close as possible to the data and we present our solution of moving the visualization tool to the data, instead of moving the data to the visualization tool. Our solution also emphasizes the necessity of reusing basic blocks to express complex visualizations and allowing the programmer to script the visualization using his preferred tools, rather than a third party format. As a validation of the expressiveness of our framework, we show how we express several already published visualizations and describe the pros and cons of the approach. Keywords: software visualization, graph visualization, model transformation 1 Introduction Visualization is an established tool to reason about data. Given a wanted visualization, we can typically find tools that take as input a certain format and that provide the needed visualization [Panas et al. 2005; Reiss 2001 Typically, the visualization tools have an internal model and they translate the data in such a way that it fits their internal model. The main advantage of this approach is that it can accommodate data provided by third party tools. This works perfectly well when it is enough to just generate the picture, or the animation without further inspection of the data. However, one drawback of the approach is that, when a deep reasoning is required, we need to refer back to the capabilities of the original tool that manipulates the actual data. A second drawback of the approach is that it actually duplicates the required resources: the data is present both in the original tool, and in the visualization tool. A third drawback is that when a programmer needs to visualize his own data, he is forced to leave his preferred environment and language and learn the language of the import/export format. Several tools take a middle ground approach and choose to work close with the data by either offering integration with other services [Lanza and Ducasse 2005], or providing the services themselves [M.-A. D. Storey and Michaud 2001 However, when another type of service is required, the integration is lost. In this paper we propose a radically different approach: instead of moving the data to be visualized to the tool, we argue for moving the visualization tool to the data. Instead of providing a required data format, we provide a simple interface through which the programmer can easily script, in a declarative fashion, the visualization. This means that our solution works directly with the objects in the data model. The primary focus of our approach is to offer the programmer the possibility of visualizing his data model while using his preferred environment and tools. We provide a framework that puts all the emphasis on providing the needed basic pieces and that places the control in the hand of the programmer. The example below shows the essence of our approach: a script that creates a view, adds nodes representing some objects (in this case the classes in the model), and adds the edges representing some other objects (in this case the inheritance relationships in the model). The nodes and edges are represented using shapes. The result of executing the script on a given model is the tree shown below the script. using: (Rectangle withborder height: #NOM; width: #NOA). Mondrian, our framework, is written in Smalltalk, and this is why the previous script is written in Smalltalk (see the Appendix for details concerning the Smalltalk syntax). However, because we wanted the model to be easily implemented in other languages too, we strived to make it simple enough so it can be built on top of any graphical framework. Paper structure. In the next section we detail the challenges that a visualization engine faces. Section 3 presents the framework from a user s point of view and then discusses the implementation. In Section 4 we validate our model by showing that the implementation of already known visualizations is straight-forward when based on the Mondrian framework. In Section 5 we show several characteristics of the user interface prototype. We position our approach with respect to the state of the art in Section 6, and we conclude in Section 7. We present the Smalltalk syntax in the Appendix. 2 Challenges for an information visualization engine Reiss postulates two reasons for the slowness of the software developer community in adopting software visualization tools [Reiss 2001 The first is the lack of flexibility: the tools which are designed for a specific purpose can not support the user when he needs a slightly (or sometimes even drastically) different visualization on the data related to the task at hand. The second reason is the difficulty of preparing and converting the data to the format understood by the visualization tool. In this work we propose an approach which solves the second problem by bringing the visualization closer to the data and not viceversa, and solves the first problem by providing an extremely malleable visualization framework. Some of the factors that would be needed to provide flexibility to the framework and to support the proximity of the visualization to the data are: The visualization engine should be domain independent. As on the one hand we want to bring the visualization to the data, and on the other hand we want to provide a framework, we will need to make sure that the framework is general enough to accommodate any data model. Visualizations shoud be easily composed from simpler parts. The user of the framework should be able to define basic blocks that he can later for building more complex visualizations. One example is the way graph-layouting tools such as GraphViz and aisee [GRA ; AIS ] implement nested layouts: once a layout is defined, it can be used to layout the internal contents of a given node which is part of another graph which has yet another layout. The visualization should be definable at a fine grained level. Indeed, it is important to detail the visualization at any level of detail desired. For example, showing the details of a figure by representing inside other figures based on the characteristics of the represented object. From another perspective, the framework should support instance based representation as opposed to type based representation, as it is sometimes desired to not show all the objects of the same type with the same representation. Object creation overhead should be kept to a minimum. Visualization engines typically have an internal meta-model, usually a graph-like one, in which they put the data and on which the visualization is defined. However, when the objects of the data model are already present, we do not need to duplicate them, but the visualization should work directly with those objects. This is important as it saves memory and time that is otherwise spent in building the internal model. The visualization description should be declarative. The description of the visualization should be declarative, as it should only be a mapping between the data model and the visualization model. The benefit of a declarative approach is that it allows for generation of the descriptions from editors. 3 Scripting visualizations with Mondrian 3.1 Painting a view with Mondrian In this section we give a simple step-by-step example of how to script visualizations using Mondrian. The example builds on a small model of a source code with 38 classes. The task we propose is to provide a simple overview of the classes in the system and of some of their relationships. Creating a view. To make the things as easy as possible for the programmer, we have designed Mondrian to work like a view the programmer paints. The first thing we do is to create an empty view: Adding nodes. Suppose we can ask the model object for the classes. We can add those classes to the visualization by creating a node for each class. In the example below we represent each class using a Rectangle with border: using: Rectangle withborder. We directly support polymetric views on a Rectangle [Lanza and Ducasse 2003 For example, if we want to specify the width and the height and the color, we need to set the different characteristics of the object to be used by the Rectangle: using: (Rectangle withborder width: #NOA; height: #NOM; liniarcolor: #LOC within: model classes). NOA, NOM and LOC are methods in the object representing a class and return the value of the corresponding metrics: NOA stands for number of attributes, NOM stands for number of methods, and LOC stands for number of lines of code. Adding edges. To show how classes inherit from each other, we can add an edge for each inheritance relationship. We use a similar instruction as for the nodes. In our example, supposing that we can ask the model for all the inheritance definitions between the classes in the model, and that each inheritance is represented as an object, the addition of the edges is illustrated in the example below: using: (Rectangle withborder width: #NOA; height: #NOM; liniarcolor: #LOC within: model classes). In this section we show the usage of our framework by providing a step-by-step example of how to handle the main parts of the visualization, and we use the example to detail the internal structure of the framework, emphasizing the different design decisions. Like in the case of the nodes, when specifying the shape, we made reference to methods that are defined in the inheritance object. Thus, given an inheritance object, we will create an edge between the node holding the superclass and the node holding the subclass. Layouting. To make the above graph understandable, we layout the nodes in a tree. By default, the nodes are arranged in a horizontal line. If another arrangement is desired, the programmer needs only to specify another supported layout. For example: using: (Rectangle withborder width: #NOA; height: #NOM; liniarcolor: #LOC within: model classes). Adding inter-edges. The edges are created by specifying the from and the to objects. Because we can have the objects at various levels of nesting, it is important to specify the location from where the lookup of the objects should start. For example, if we want to add invocations as edges between the methods, and if we suppose that we can ask the model object about those invocations we can add them like we added inheritances: using: (Rectangle withborder liniarcolor: #LOC within: model classes). foreach: [:eachclass view nodes: eachclass methods using: Rectangle withborder. view layout: CheckerboardLayout new view edges: model invocations using (Line from: #invokedby: to: #invoked). Nesting. To obtain more details for the classes, we would like to see which are the methods inside. To nest we specify for each node the view that goes inside. Supposing that we can ask each class in the model about its methods, we can add those methods to the class by specifying the view for each class: using: (Rectangle withborder liniarcolor: #LOC within: model classes). foreach: [:eachclass view nodes: eachclass methods using: Rectangle withborder. view layout: CheckerboardLayout new. We defined the invocation edges in the outer graph, and as a result we obtained the edges between methods defined in different classes. However, if we want to restrict the edges only to the scope of one class, all we have to do is to move the instruction at the right nesting level: using: (Rectangle withborder liniarcolor: #LOC within: model classes). foreach: [:eachclass view nodes: eachclass methods using: Rectangle withborder. view layout: CheckerboardLayout new view edges: model invocations using (Line from: #invokedby to: #invoked) In the example, we use a Smalltalk construct which represents a closure, or a lamba. In our example, we use [:eachclass... This is equivalent to (lamba(eachclass)(...)). In Java, the closure can be modeled by using a Command pattern together with an anonymous class. A similar problem was solved in the SWT 1 framework of Eclipse, where the user interface needs to accommodate any type of objects using duck typing 2. We use the closure to depict the nesting level: the code from inside the closure depicts the graph for each class visual editor/?p=25 Decorating shapes. By default, the sense of the edges is shown by the convention that edges leave from the bottom-right of the node and end on the top-left of the node [Lanza and Ducasse 2003 However, when the user wants to specify an arrow at the end of the line, he can use decorations. We introduce the notion of decorations to allow the programmer compose the overall visual representation out of basic shapes. For example, when we want to show the arrows on the inheritances all we have to do is to decorate the Line with an Arrow: using: (Rectangle withborder liniarcolor: #LOC within: model classes). foreach: [:eachclass view nodes: eachclass methods using: Rectangle withborder. view layout: CheckerboardLayout new view edges: model invocations using (Line from: #invokedby to: #invoked) using: ((Line from: #superclass to: #subclass) decoratedwith: Arrow new). Decorations can be applied to any figure. In fact, Rectangle with- Border is implemented as Rectangle new decoratedwith: Border new. 3.2 Mondrian internals Overview. Figure 1 reveals the core structure of our framework. Each Figure represents and holds an Object. The Figure, NodeFigure and EdgeFigure are implemented directly on top of the graphical framework, but they hold no specific value for the visualization (e.g., label or the size of the shape). The entire responsibility of what gets drawn belongs to the Shape.... Shape decoratedwith: displayfigure:on: Line color: width: ViewRenderer graphstack nodes:using: node:using: nodes:using:foreach: node:using:forit: edges:using: edge:using: layout: open Rectangle width: height: color: liniarcolor:within: 1 *... 1 * NodeFigure TreemapLayout Object Figure Layout Figure 1: The internal model of Mondrian. * 1 * EdgeFigure 1 TreeLayout As we want to accommodate any Object, we cannot tie the implementation to a particular interface. That is why, the Figure talks to the Object through the Shape which acts like a translator between the visualization model and the data model. We can have several shapes (e.g., Rectangle, Line), and depending on the Shape we can specify how to compute a certain visual characteristic via a closure. For example, to a Rectangle we can specify how to compute the width, height and color. As mentioned in the previous section, in Smalltalk, closures are first class objects that can be passed around and get executed with a specified context. Closures can be simulated in Java using anonymous classes that implement a command. A similar problem was addressed and solved in SWT. The Shape is just a specification of how the Figure should be displayed on a canvas (via displayfigure:on:). The Shape holds no state, and thus it is possible to share a Shape between several nodes or edges. For example, the instruction using: Rectangle withborder will create one NodeFigure for each class, but all those figures will share and be displayed according to the specification in Rectangle withborder. The Figure is implemented directly on top of the graphical framework. One goal of our framework was to create as less objects as possible for the visualization. The assumption is that the graphical framework creates an object for each visual figure, and we wanted to reuse that to model the graph. Our particular implementation was accomplished on top of the Smalltalk Hotdraw framework [Brant 1995 We claim that such an implementation is not tied to Smalltalk: on the one hand Hotdraw is implemented in Java 3 too, on the other hand, the specific implementation is minimal. The three classes have 354 lines of code. Each Figure is a graph and holds several NodeFigures and Edges- Figures. Furthermore, the Figure also knows the Layout to be applied on its children. The specific Layouts are implemented in subclasses of the Layout. ViewRenderer. To make the script easy to write, we have designed the ViewRenderer to hide the internal details of the model. The intent of the ViewRenderer was to provide a script which is concise and which looks similar with a dedicated format, while still being an executable program 4. In Figure 1 we show the main protocol of the ViewRenderer: two methods dealing with adding nodes There are two methods for adding several nodes, and two for adding one node. two methods dealing with adding nodes with nested graphs Again, we can add nodes specifying for each what goes inside, or we can add just one node specifying for it what goes inside. two methods dealing with adding edges Like in the case of the nodes, we can add one or several edges. one method for specifying the layout This method simply takes an instance of a Layout. one method for spawning the view A particular implementation that dramatically increased the readability is the graphstack implemented internally. This is useful for expressing nested graphs. For example in the example below: using: Rectangle withborder foreach: [:eachclass view nodes: eachclass methods using: Rectangle withborder view layout: CheckerboardLayout new The design of the ViewRenderer was inspired by the HtmlRenderer from Seaside [Ducasse et al. 2004] we refer to the same variable view, both from the outer context and from the inner context. Internally, the implementation of view:using:foreach: puts the current graph (represented by a figure) on the stack and whenever view is called from within the nested context, the commands are attributed to the current graph. In this way the programmer feels like he is all the time creating the same view and by indenting correspondingly with the nesting levels, the script reads as the format of a GraphViz-like tool. Reusing Scripts. To fully support the programmer, we want to allow him to place his views in methods, and then reuse them. For this we can pass the view as a parameter to a method that builds the visualization on the view. For example, the previous example script in the previous section can be implemented like: using: Rectangle withborder foreach: [:eachclass eachclass viewmethodsin: view]... view open ModelClass viewMethodsIn: view view nodes: self methods using: Rectangle withborder view layout: CheckerboardLayout new. We implemented viewmethodsin: to show on a view the methods from the ModelClass, and call it from within the graph inside a class node. This example shows how we can put the visualization near the data it represents and then reuse it in a larger context. 4 Case studies To validate our model, we have implemented several already published visualizations. Each case study presented here exercises another part of the framework. Together with each resulting visualization we attach the code we used to generate it. The scripts presented are complete, except for the implementation of the data model. In our case, we assume we have a model object from which we can obtain the different other objects needed for the visualization (e.g., classes, methods). The actual implementation makes use of the Moose
We Need Your Support
Thank you for visiting our website and your interest in our free products and services. We are nonprofit website to share and download documents. To the running of this website, we need your help to support us.

Thanks to everyone for your continued support.

No, Thanks