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