001 package ui.recognizer; 002 003 import java.awt.*; 004 import javax.swing.*; 005 import static java.lang.Math.*; 006 007 public class XRule extends Rule { 008 public static final int SIZE = 35; 009 010 ImageCoordinate[] imagePoints = null; // required 011 012 public XRule(boolean isDataUnits, Calibration aCalibration, ImageCoordinate[] someImagePoints) { 013 super(isDataUnits, aCalibration); 014 imagePoints = someImagePoints; 015 } 016 017 private int xmax, xmin, ymax, ymin; // data point extrema 018 019 /** Set the data points in image coordinate representation. 020 * Used for rendering a gray image version of plot in horizontal rule. 021 * @param someImagePoints an array of recognized plot points 022 */ 023 public void setImagePoints(ImageCoordinate[] someImagePoints) { 024 xmax = Integer.MIN_VALUE; // find maximum and minimum of points 025 xmin = Integer.MAX_VALUE; 026 ymax = Integer.MIN_VALUE; 027 ymin = Integer.MAX_VALUE; 028 for (ImageCoordinate point : someImagePoints) { 029 int x = (int) point.getX(); 030 xmax = max(xmax, x); 031 xmin = min(xmin, x); 032 int y = (int) point.getY(); 033 if (y != 0) { // zero encodes that no data is available 034 ymax = max(ymax, y); 035 ymin = min(ymin, y); 036 } 037 } 038 repaint(); 039 } 040 041 public void setPreferredWidth(int pw) { 042 setPreferredSize(new Dimension(pw, SIZE)); 043 } 044 045 public void paintComponent(Graphics g) { 046 Rectangle drawHere = g.getClipBounds(); 047 048 // Fill clipping area with neutral gray 049 g.setColor(Color.gray); 050 g.fillRect(drawHere.x, drawHere.y, drawHere.width, drawHere.height); 051 052 // Use clipping bounds to calculate first tick and last tick location. 053 054 int start = (drawHere.x / increment) * increment; 055 int end = (((drawHere.x + drawHere.width) / increment) + 1) * increment; 056 057 // ticks and labels 058 int tickLength = 0; 059 String text = null; 060 061 if (imagePoints != null) { 062 int localymax = Integer.MIN_VALUE; 063 int localymin = Integer.MAX_VALUE; 064 for (int i = drawHere.x; i < imagePoints.length && i < (drawHere.x + drawHere.width); i++) { 065 ImageCoordinate point = imagePoints[i]; 066 int y = (int) point.getY(); 067 if (y != 0) { 068 localymax = max(localymax, y); 069 localymin = min(localymin, y); 070 } 071 } 072 if ((localymax - localymin) == 0) localymax = localymin+1; 073 for (int i = drawHere.x; i < imagePoints.length && i < (drawHere.x + drawHere.width); i++) { 074 ImageCoordinate point = imagePoints[i]; 075 int y = (int) point.getY(); 076 float intensity; 077 if (y == 0) intensity = 0.0f; 078 else intensity = (float) (localymax - y) / (float) (localymax - localymin); 079 080 if (intensity < 0.0f) intensity = 0.0f; 081 if (intensity > 1.0f) intensity = 1.0f; 082 g.setColor(new Color(intensity, intensity, intensity)); 083 g.drawLine(i, 0, i, SIZE-1); 084 } 085 086 } 087 088 // Do the ruler labels in a small font that's black. 089 g.setFont(new Font("SansSerif", Font.PLAIN, 10)); 090 g.setColor(Color.red); 091 092 for (int i = start; i < end; i += increment) { 093 if (i % units == 0) { 094 tickLength = 10; 095 text = Integer.toString(i/units); 096 } else { 097 tickLength = 7; 098 text = null; 099 } 100 101 if (tickLength != 0) { 102 g.drawLine(i, SIZE-1, i, SIZE-tickLength-1); 103 if (text != null) g.drawString(text, i-3, 21); 104 105 } 106 } 107 } 108 }