Bug 9031 fixed: Misalignment when using xstring with a matrix
[scilab.git] / scilab / modules / scirenderer / src / org / scilab / forge / scirenderer / implementation / g2d / texture / G2DTextureDrawingTools.java
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) 2009-2011 - DIGITEO - Pierre Lando
4  *
5  * This file must be used under the terms of the CeCILL.
6  * This source file is licensed as described in the file COPYING, which
7  * you should have received as part of this distribution.  The terms
8  * are also available at
9  * http://www.cecill.info/licences/Licence_CeCILL_V2.1-en.txt
10  */
11
12 package org.scilab.forge.scirenderer.implementation.g2d.texture;
13
14 import org.scilab.forge.scirenderer.implementation.g2d.motor.G2DStroke;
15 import org.scilab.forge.scirenderer.implementation.g2d.texture.G2DTextureManager;
16 import org.scilab.forge.scirenderer.shapes.appearance.Appearance;
17 import org.scilab.forge.scirenderer.shapes.appearance.Color;
18 import org.scilab.forge.scirenderer.texture.Texture;
19 import org.scilab.forge.scirenderer.texture.TextureDrawer;
20 import org.scilab.forge.scirenderer.texture.TextureDrawingTools;
21 import org.scilab.forge.scirenderer.texture.TextEntity;
22
23 import javax.swing.Icon;
24 import javax.swing.JLabel;
25 import java.awt.Dimension;
26 import java.awt.Graphics2D;
27 import java.awt.RenderingHints;
28 import java.awt.font.TextLayout;
29 import java.awt.geom.Ellipse2D;
30 import java.awt.geom.Rectangle2D;
31
32 /**
33  *
34  * Implementation of {@link TextureDrawingTools}.
35  * This implementation create a {@link TextureBufferedImage} an fill it with sprite drawing.
36  *
37  * @author Pierre Lando
38  */
39 public class G2DTextureDrawingTools implements TextureDrawingTools {
40
41     private Graphics2D g2d;
42     private int width;
43     private int height;
44
45     /**
46      * Default constructor.
47      * @param width the image width.
48      * @param height the image height.
49      * @param useSquareTexture true if square texture is needed.
50      */
51     public G2DTextureDrawingTools(Graphics2D g2d) {
52         this.g2d = g2d;
53     }
54
55     public void setGraphics(Graphics2D g2d) {
56         this.g2d = g2d;
57     }
58
59     public void accept(Texture texture) {
60         G2DTextureManager.G2DTexture t = (G2DTextureManager.G2DTexture) texture;
61         TextureDrawer drawer = t.getDrawer();
62         Dimension d = drawer.getTextureSize();
63         this.width = (int) d.getWidth();
64         this.height = (int) d.getHeight();
65         accept(drawer, this.width, this.height);
66     }
67
68     /**
69      * Ask this image to accept a sprite drawer.
70      * This image will contain the drawing of the given drawer.
71      * @param spriteDrawer the given sprite drawer.
72      */
73     public void accept(TextureDrawer textureDrawer, int width, int height) {
74         // Change center coordinate to (0, 0).
75         if (textureDrawer.getOriginPosition() == TextureDrawer.OriginPosition.CENTER) {
76             g2d.translate(width / 2.0, height / 2.0);
77         }
78
79         boolean aa = g2d.getRenderingHint(RenderingHints.KEY_ANTIALIASING) == RenderingHints.VALUE_ANTIALIAS_ON;
80         if (!aa) {
81             g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
82         }
83         textureDrawer.draw(this);
84
85         if (!aa) {
86             g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);
87         }
88     }
89
90     @Override
91     public void drawPlus(int size, Appearance appearance) {
92         if (size > 1) {
93             int r = size / 2;
94             int[] coords1 = new int[] { -r, 0, r, 0};
95             int[] coords2 = new int[] {0, -r, 0, r};
96
97             drawPolyline(coords1, appearance);
98             drawPolyline(coords2, appearance);
99         } else {
100             fillDisc(0, 0, 1, appearance.getLineColor());
101         }
102     }
103
104     @Override
105     public void drawPolyline(int[] coordinates, Appearance appearance) {
106         if (coordinates.length == 2) {
107
108         }
109
110         int nbPoint = coordinates.length / 2;
111
112         int[] xCoordinates = new int[nbPoint];
113         int[] yCoordinates = new int[nbPoint];
114
115         int k = 0;
116         for (int i = 0; i < coordinates.length; i += 2) {
117             xCoordinates[k] = coordinates[i];
118             yCoordinates[k] = coordinates[i + 1];
119             k++;
120         }
121
122         g2d.setColor(appearance.getLineColor());
123         g2d.setStroke(G2DStroke.getStroke(appearance, 0));
124
125         g2d.drawPolyline(xCoordinates, yCoordinates, nbPoint);
126     }
127
128     @Override
129     public void fillPolygon(int[] coordinates, Appearance appearance) {
130         int nbPoint = coordinates.length / 2;
131
132         int[] xCoordinates = new int[nbPoint];
133         int[] yCoordinates = new int[nbPoint];
134
135         int k = 0;
136         for (int i = 0; i < coordinates.length; i += 2) {
137             xCoordinates[k] = coordinates[i];
138             yCoordinates[k] = coordinates[i + 1];
139             k++;
140         }
141
142         if (appearance.getFillColor().getAlphaAsFloat() != 0) {
143             g2d.setColor(appearance.getFillColor());
144             g2d.fillPolygon(xCoordinates, yCoordinates, nbPoint);
145         }
146
147         if (!appearance.getLineColor().equals(appearance.getFillColor())) {
148             int usedLength = coordinates.length - (coordinates.length % 2);
149             int[] borderCoordinate = new int[usedLength + 2];
150             System.arraycopy(coordinates, 0, borderCoordinate, 0, usedLength);
151             borderCoordinate[usedLength]     = coordinates[0];
152             borderCoordinate[usedLength + 1] = coordinates[1];
153
154             drawPolyline(borderCoordinate, appearance);
155         }
156     }
157
158     @Override
159     public void drawCircle(int x, int y, int diameter, Appearance appearance) {
160         g2d.setColor(appearance.getLineColor());
161         g2d.setStroke(G2DStroke.getStroke(appearance, 0));
162         double r = ((double) diameter) / 2;
163         g2d.draw(new Ellipse2D.Double(x - r, y - r, diameter, diameter));
164     }
165
166     @Override
167     public void fillDisc(int x, int y, int diameter, Color color) {
168         if (color.getAlphaAsFloat() != 0) {
169             g2d.setColor(color);
170             double r = ((double) diameter) / 2;
171             g2d.fill(new Ellipse2D.Double(x - r, y - r, diameter, diameter));
172         }
173     }
174
175     @Override
176     public void draw(TextEntity textEntity, int x, int y) {
177         if (textEntity != null && textEntity.isValid()) {
178             if (textEntity.isTextAntiAliased()) {
179                 g2d.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
180             } else {
181                 g2d.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_OFF);
182             }
183
184             if (textEntity.isTextUseFractionalMetrics()) {
185                 g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
186             } else {
187                 g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_OFF);
188             }
189             g2d.setColor(textEntity.getTextColor());
190             TextLayout textLayout = new TextLayout(textEntity.getText(), textEntity.getFont(), g2d.getFontRenderContext());
191             Rectangle2D bounds = textLayout.getBounds();
192             g2d.setFont(textEntity.getFont());
193             g2d.drawString(textEntity.getText(), (float) (x - bounds.getX()), (float) (y + textLayout.getAscent()));
194         }
195     }
196
197     @Override
198     public void draw(Icon icon, int x, int y) {
199         icon.paintIcon(new JLabel(), g2d, x, y);
200     }
201
202     @Override
203     public void clear(Color color) {
204         g2d.setColor(color);
205         g2d.fillRect(0, 0, width, height);
206     }
207 }