visualization.GridD3Json.java Source code

Java tutorial

Introduction

Here is the source code for visualization.GridD3Json.java

Source

/*
 * Copyright (c) 2011-2015, fortiss GmbH.
 * Licensed under the Apache License, Version 2.0.
 *
 * Use, modification and distribution are subject to the terms specified
 * in the accompanying license file LICENSE.txt located at the root directory
 * of this software distribution.
 */

package visualization;

import helper.IoHelper;
import helper.SerializationHelper;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;

import org.apache.commons.lang3.StringUtils;

import topology.ActorTopology;
import akka.basicActors.ActorOptions;

/**
 * Created with IntelliJ IDEA.
 * User: amack
 * Date: 25.10.13
 * Time: 20:09
 * To change this template use File | Settings | File Templates.
 */

public class GridD3Json {
    public String name;
    public List<GridD3Json> children = new ArrayList<GridD3Json>();

    @Override
    public String toString() {
        return "{" + "'name':'" + name + '\'' + ", 'children':" + children + '}';
    }

    public static HashSet<String> getSupervisorChildren(ActorTopology topology) {
        HashSet<String> childrenSet = new HashSet<String>();
        for (String path : topology.getActorTopology().keySet()) {
            if (StringUtils.countMatches(path, "/") == 3)
                childrenSet.add(path.replace("/user/ActorSupervisor/", ""));
        }
        return childrenSet;
    }

    public GridD3Json(String name, List<GridD3Json> children) {
        this.name = name;
        this.children = children;
    }

    public GridD3Json() {
    }

    public static GridD3Json extractChildrenFromActorOptions(String actorPath, ActorOptions options,
            ActorTopology topology) {
        String actorName = getActorName(actorPath);

        // Sortieren
        ArrayList<String> arrayList = new ArrayList<String>();
        for (String name : options.childrenNameList)
            arrayList.add(name);
        Collections.sort(arrayList);

        if (options.childrenNameList.isEmpty())
            return new GridD3Json(actorName, null);
        else {
            GridD3Json gridD3Json = new GridD3Json();
            gridD3Json.name = actorName;
            for (String childName : arrayList) {
                gridD3Json.children.add(extractChildrenFromActorOptions(actorPath + "/" + childName,
                        topology.getActorOptions(actorPath + "/" + childName), topology));
            }
            return gridD3Json;
        }
    }

    public static String getActorName(String actorPath) {
        return actorPath.substring(actorPath.lastIndexOf("/") + 1);
    }

    public static void saveAsJson(String filePath, String json) {
        IoHelper.saveFile(filePath, json);
    }

    /**
     * 
     * This method converts the HashTable Topology to a JSON String
     * 
     * @param topology This is the GridTopology as input
     * @return
     */
    public static String convertToJson(ActorTopology topology) {
        ActorOptions supervisorOptions = new ActorOptions();
        supervisorOptions.childrenNameList = getSupervisorChildren(topology);

        GridD3Json grid = new GridD3Json();
        if (supervisorOptions.childrenNameList.size() == 1) {
            String key = supervisorOptions.childrenNameList.iterator().next();
            grid.name = key;
            String path = "/user/ActorSupervisor/" + key;
            grid = extractChildrenFromActorOptions(path, topology.getActorOptions(path), topology);
        } else {
            for (String key : supervisorOptions.childrenNameList) {
                grid.name = "ActorSupervisor";
                String path = "/user/ActorSupervisor/" + key;
                grid.children.add(extractChildrenFromActorOptions(path, topology.getActorOptions(path), topology));
            }
        }
        //GridD3Json grid = extractChildrenFromActorOptions("/user/ActorSupervisor", supervisorOptions, topology);  
        // das Grid ist eigentlich schon eine fertige JSON datei.   
        return SerializationHelper.serializeObject(grid);
    }

    public static void saveHtml(String filePath) {
        String html = "<!DOCTYPE html>\n" + "<html>\n" + "<head>\n" + "   <meta charset=\"utf-8\">\n"
                + "   <title>FortissSimulation</title>\n"
                + "   <script src=\"//ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js\"></script>\n"
                + "   <script src=\"http://d3js.org/d3.v3.min.js\" charset=\"utf-8\"></script>\n" + "    <style>\n"
                + "        .node {\n" + "            cursor: pointer;\n" + "        }\n\n"
                + "        .node circle {\n" + "            fill: #fff;\n" + "            stroke: steelblue;\n"
                + "            stroke-width: 1.5px;\n" + "        }\n" + "\n" + "        .node text {\n"
                + "            font: 10px sans-serif;\n" + "        }\n" + "\n" + "        .link {\n"
                + "            fill: none;\n" + "            stroke: #ccc;\n" + "            stroke-width: 1.5px;\n"
                + "        }\n" + "\n" + "    </style>\n" + "</head>\n" + "<body>\n" + "<script>\n" + "\n"
                + "    var margin = {top: 20, right: 120, bottom: 20, left: 120},\n"
                + "            width = 960 - margin.right - margin.left,\n"
                + "            height = 800 - margin.top - margin.bottom;\n" + "\n" + "    var i = 0,\n"
                + "            duration = 750,\n" + "            root;\n" + "\n"
                + "    var tree = d3.layout.tree()\n" + "            .size([height, width]);\n" + "\n"
                + "    var diagonal = d3.svg.diagonal()\n"
                + "            .projection(function(d) { return [d.y, d.x]; });\n" + "\n"
                + "    var svg = d3.select(\"body\").append(\"svg\")\n"
                + "            .attr(\"width\", width + margin.right + margin.left)\n"
                + "            .attr(\"height\", height + margin.top + margin.bottom)\n"
                + "            .append(\"g\")\n"
                + "            .attr(\"transform\", \"translate(\" + margin.left + \",\" + margin.top + \")\");\n"
                + "\n" + "    d3.json(\"gridtopology.json\", function(error, topology) {\n"
                + "        root = topology;\n" + "        console.log(topology);\n"
                + "        root.x0 = height / 2;\n" + "        root.y0 = 0;\n" + "\n"
                + "        function collapse(d) {\n" + "            if (d.children) {\n"
                + "                d._children = d.children;\n" + "                d._children.forEach(collapse);\n"
                + "                d.children = null;\n" + "            }\n" + "        }\n" + "\n"
                + "        root.children.forEach(collapse);\n" + "        update(root);\n" + "    });\n" + "\n"
                + "    d3.select(self.frameElement).style(\"height\", \"800px\");\n" + "\n"
                + "    function update(source) {\n" + "\n" + "        // Compute the new tree layout.\n"
                + "        var nodes = tree.nodes(root).reverse(),\n"
                + "                links = tree.links(nodes);\n" + "\n" + "        // Normalize for fixed-depth.\n"
                + "        nodes.forEach(function(d) { d.y = d.depth * 180; });\n" + "\n"
                + "        // Update the nodes\n" + "        var node = svg.selectAll(\"g.node\")\n"
                + "                .data(nodes, function(d) { return d.id || (d.id = ++i); });\n" + "\n"
                + "        // Enter any new nodes at the parent's previous position.\n"
                + "        var nodeEnter = node.enter().append(\"g\")\n"
                + "                .attr(\"class\", \"node\")\n"
                + "                .attr(\"transform\", function(d) { return \"translate(\" + source.y0 + \",\" + source.x0 + \")\"; })\n"
                + "                .on(\"click\", click);\n" + "\n" + "        nodeEnter.append(\"circle\")\n"
                + "                .attr(\"r\", 1e-6)\n"
                + "                .style(\"fill\", function(d) { return d._children ? \"lightsteelblue\" : \"#fff\"; });\n"
                + "\n" + "        nodeEnter.append(\"text\")\n"
                + "                .attr(\"x\", function(d) { return d.children || d._children ? -10 : 10; })\n"
                + "                .attr(\"dy\", \".35em\")\n"
                + "                .attr(\"text-anchor\", function(d) { return d.children || d._children ? \"end\" : \"start\"; })\n"
                + "                .text(function(d) { return d.name; })\n"
                + "                .style(\"fill-opacity\", 1e-6);\n" + "\n"
                + "        // Transition nodes to their new position.\n"
                + "        var nodeUpdate = node.transition()\n" + "                .duration(duration)\n"
                + "                .attr(\"transform\", function(d) { return \"translate(\" + d.y + \",\" + d.x + \")\"; });\n"
                + "\n" + "        nodeUpdate.select(\"circle\")\n" + "                .attr(\"r\", 4.5)\n"
                + "                .style(\"fill\", function(d) { return d._children ? \"lightsteelblue\" : \"#fff\"; });\n"
                + "\n" + "        nodeUpdate.select(\"text\")\n" + "                .style(\"fill-opacity\", 1);\n"
                + "\n" + "        // Transition exiting nodes to the parent's new position.\n"
                + "        var nodeExit = node.exit().transition()\n" + "                .duration(duration)\n"
                + "                .attr(\"transform\", function(d) { return \"translate(\" + source.y + \",\" + source.x + \")\"; })\n"
                + "                .remove();\n" + "\n" + "        nodeExit.select(\"circle\")\n"
                + "                .attr(\"r\", 1e-6);\n" + "\n" + "        nodeExit.select(\"text\")\n"
                + "                .style(\"fill-opacity\", 1e-6);\n" + "\n" + "        // Update the links\n"
                + "        var link = svg.selectAll(\"path.link\")\n"
                + "                .data(links, function(d) { return d.target.id; });\n" + "\n"
                + "        // Enter any new links at the parent's previous position.\n"
                + "        link.enter().insert(\"path\", \"g\")\n" + "                .attr(\"class\", \"link\")\n"
                + "                .attr(\"d\", function(d) {\n"
                + "                    var o = {x: source.x0, y: source.y0};\n"
                + "                    return diagonal({source: o, target: o});\n" + "                });\n" + "\n"
                + "        // Transition links to their new position.\n" + "        link.transition()\n"
                + "                .duration(duration)\n" + "                .attr(\"d\", diagonal);\n" + "\n"
                + "        // Transition exiting nodes to the parent's new position.\n"
                + "        link.exit().transition()\n" + "                .duration(duration)\n"
                + "                .attr(\"d\", function(d) {\n"
                + "                    var o = {x: source.x, y: source.y};\n"
                + "                    return diagonal({source: o, target: o});\n" + "                })\n"
                + "                .remove();\n" + "\n" + "        // Stash the old positions for transition.\n"
                + "        nodes.forEach(function(d) {\n" + "            d.x0 = d.x;\n"
                + "            d.y0 = d.y;\n" + "        });\n" + "    }\n" + "\n"
                + "    // Toggle children on click.\n" + "    function click(d) {\n" + "        if (d.children) {\n"
                + "            d._children = d.children;\n" + "            d.children = null;\n"
                + "        } else {\n" + "            d.children = d._children;\n"
                + "            d._children = null;\n" + "        }\n" + "        update(d);\n" + "    }\n" + "\n"
                + "</script>\n" + "</body>\n" + "</html>";
        IoHelper.saveFile(filePath, html);
    }
}