Revision 3:f4335dcd7a98

View differences:

src/main/java/cz/agents/alite/visualizer2d/Layer.java
3 3
/**
4 4
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
5 5
 */
6
public interface Layer {
6
public interface Layer<T> {
7 7

  
8
    public void paint(VisCanvas canvas);
8
    public void paint(VisCanvas canvas, Point2dAdapter<T> adapter);
9 9

  
10 10
}
src/main/java/cz/agents/alite/visualizer2d/LayerContainer.java
6 6
/**
7 7
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
8 8
 */
9
public class LayerContainer {
9
public class LayerContainer<T> {
10 10

  
11
    private final List<Layer> layers = new CopyOnWriteArrayList<>();
11
    private final List<Layer<T>> layers = new CopyOnWriteArrayList<>();
12 12

  
13
    final void updateLayers(final VisCanvas visCanvas) {
14
        for (Layer layer : layers) {
15
            layer.paint(visCanvas);
13
    final void updateLayers(VisCanvas visCanvas, Point2dAdapter<T> adapter) {
14
        for (Layer<T> layer : layers) {
15
            layer.paint(visCanvas, adapter);
16 16
        }
17 17
    }
18 18

  
19
    public void addLayer(Layer layer) {
19
    public void addLayer(Layer<T> layer) {
20 20
        if (!layers.contains(layer)) {
21 21
            layers.add(layer);
22 22
        }
src/main/java/cz/agents/alite/visualizer2d/VisCanvas.java
12 12
    private final AffineTransform worldAffineTransform;
13 13
    private final AffineTransform originalTransform;
14 14
    private final Graphics2D canvas;
15
    private final Rectangle bounds;
15 16

  
16
    public VisCanvas(AffineTransform worldAffineTransform, Graphics2D canvas) {
17
    public VisCanvas(AffineTransform worldAffineTransform, Graphics2D canvas, Rectangle bounds) {
18
        this.bounds = bounds;
19
        this.canvas = canvas;
20

  
17 21
        this.originalTransform = canvas.getTransform();
18 22
        this.worldAffineTransform = new AffineTransform(originalTransform);
19 23
        this.worldAffineTransform.concatenate(worldAffineTransform);
20
        this.canvas = canvas;
21 24
    }
22 25

  
23 26
    public final Graphics2D getWorldCanvas() {
......
35 38
        }
36 39
        return canvas;
37 40
    }
41

  
42
    public Rectangle getBounds() {
43
        return bounds;
44
    }
38 45
}
src/main/java/cz/agents/alite/visualizer2d/VisPane.java
2 2

  
3 3
import javax.swing.*;
4 4
import java.awt.*;
5
import java.awt.event.ComponentAdapter;
6
import java.awt.event.ComponentEvent;
5 7
import java.awt.geom.AffineTransform;
6 8
import java.awt.geom.NoninvertibleTransformException;
7 9
import java.awt.geom.Point2D;
......
12 14
/**
13 15
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
14 16
 */
15
public class VisPane {
17
public final class VisPane<T> {
16 18

  
17 19
    private AffineTransform transform;
18 20

  
19 21
    private static final int REFRESH_IN_MS = 40; //25 FPS
20 22
    private static final int VIS_THREAD_PRIORITY = Thread.MIN_PRIORITY;
21 23

  
22
    private final LayerContainer layerContainer = new LayerContainer();
24
    //TODO solve volatile vs synchronized
25
    private volatile LayerContainer<T> layerContainer;
26
    private volatile Point2dAdapter<T> adapter;
23 27

  
24 28
    private boolean reinitializeBuffers = true;
25 29
    private BufferStrategy strategy;
......
28 32
    private final JPanel panel = new JPanel();
29 33
    private final Canvas canvas = new Canvas();
30 34

  
31
    public VisPane() {
35
    public VisPane(LayerContainer<T> layerContainer, Point2dAdapter<T> adapter) {
36
        this.layerContainer = layerContainer;
37
        this.adapter = adapter;
38

  
32 39
        transform = new AffineTransform();
33 40
        VisPaneMouseListener mouseListener = new VisPaneMouseListener(this);
34 41
        canvas.addMouseListener(mouseListener);
35 42
        canvas.addMouseMotionListener(mouseListener);
36 43
        canvas.addMouseWheelListener(mouseListener);
37 44
        canvas.addKeyListener(new VisPaneKeyListener(this));
38
        canvas.setBounds(0, 0, 1024, 768);
39 45
        panel.add(canvas);
46

  
47
        panel.addComponentListener(new ComponentAdapter() {
48
            @Override
49
            public void componentResized(ComponentEvent e) {
50
                synchronized (VisPane.this) {
51
                    reinitializeBuffers = true;
52
                    canvas.setBounds(panel.getBounds());
53
                }
54
            }
55
        });
40 56
    }
41 57

  
42 58
    public void start() {
......
48 64
        return panel;
49 65
    }
50 66

  
51
    public void registerLayer(Layer layer) {
52
        layerContainer.addLayer(layer);
67
    public Point2dAdapter<T> getAdapter() {
68
        return adapter;
53 69
    }
54 70

  
55
    private boolean reinitializeBuffers() {
56
        if (reinitializeBuffers) {
57
            reinitializeBuffers = false;
58

  
59
            canvas.createBufferStrategy(2);
60
            strategy = canvas.getBufferStrategy();
61

  
62
            graphics = (Graphics2D) strategy.getDrawGraphics();
63
            graphics.setColor(Color.WHITE);
64
            graphics.setBackground(Color.BLACK);
65

  
66
            return true;
67
        }
68

  
69
        return false;
71
    public void setAdapter(Point2dAdapter<T> adapter) {
72
        this.adapter = adapter;
70 73
    }
71 74

  
72
    private void update() {
73
        if (canvas.isDisplayable()) {
74
            reinitializeBuffers();
75

  
76
            AffineTransform originalTransform = graphics.getTransform();
77
            AffineTransform affineTransform = calculateAffineTransform();
78
            VisCanvas visCanvas = new VisCanvas(affineTransform, graphics);
79

  
80
            layerContainer.updateLayers(visCanvas);
81

  
82
            graphics.setTransform(originalTransform);
83
            strategy.show();
84
        }
75
    public LayerContainer<T> getLayerContainer() {
76
        return layerContainer;
85 77
    }
86 78

  
87
    private synchronized AffineTransform calculateAffineTransform() {
88
        return new AffineTransform(transform);
79
    public void setLayerContainer(LayerContainer<T> layerContainer) {
80
        this.layerContainer = layerContainer;
89 81
    }
90 82

  
91 83
    public final void translate(int deltaX, int deltaY) {
......
133 125
            }
134 126
        }
135 127
    }
128

  
129
    private void update() {
130
        if (canvas.isDisplayable()) {
131
            reinitializeBuffers();
132

  
133
            AffineTransform originalTransform = graphics.getTransform();
134
            AffineTransform affineTransform = calculateAffineTransform();
135
            VisCanvas visCanvas = new VisCanvas(affineTransform, graphics, panel.getBounds());
136

  
137
            layerContainer.updateLayers(visCanvas, adapter);
138

  
139
            graphics.setTransform(originalTransform);
140
            strategy.show();
141
        }
142
    }
143

  
144
    private boolean reinitializeBuffers() {
145
        if (reinitializeBuffers) {
146
            reinitializeBuffers = false;
147

  
148
            canvas.createBufferStrategy(2);
149
            strategy = canvas.getBufferStrategy();
150

  
151
            graphics = (Graphics2D) strategy.getDrawGraphics();
152
            graphics.setColor(Color.WHITE);
153
            graphics.setBackground(Color.BLACK);
154

  
155
            return true;
156
        }
157

  
158
        return false;
159
    }
160

  
161
    private synchronized AffineTransform calculateAffineTransform() {
162
        return new AffineTransform(transform);
163
    }
136 164
}
src/main/java/cz/agents/alite/visualizer2d/Visualizable.java
1
package cz.agents.alite.visualizer2d;
2

  
3
import java.awt.*;
4

  
5
/**
6
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
7
 */
8
public interface Visualizable {
9

  
10
    public void paint(Graphics2D canvas);
11

  
12
}
src/main/java/cz/agents/alite/visualizer2d/VisualizableLayer.java
1
package cz.agents.alite.visualizer2d;
2

  
3
import java.awt.*;
4

  
5
/**
6
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
7
 */
8
public class VisualizableLayer implements Layer {
9

  
10
    private final VisualizableProvider provider;
11

  
12
    public VisualizableLayer(VisualizableProvider provider) {
13
        this.provider = provider;
14
    }
15

  
16
    //TODO check if forEach is as fast as for each cycle
17
    @Override
18
    public void paint(VisCanvas canvas) {
19
        final Graphics2D worldCanvas = canvas.getWorldCanvas();
20
        provider.getData().forEach(element -> element.paint(worldCanvas));
21
    }
22
}
src/main/java/cz/agents/alite/visualizer2d/VisualizableProvider.java
1
package cz.agents.alite.visualizer2d;
2

  
3
/**
4
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
5
 */
6
public interface VisualizableProvider {
7

  
8
    public Iterable<? extends Visualizable> getData();
9

  
10
}
src/main/java/cz/agents/alite/visualizer2d/demo/Demo.java
1 1
package cz.agents.alite.visualizer2d.demo;
2 2

  
3
import cz.agents.alite.visualizer2d.LayerContainer;
4
import cz.agents.alite.visualizer2d.Point2dAdapter;
3 5
import cz.agents.alite.visualizer2d.VisPane;
4
import cz.agents.alite.visualizer2d.VisualizableLayer;
5
import cz.agents.alite.visualizer2d.implementation.ColorLayer;
6
import cz.agents.alite.visualizer2d.implementation.Point;
6
import cz.agents.alite.visualizer2d.layers.ColorLayer;
7
import cz.agents.alite.visualizer2d.layers.elements.ElementsLayer;
8
import cz.agents.alite.visualizer2d.layers.elements.PointElement;
7 9

  
8 10
import javax.swing.*;
9 11
import javax.vecmath.Point2d;
10 12
import java.awt.*;
11 13
import java.util.Arrays;
12 14

  
13
import static cz.agents.alite.visualizer2d.Point2dAdapter.IDENTITY;
14

  
15 15
/**
16 16
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
17 17
 */
......
20 20

  
21 21
    public static void main(String[] args) {
22 22
        final AngleProvider angleProvider = new AngleProvider();
23

  
24
        LayerContainer<Point2d> layers = new LayerContainer<>();
25
        layers.addLayer(ColorLayer.create(Color.BLACK));
26
        layers.addLayer(ElementsLayer.create(() -> Arrays.asList(
27
                new PointElement<>(new Point2d(AngleProvider.TRANS_X, AngleProvider.TRANS_Y), 3, Color.RED),
28
                new PointElement<>(angleProvider.getPoint(), 3, Color.WHITE),
29
                new PointElement<>(new Point2d(AngleProvider.TRANS_X + 25, AngleProvider.TRANS_Y), 3, Color.GREEN))
30
        ));
31
        VisPane<Point2d> visPane = new VisPane<>(layers, Point2dAdapter.IDENTITY);
23 32
        JFrame frame = new JFrame("Visualizer2d Demo");
24 33
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
25 34
        frame.setSize(1024, 768);
26
        //frame.setLayout(new GridLayout(1, 1));
27 35

  
28
        VisPane visPane = new VisPane();
29 36
        frame.setContentPane(visPane.getPanel());
30 37

  
31
        visPane.registerLayer(new ColorLayer(Color.BLACK));
32
        visPane.registerLayer(new VisualizableLayer(() -> Arrays.asList(
33
                new Point<>(new Point2d(AngleProvider.TRANS_X, AngleProvider.TRANS_Y), 3, Color.RED, IDENTITY),
34
                new Point<>(angleProvider.getPoint(), 3, Color.WHITE, IDENTITY),
35
                new Point<>(new Point2d(AngleProvider.TRANS_X+25, AngleProvider.TRANS_Y), 3, Color.GREEN, IDENTITY))));
36 38
        visPane.start();
37 39
        frame.setVisible(true);
38 40
        //frame.pack();
src/main/java/cz/agents/alite/visualizer2d/implementation/ColorLayer.java
1
package cz.agents.alite.visualizer2d.implementation;
2

  
3
import cz.agents.alite.visualizer2d.Layer;
4
import cz.agents.alite.visualizer2d.VisCanvas;
5

  
6
import java.awt.*;
7

  
8
/**
9
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
10
 */
11
public class ColorLayer implements Layer {
12

  
13
    private final Color color;
14

  
15
    public ColorLayer(Color color) {
16
        this.color = color;
17
    }
18

  
19
    @Override
20
    public void paint(VisCanvas canvas) {
21
        Graphics2D graphics = canvas.getOriginalCanvas();
22
        graphics.setColor(color);
23
        Rectangle rectangle = graphics.getClipBounds();
24
        graphics.fillRect(0, 0, 1024, 768);
25
    }
26
}
src/main/java/cz/agents/alite/visualizer2d/implementation/Point.java
1
package cz.agents.alite.visualizer2d.implementation;
2

  
3
import cz.agents.alite.visualizer2d.Point2dAdapter;
4
import cz.agents.alite.visualizer2d.Visualizable;
5

  
6
import javax.vecmath.Point2d;
7
import java.awt.*;
8
import java.awt.geom.Ellipse2D;
9

  
10
/**
11
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
12
 */
13
public class Point<T> implements Visualizable {
14

  
15
    private final T centerPosition;
16
    private final int radius;
17
    private final Point2dAdapter<T> adapter;
18
    private final Color color;
19

  
20
    public Point(T centerPosition, int radius, Color color, Point2dAdapter<T> adapter) {
21
        this.centerPosition = centerPosition;
22
        this.radius = radius;
23
        this.adapter = adapter;
24
        this.color = color;
25
    }
26

  
27
    @Override
28
    public void paint(Graphics2D canvas) {
29
        Point2d center = adapter.convert(centerPosition);
30
        canvas.setColor(color);
31

  
32
        Ellipse2D point = new Ellipse2D.Double(center.x - radius, center.y - radius,
33
                2 * radius + 1, 2 * radius + 1);
34
        canvas.fill(point);
35
    }
36
}
src/main/java/cz/agents/alite/visualizer2d/layers/ColorLayer.java
1
package cz.agents.alite.visualizer2d.layers;
2

  
3
import cz.agents.alite.visualizer2d.Layer;
4
import cz.agents.alite.visualizer2d.Point2dAdapter;
5
import cz.agents.alite.visualizer2d.VisCanvas;
6

  
7
import java.awt.*;
8

  
9
/**
10
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
11
 */
12
public class ColorLayer<T> implements Layer<T> {
13

  
14
    public static <T> ColorLayer<T> create(Color color) {
15
        return new ColorLayer<>(color);
16
    }
17

  
18
    private final Color color;
19

  
20
    private ColorLayer(Color color) {
21
        this.color = color;
22
    }
23

  
24
    @Override
25
    public void paint(VisCanvas canvas, Point2dAdapter<T> adapter) {
26
        Graphics2D graphics = canvas.getOriginalCanvas();
27
        graphics.setColor(color);
28
        Rectangle rectangle = canvas.getBounds();
29
        graphics.fill(rectangle);
30
    }
31
}
src/main/java/cz/agents/alite/visualizer2d/layers/elements/Element.java
1
package cz.agents.alite.visualizer2d.layers.elements;
2

  
3
import cz.agents.alite.visualizer2d.Point2dAdapter;
4

  
5
import java.awt.*;
6

  
7
/**
8
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
9
 */
10
public interface Element<T> {
11

  
12
    public void paint(Graphics2D canvas, Point2dAdapter<T> adapter);
13

  
14
}
src/main/java/cz/agents/alite/visualizer2d/layers/elements/ElementsLayer.java
1
package cz.agents.alite.visualizer2d.layers.elements;
2

  
3
import cz.agents.alite.visualizer2d.Layer;
4
import cz.agents.alite.visualizer2d.Point2dAdapter;
5
import cz.agents.alite.visualizer2d.VisCanvas;
6

  
7
import java.awt.*;
8
import java.util.Arrays;
9
import java.util.List;
10

  
11
/**
12
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
13
 */
14
public class ElementsLayer<T> implements Layer<T> {
15

  
16
    @SafeVarargs
17
    public static <T> Layer<T> create(Element<T>... elements) {
18
        List<Element<T>> pointList = Arrays.asList(elements);
19
        return create(() -> pointList);
20
    }
21

  
22
    public static <T> Layer<T> create(ElementsProvider<T> provider) {
23
        return new ElementsLayer<>(provider);
24
    }
25

  
26
    private final ElementsProvider<T> provider;
27

  
28
    private ElementsLayer(ElementsProvider<T> provider) {
29
        this.provider = provider;
30
    }
31

  
32
    //TODO check if forEach is as fast as for each cycle
33
    @Override
34
    public void paint(VisCanvas canvas, Point2dAdapter<T> adapter) {
35
        final Graphics2D worldCanvas = canvas.getWorldCanvas();
36
        provider.getElements().forEach(element -> element.paint(worldCanvas, adapter));
37
    }
38
}
src/main/java/cz/agents/alite/visualizer2d/layers/elements/ElementsProvider.java
1
package cz.agents.alite.visualizer2d.layers.elements;
2

  
3
/**
4
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
5
 */
6
public interface ElementsProvider<T> {
7

  
8
    public Iterable<? extends Element<T>> getElements();
9

  
10
}
src/main/java/cz/agents/alite/visualizer2d/layers/elements/PointElement.java
1
package cz.agents.alite.visualizer2d.layers.elements;
2

  
3
import cz.agents.alite.visualizer2d.Point2dAdapter;
4

  
5
import javax.vecmath.Point2d;
6
import java.awt.*;
7
import java.awt.geom.Ellipse2D;
8

  
9
/**
10
 * @author Ondrej Hrstka (ondrej.hrstka at agents.fel.cvut.cz)
11
 */
12
public class PointElement<T> implements Element<T> {
13

  
14
    private final T centerPosition;
15
    private final int radius;
16
    private final Color color;
17

  
18
    public PointElement(T centerPosition, int radius, Color color) {
19
        this.centerPosition = centerPosition;
20
        this.radius = radius;
21
        this.color = color;
22
    }
23

  
24
    @Override
25
    public void paint(Graphics2D canvas, Point2dAdapter<T> adapter) {
26
        Point2d center = adapter.convert(centerPosition);
27
        canvas.setColor(color);
28

  
29
        Ellipse2D point = new Ellipse2D.Double(center.x - radius, center.y - radius,
30
                2 * radius + 1, 2 * radius + 1);
31
        canvas.fill(point);
32
    }
33
}

Also available in: Unified diff