1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23 package org.utgenome.gwt.utgb.client.canvas;
24
25 import java.util.ArrayList;
26 import java.util.List;
27
28 import org.utgenome.gwt.utgb.client.UTGBEntryPointBase;
29 import org.utgenome.gwt.utgb.client.canvas.GWTGraphCanvas.GraphStyle;
30 import org.utgenome.gwt.utgb.client.track.TrackWindow;
31 import org.utgenome.gwt.widget.client.Style;
32
33 import com.google.gwt.core.client.JavaScriptException;
34 import com.google.gwt.user.client.ui.AbsolutePanel;
35 import com.google.gwt.user.client.ui.Composite;
36 import com.google.gwt.user.client.ui.Label;
37 import com.google.gwt.user.client.ui.Widget;
38 import com.google.gwt.widgetideas.graphics.client.Color;
39 import com.google.gwt.widgetideas.graphics.client.GWTCanvas;
40
41
42
43
44
45
46
47 public class GraphScale extends Composite {
48
49 private AbsolutePanel panel = new AbsolutePanel();
50 private GWTCanvas frameCanvas = new GWTCanvas();
51 private List<Widget> graphLabels = new ArrayList<Widget>();
52
53 public GraphScale() {
54 panel.add(frameCanvas, 0, 0);
55 initWidget(panel);
56 }
57
58 public void clearScaleBar() {
59 frameCanvas.clear();
60 }
61
62 public void clearScaleLabel() {
63 for (Widget each : graphLabels) {
64 each.removeFromParent();
65 }
66 graphLabels.clear();
67 }
68
69 public void clear() {
70 clearScaleBar();
71 clearScaleLabel();
72 }
73
74 public void draw(GraphStyle style, TrackWindow viewWindow) {
75
76
77 int width = viewWindow.getPixelWidth();
78 int height = style.windowHeight;
79 panel.setPixelSize(width, height);
80 frameCanvas.setPixelSize(width, height);
81 frameCanvas.setCoordSize(width, height);
82
83 ScalePainter scalePainter = new ScalePainter(style, viewWindow);
84 scalePainter.draw();
85
86 }
87
88 class ScalePainter {
89 private GraphStyle style;
90 private TrackWindow viewWindow;
91 private final Scale scale;
92 private final Indent indent;
93
94 public ScalePainter(GraphStyle style, TrackWindow window) {
95 this.style = style;
96 this.viewWindow = window;
97 scale = new Scale(style);
98 indent = createIndent();
99 }
100
101 public void draw() {
102 clear();
103 if (style.drawScale)
104 drawScale();
105
106 if (style.showScaleLabel)
107 drawScaleLabel();
108 }
109
110 public void drawScale() {
111
112
113 frameCanvas.saveContext();
114 frameCanvas.setStrokeStyle(new Color(0, 0, 0, 0.5f));
115 frameCanvas.setLineWidth(1.0f);
116 frameCanvas.beginPath();
117 frameCanvas.rect(0, 0, viewWindow.getPixelWidth(), style.windowHeight);
118 frameCanvas.stroke();
119 frameCanvas.restoreContext();
120
121
122 frameCanvas.saveContext();
123 frameCanvas.setStrokeStyle(Color.BLACK);
124 frameCanvas.setGlobalAlpha(0.2f);
125 frameCanvas.setLineWidth(0.5f);
126 for (int i = 0; i <= indent.nSteps; i++) {
127 float value = indent.getIndentValue(i);
128
129 frameCanvas.saveContext();
130 frameCanvas.beginPath();
131 frameCanvas.translate(0, scale.getYPosition(value) + 0.5d);
132 frameCanvas.moveTo(0d, 0d);
133 frameCanvas.lineTo(viewWindow.getPixelWidth(), 0);
134 frameCanvas.stroke();
135 frameCanvas.restoreContext();
136 }
137 {
138
139 frameCanvas.saveContext();
140 frameCanvas.beginPath();
141 frameCanvas.translate(0, scale.getYPosition(0f));
142 frameCanvas.moveTo(0, 0);
143 frameCanvas.lineTo(viewWindow.getPixelWidth(), 0);
144 frameCanvas.stroke();
145 frameCanvas.restoreContext();
146 }
147
148 frameCanvas.restoreContext();
149 }
150
151 public Indent createIndent() {
152 return new Indent(scale.getMin(), scale.getMax(), style);
153 }
154
155 public void drawScaleLabel() {
156
157 int fontHeight = 10;
158
159 for (int i = 0; i <= indent.nSteps; i++) {
160 float value = indent.getIndentValue(i);
161 String labelString = indent.getIndentString(i);
162 Label label = new Label(labelString);
163 label.setTitle(labelString);
164 Style.fontSize(label, fontHeight);
165 Style.textAlign(label, "left");
166 Style.fontColor(label, "#003366");
167
168 int labelX = 1;
169 int labelY = (int) (scale.getYPosition(value) - (fontHeight / 2.0f) - 1);
170
171 if (labelY < 0 && labelY > -fontHeight)
172 labelY = -1;
173
174 if (labelY > style.windowHeight - fontHeight) {
175 labelY = style.windowHeight - fontHeight;
176 }
177
178 graphLabels.add(label);
179 panel.add(label, labelX, labelY);
180 }
181 }
182
183 public class Indent {
184 public int exponent = 0;
185 public long fraction = 0;
186
187 public int nSteps = 0;
188
189 public float min = 0.0f;
190 public float max = 0.0f;
191
192 private GraphStyle style;
193
194 public Indent(float minValue, float maxValue, GraphStyle style) {
195 this.style = style;
196
197 final int indentHeight = 10;
198
199 min = minValue < maxValue ? minValue : maxValue;
200 max = minValue > maxValue ? minValue : maxValue;
201
202 if (style.logScale) {
203 min = scale.getLogValue(min);
204 max = scale.getLogValue(max);
205 }
206
207 try {
208 double tempIndentValue = (max - min) / style.windowHeight * indentHeight;
209
210 if (style.logScale && tempIndentValue < 1.0)
211 tempIndentValue = 1.0;
212
213 fraction = (long) Math.floor(Math.log10(tempIndentValue));
214 exponent = (int) Math.ceil(Math.round(tempIndentValue / Math.pow(10, fraction - 3)) / 1000.0);
215
216 if (exponent <= 5)
217 ;
218
219
220 else {
221 exponent = 1;
222 fraction++;
223 }
224 double stepSize = exponent * Math.pow(10, fraction);
225 max = (float) (Math.floor(max / stepSize) * stepSize);
226 min = (float) (Math.ceil(min / stepSize) * stepSize);
227
228 nSteps = (int) Math.abs((max - min) / stepSize);
229 }
230 catch (JavaScriptException e) {
231 UTGBEntryPointBase.showErrorMessage(e.getMessage());
232 }
233
234 }
235
236 public float getIndentValue(int step) {
237 double indentValue = min + (step * exponent * Math.pow(10, fraction));
238
239 if (!style.logScale)
240 return (float) indentValue;
241 else if (indentValue == 0.0f)
242 return 0.0f;
243 else if (indentValue >= 0.0f)
244 return (float) Math.pow(2, indentValue - 1);
245 else
246 return (float) -Math.pow(2, -indentValue - 1);
247 }
248
249 public String getIndentString(int step) {
250 float indentValue = getIndentValue(step);
251
252 if (indentValue == (int) indentValue)
253 return String.valueOf((int) indentValue);
254 else {
255 int exponent_tmp = (int) Math.ceil(Math.round(indentValue / Math.pow(10, fraction - 3)) / 1000.0);
256 int endIndex = String.valueOf(exponent_tmp).length() + 1;
257 if (fraction < 0)
258 endIndex -= fraction;
259 endIndex = Math.min(String.valueOf(indentValue).length(), endIndex);
260
261 return String.valueOf(indentValue).substring(0, endIndex);
262 }
263 }
264 }
265
266 }
267
268 }