1 package npw; 2 3 import painter.SPainter; 4 import shapes.SCircle; 5 6 import javax.swing.*; 7 import java.awt.*; 8 import java.util.Random; 9 import java.util.Scanner; 10 11 public class HirstDots { 12 13 private void paintTheImage () { 14 //Get the input info 15 int radius = getNumber("circle radius"); 16 int diameter = getNumber("dot radius"); 17 18 //Establish the painter 19 SPainter painter = new SPainter("Hirst Dots", radius * 2 + 50, radius * 2 + 50); 20 painter.setBrushWidth(3); 21 SCircle circle = new SCircle(radius); 22 SCircle dot = new SCircle(diameter/2); 23 24 //Paint the dots 25 paintCircleOfDots(painter, circle, dot); 26 } 27 private void paintCircleOfDots(SPainter painter, SCircle circle, SCircle dot) { 28 //Position the painter to begin drawing the rows 29 painter.mfd(circle.radius()); 30 painter.tr(); 31 // Paint the circle of dots 32 double moved = 0; 33 while (moved < circle.diameter()) { 34 double chord = chordLength(circle.radius() - moved, circle); 35 int dots = dotOnLineCount(chord, dot.diameter()/2); 36 paintRow(painter, dot, dots); 37 nextRow(painter, (dot.diameter()/2)); 38 moved = moved + (dot.diameter()/2); 39 } 40 41 //Make the method invariant with respect to painter position 42 painter.tl(); 43 painter.mfd(circle.radius()); 44 } 45 //Move to the next row 46 private void nextRow(SPainter painter, double rowHeight) { 47 painter.tr(); 48 painter.mfd(rowHeight); 49 painter.tl(); 50 } 51 52 //Assumes the painter is at the center of the row to paint, facing right. 53 private void paintRow(SPainter painter, SCircle dot, int dotsToPaint){ 54 //Move backward 1/2 of the length we're painting to get ready to paint the row. 55 double centerOffset = ((dotsToPaint * dot.diameter()/4) - dot.diameter()/4); 56 painter.mbk(centerOffset); 57 58 //Paint the row of dots. 59 int painted = 0; 60 while (painted < dotsToPaint) { 61 paintOneDot(painter, dot); 62 painter.mfd(dot.diameter()/2); 63 painted = painted + 1; 64 } 65 66 //Make the method invariant with respect to painter position. 67 painter.mbk(centerOffset + (dot.diameter()/2)); 68 } 69 70 private void paintOneDot(SPainter painter, SCircle dot) { 71 dot.s3(); 72 painter.setColor(randomColor()); 73 painter.paint(dot); 74 dot.x3(); 75 } 76 77 private static int dotOnLineCount(double lineLength, double diameterLength) { 78 int dots = ((int)Math.ceil((lineLength - diameterLength) / diameterLength) + 1); 79 return dots; 80 } 81 82 private double chordLength(double yOffset, SCircle circle){ 83 double xLength = Math.sqrt(Math.pow(circle.radius(), 2) - Math.pow(yOffset, 2)); 84 double chordLength = xLength * 2; 85 return chordLength; 86 } 87 88 private static int getNumber(String prompt) { 89 String nss = JOptionPane.showInputDialog(null,prompt + "?"); 90 Scanner scanner = new Scanner(nss); 91 return scanner.nextInt(); 92 } 93 94 private static Color randomColor() { 95 Random rgen = new Random(); 96 int r = rgen.nextInt(256); 97 int g = rgen.nextInt(256); 98 int b = rgen.nextInt(256); 99 return new Color(r,g,b); 100 } 101 102 public HirstDots() { 103 paintTheImage(); 104 } 105 106 public static void main(String[] args) { 107 SwingUtilities.invokeLater(new Runnable() { 108 @Override 109 public void run() { 110 new HirstDots(); 111 } 112 }); 113 } 114 } 115