2012-11-15 1 views
1

신입생 키 노드 나 꼭지점이 빨간색이고 다른 꼭지점이 파란색 인 네트워크 토폴로지를 나타내는 FRLayout이 있습니다. 시작 노드에서 끝 노드는 파란색입니다. 끝 노드에 대한 경로의 애니메이션을 보여주고 싶습니다. 애니메이션을 사용하면 지정된 시간 간격으로 start_node에서 end_node까지 가장자리를 그립니 까? 예제를 제공하거나 참조 할 수 있습니까?JUNG로 드로잉 가장자리에 애니메이션 효과를 적용하는 방법

답변

2

Edge 데이터에 키 프레임을 첨부 할 수 있습니다. 그런 다음 (변압기를 사용) 그릴 때마다 당신은 가장자리의 기울기를 조정하기 위해 키 프레임을 사용할 수 있습니다

RenderContext<V, E> context = vv.getRenderContext(); 
context.setEdgeDrawPaintTransformer(new KeyframeGradientTransformer()); 

public class KeyframeGradientTransformer() implements Transformer<E, Paint> { 
     @Override 
     public Paint transform(Edge edge) { 
      // TODO: Here you would determine the gradient information 
      // based on the edge.getKeyframe(). 
      Paint gradient = new GradientPaint(...); 
      return gradient; 
     } 
} 

편집 :

enter image description here

: 나는 빠른 예를 쓴

하나의 꼭지점에서 다른 꼭지점으로 움직입니다 (하나의 가장자리를 따라). 여러 개의 꼭지점을 움직이게하려면 더 많은 논리가 필요합니다. 그러나, 이것은 매우 차갑게 보이고 당신에게 시작을 주어야합니다. 귀하 (또는 다른 누구)가 더 많은 의견을 필요로하는 경우 알려 주시면보다 명확하게 알려 드릴 수 있습니다.

import java.awt.BasicStroke; 
import java.awt.Color; 
import java.awt.Dimension; 
import java.awt.LinearGradientPaint; 
import java.awt.Paint; 
import java.awt.Stroke; 
import java.awt.geom.Point2D; 
import java.util.Timer; 
import java.util.TimerTask; 

import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.SwingUtilities; 

import org.apache.commons.collections15.Factory; 
import org.apache.commons.collections15.Transformer; 

import edu.uci.ics.jung.algorithms.generators.random.EppsteinPowerLawGenerator; 
import edu.uci.ics.jung.algorithms.layout.Layout; 
import edu.uci.ics.jung.algorithms.layout.SpringLayout; 
import edu.uci.ics.jung.graph.Graph; 
import edu.uci.ics.jung.graph.SparseMultigraph; 
import edu.uci.ics.jung.graph.util.Pair; 
import edu.uci.ics.jung.visualization.VisualizationViewer; 

public class Test { 

    public static void main(String[] args) { 

     SwingUtilities.invokeLater(new Runnable() { 

      @Override 
      public void run() { 
       JFrame frame = new JFrame(); 
       frame.setPreferredSize(new Dimension(1024, 768)); 
       frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 

       JPanel content = new JPanel(); 

       // Set up the graph and the display. 
       int numV = 70; 
       int numE = 50; 
       EppsteinPowerLawGenerator<String, String> gen = new EppsteinPowerLawGenerator<String, String>(
         new GraphFactory(), new CountFactory(), 
         new CountFactory(), numV, numE, 10); 
       Graph<String, String> graph = gen.create(); 
       Layout<String, String> layout = new SpringLayout<String, String>(
         graph); 
       VisualizationViewer<String, String> vv = new VisualizationViewer<String, String>(
         layout); 
       vv.getRenderContext().setEdgeStrokeTransformer(
         new Transformer<String, Stroke>() { 

          @Override 
          public Stroke transform(String edge) { 
           return new BasicStroke(1.5f); 
          } 
         }); 

       content.add(vv); 

       frame.setContentPane(content); 
       frame.pack(); 
       frame.setLocationRelativeTo(null); 
       frame.setVisible(true); 

       // Animate the edges! 
       AnimationTimerTask at = new AnimationTimerTask(vv); 
       Timer timer = new Timer(); 
       timer.scheduleAtFixedRate(at, 10, 30); 
      } 

     }); 
    } 

    static class AnimationTimerTask extends TimerTask { 

     private final double width = 0.1; // Size of the colored line. 
     private final double stepsize = 0.01; 
     private double keyframe = 0 + width; // Between 0.0 and 1.0 
     private VisualizationViewer<String, String> vv = null; 

     public AnimationTimerTask(VisualizationViewer<String, String> vv) { 
      this.vv = vv; 
     } 

     @Override 
     public void run() { 
      vv.getRenderContext().setEdgeDrawPaintTransformer(
        new Transformer<String, Paint>() { 

         @Override 
         public Paint transform(String edge) { 
          // Find both points of the edge. 
          Pair<String> vs = vv.getGraphLayout().getGraph() 
            .getEndpoints(edge); 
          Point2D p1 = vv.getGraphLayout().transform(
            vs.getFirst()); 
          Point2D p2 = vv.getGraphLayout().transform(
            vs.getSecond()); 

          // This code won't handle self-edges. 
          if (p1.equals(p2)) { 
           return Color.red; 
          } 

          Color[] colors = { Color.gray, Color.red, 
            Color.gray }; 
          float start = (float) Math.max(0.0, keyframe 
            - width); 
          float end = (float) Math.min(1.0, keyframe + width); 
          float[] fractions = { start, (float) keyframe, end }; 
          return new LinearGradientPaint(p1, p2, fractions, 
            colors); 
         } 

        }); 
      vv.repaint(); 
      keyframe += stepsize; 
      keyframe %= 1.0; 
     } 
    } 

    static class GraphFactory implements Factory<Graph<String, String>> { 

     @Override 
     public Graph<String, String> create() { 
      return new SparseMultigraph<String, String>(); 
     } 
    } 

    static class CountFactory implements Factory<String> { 

     private int count = 0; 

     @Override 
     public String create() { 
      return String.valueOf(count++); 
     } 
    } 
} 

또한 이전에 약간 열이 남았습니다. 이렇게하려면 JUNG 라이브러리가 필요합니다. 가지고 있지 않으면 SSCCEE를 실행할 수 없습니다.

+0

키 프레임에 대한 자세한 내용을 알려주십시오. – Nabegh

+1

@Nabegh 편집을 살펴보세요. (이것이 얼마나 효율적인지 모르겠지만, 500 정점과 모서리에서 작동하는 것 같습니다.) – sdasdadas

+0

이것은 매우 유용합니다. 감사. 가장자리 선을 변경하려면 동일한 논리를 사용하여 setEdgeStrokeTransformer를 구현해야한다고 생각합니다. – Nabegh