zoukankan      html  css  js  c++  java
  • GEF的图形渐变方法

    http://www.4ucode.com/Study/Topic/1967675(引用)

    在GEF的Flow例子里,已经提供了另一种实现动态变化的方式,这个实现方法主要由以下三部分组成:

    1. 需要有一个辅助类,用于记录初始和终态,并计算渐近过程
    2. 需要自定义一个布局类,借助上面的辅助类来给出当前布局
    3. 需要窗口类控制器需要监听状态变化,以决定什么时候开始激活动态过程
    4. 每个可能属于变化集的对象都需要提供一个方法,用于把自己加入到这个变化集中。
    下面一部分一部分的介绍。
     
    首先第一个部分,就是辅助类的实现,不过我也没写过自己的实现方式,暂且先以flow中的类作例子,见附件GraphAnimation.zip.
     
    第二部分也是一个类实现,简单如下:
     
    class GraphLayoutManager extends AbstractLayout {
    
    private NumaDiagramNodePart diagram;
    
    GraphLayoutManager(NumaDiagramNodePart diagram) {
    	this.diagram = diagram;
    }
    
    protected Dimension calculatePreferredSize(IFigure container, int wHint, int hHint) {
    	container.validate();
    	List children = container.getChildren();
    	Rectangle result =
    		new Rectangle().setLocation(container.getClientArea().getLocation());
    	for (int i = 0; i < children.size(); i++)
    		result.union(((IFigure)children.get(i)).getBounds());
    	result.resize(container.getInsets().getWidth(), container.getInsets().getHeight());
    	return result.getSize();
    }
    
    public void layout(IFigure container) {
    	GraphAnimation.recordInitialState(container);
    	if (GraphAnimation.playbackState(container))
    		return;
    
    	CompoundDirectedGraph graph = new CompoundDirectedGraph();
    	graph.setDirection(PositionConstants.EAST);
    	Map partsToNodes = new HashMap();
    	diagram.contributeNodesToGraph(graph, partsToNodes);
    	diagram.contributeEdgesToGraph(graph, partsToNodes);
    	new CompoundDirectedGraphLayout().visit(graph);
    	diagram.applyGraphResults(graph, partsToNodes);
    }
    
    }
     这里借助了两个对象来实现过程:CompoundDirectedGraph和CompoundDirectedGraphLayout。
     
    第三,监听状态变化,这部分主要就是通过在容器类中增加Command变化监听来实现,例如:
     
    	CommandStackListener stackListener = new CommandStackListener() {
    		public void commandStackChanged(EventObject event) {
    			if (!GraphAnimation.captureLayout(getFigure()))
    				return;
    			while (GraphAnimation.step())
    				getFigure().getUpdateManager().performUpdate();
    			GraphAnimation.end();
    		}
    	};
    
    	public void activate() {
    		super.activate();
    		getViewer().getEditDomain().getCommandStack().addCommandStackListener(
    				stackListener);
    	}
    
    	public void deactivate() {
    		getViewer().getEditDomain().getCommandStack()
    				.removeCommandStackListener(stackListener);
    		super.deactivate();
    	}
    最后一部分,也就是参与的过程,虽然上面我们已经定义好了整个辅助过程,但是具体在这一过程中有哪些对象会参与,怎么参与,需要我们自己实现,例如A是容器对象,里面有B和C对象,且B和C之间有一条连线,那么一般来说,一旦有变化,那么B,C和他们连线都需要处理。
     
    对于一个结点对象,处理过程通常如:
     
    	public void applyGraphResults(CompoundDirectedGraph graph, Map map) {
    		for (int i = 0; i < getChildren().size(); i++) {
    			NumaNodePart node = (NumaNodePart) getChildren().get(i);
    			Dimension dimension = node.getFigure().getPreferredSize(-1, -1);
    			Node n = (Node) map.get(node);
    			node.getFigure().setBounds(
    					new Rectangle(n.x, n.y, n.width, dimension.height));
    			applyEdgesResults(node, graph, map);
    		}
    	}
    
    	public void contributeNodesToGraph(CompoundDirectedGraph graph, Map map) {
    		GraphAnimation.recordInitialState(getContentPane());
    		for (int i = 0; i < getChildren().size(); i++) {
    			NumaNodePart node = (NumaNodePart) getChildren().get(i);
    			Node n = new Node(node);
    			n.width = node.getFigure().getPreferredSize().width;
    			n.height = node.getFigure().getPreferredSize().height;
    			n.setPadding(new Insets(10, 8, 30, 12));
    			map.put(node, n);
    			graph.nodes.add(n);
    		}
    	}
    
    	public void contributeEdgesToGraph(CompoundDirectedGraph graph, Map map) {
    		for (int i = 0; i < getChildren().size(); i++) {
    			NumaNodePart node = (NumaNodePart) children.get(i);
    			List outgoing = node.getSourceConnections();
    			for (int j = 0; j < outgoing.size(); j++) {
    				NodeRelationPart conn = (NodeRelationPart) outgoing.get(j);
    				conn.contributeToGraph(graph, map);
    			}
    		}
    	}
    
    	public void applyEdgesResults(NumaNodePart node,
    			CompoundDirectedGraph graph, Map map) {
    		List outgoing = node.getSourceConnections();
    		for (int j = 0; j < outgoing.size(); j++) {
    			NodeRelationPart conn = (NodeRelationPart) outgoing.get(j);
    			conn.applyGraphResults(graph, map);
    		}
    	}
    对于连线,因为要处理他们的Bend点,通常如下:
    	protected void applyGraphResults(CompoundDirectedGraph graph, Map map) {
    		Edge e = (Edge)map.get(this);
    		NodeList nodes = e.vNodes;
    		PolylineConnection conn = (PolylineConnection)getConnectionFigure();
    //		conn.setTargetDecoration(new PolygonDecoration());
    		if (nodes != null) {
    			List bends = new ArrayList();
    			for (int i = 0; i < nodes.size(); i++) {
    				Node vn = nodes.getNode(i);
    				int x = vn.x;
    				int y = vn.y;
    				if (e.isFeedback()) {
    					bends.add(new AbsoluteBendpoint(x, y + vn.height));
    					bends.add(new AbsoluteBendpoint(x, y));
    				} else {
    					bends.add(new AbsoluteBendpoint(x, y));
    					bends.add(new AbsoluteBendpoint(x, y + vn.height));
    				}
    			}
    			conn.setRoutingConstraint(bends);
    		} else {
    			conn.setRoutingConstraint(Collections.EMPTY_LIST);
    		}
    	}
    
    	public void contributeToGraph(CompoundDirectedGraph graph, Map map) {
    		GraphAnimation.recordInitialState(getConnectionFigure());
    		Node source = (Node)map.get(getSource());
    		Node target = (Node)map.get(getTarget());
    		Edge e = new Edge(this, source, target);
    		e.weight = 2;
    		graph.edges.add(e);
    		map.put(this, e);
    	}
     并且,在他们重连的时候需要处理:
     
    			figure.setConnectionRouter(new BendpointConnectionRouter(){
    				public void route(Connection conn) {
    					GraphAnimation.recordInitialState(conn);
    					if (!GraphAnimation.playbackState(conn))
    						super.route(conn);
    				}
    			})
  • 相关阅读:
    离奇的软件开发之路
    集群环境中的单例设计模式
    Android 如何更换屏幕上锁界面背景图片
    基于华为Java编程规范的Eclipse checkStyle.xml
    对数据库事务的总结
    [Sciter系列] MFC下的Sciter–1.创建工程框架
    Android 如何添加一种锁屏方式
    Hibernate级联操作 注解
    linux就是这个范儿之融于心而表于行(1)
    Android 如何修改默认的searchable items。
  • 原文地址:https://www.cnblogs.com/fbiswt/p/2256411.html
Copyright © 2011-2022 走看看