8 Replies - 1822 Views - Last Post: 15 November 2012 - 09:29 AM Rate Topic: -----

#1 AaronHopkins  Icon User is offline

  • D.I.C Head

Reputation: -1
  • View blog
  • Posts: 180
  • Joined: 01-March 11

Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 11:38 AM

I am currently trying to write a program that draws a clock face with a time that a user enters in two text fields (one for the hours, one for the minutes). I am pretty sure my code is correct, but for some reason when I run it, the frame doesn't show the 2 text fields where the user is supposed to enter the time.

import javax.swing.JFrame;
/**
 * This program displays a clock face with a time
 * the the user specified.
 */
public class ClockViewer {
	public static void main (String[] args) {		
		JFrame frame = new ClockViewerFrame();
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.setTitle("ClockViewer");
                frame.setVisible(true);
	}
}


import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JComponent;
import java.util.Random;
import java.awt.geom.Line2D;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Point2D;
/**
 * This programs draws a clock based on the hour and minutes.
 */
public class ClockViewerComponent extends JComponent {
   
   private double hours;
   private double minutes;
   private final double RADIUS = 100;
   private final double MINUTES_PER_HOUR = 60;
   private final double HOURS_PER_DAY = 12;
   private final double HOUR_HAND = 75;
   private final double MINUTE_HAND = 90;
   /**
    * Initilizes the component with a default time of 12:00.
    */
   public ClockViewerComponent() {
      hours = 12;
      minutes = 0;
   }
   
   /**
    * Sets the time of the clock.
    * @param anHour the hour
    * @param aMinute the minute(s)
    */
   public void setHourAndMinute(double anHour, double aMinute) {
      minutes = aMinute;
      hours = anHour;
   }
   
   /**
    * Paints the clock within the JFrame.
    */
   public void paintComponent(Graphics g) {
      
      Graphics2D g2 = (Graphics2D) g;
      
      Ellipse2D.Double face = new Ellipse2D.Double(0, 0, 2 * RADIUS,
         2 * RADIUS);
      g2.draw(face);
      Point2D.Double center = new Point2D.Double(RADIUS, RADIUS);
      double angle = Math.PI /2 - 2 * Math.PI * minutes / MINUTES_PER_HOUR;
      Point2D.Double minutePoint = new Point2D.Double(RADIUS + MINUTE_HAND
         * Math.cos(angle), RADIUS - MINUTE_HAND * Math.sin(angle));
      Line2D.Double minuteHand = new Line2D.Double(center, minutePoint);
      g2.draw(minuteHand);
      angle = Math.PI / 2 - 2 * Math.PI * (hours * MINUTES_PER_HOUR +
         minutes) / (MINUTES_PER_HOUR * HOURS_PER_DAY);
      Point2D.Double hourPoint = new Point2D.Double(RADIUS + HOUR_HAND *
         Math.cos(angle), RADIUS - HOUR_HAND * Math.sin(angle));
      Line2D.Double hourHand = new Line2D.Double(center, hourPoint);
      g2.draw(hourHand);
   }
}


import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JComponent;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
/**
 * This program creates a template JFrame for our clock.
 */
public class ClockViewerFrame extends JFrame {
   private JLabel hourLabel;
   private JLabel minuteLabel;
   private JTextField hourField;
   private JTextField minuteField;
   private JButton button;
   private JPanel panel;
   private final int FRAME_WIDTH = 400;
   private final int FRAME_HEIGHT = 400;
   
   final ClockViewerComponent component;
   
   /**
    * Initializes the framer with the ClockViewer component,
    * helper methods, and the frame size.
    */
   public ClockViewerFrame() {
      component = new ClockViewerComponent();
      createTextField();
      createButton();
      createPanel();
      setSize(FRAME_WIDTH, FRAME_HEIGHT);
   }
   /**
    * Creates the label and text field for the user to read,
    * and input desired values.
    */
   public void createTextField() {
      final int FIELD_WIDTH = 5;
      
      hourLabel = new JLabel("Hour = ");
      hourField = new JTextField(FIELD_WIDTH);
      hourField.setText("");
      
      minuteLabel = new JLabel("Minute = ");
      minuteField = new JTextField(FIELD_WIDTH);
      minuteField.setText("");
   }
   
   /**
    * Creates the button the user clicks when finishing entering input,
    * Takes the input and passes it to the component.
    */
   public void createButton() {
      button = new JButton("Draw");
      
      class DrawListener implements ActionListener {
         public void actionPerformed(ActionEvent event) {
            double hour = Double.parseDouble(hourField.getText());
            double minute = Double.parseDouble(minuteField.getText());
            component.setHourAndMinute(hour, minute);
            component.repaint();
            component.setPreferredSize(new Dimension (325, 325));
         }
      }
      ActionListener listener = new DrawListener();
      button.addActionListener(listener);       
   }
   
   /**
    * Adds the panel and adds each part to it.
    */
   private void createPanel() {
      panel = new JPanel(new BorderLayout());
      JPanel controlPanel = new JPanel();
      panel.add(hourLabel);
      panel.add(hourField);
      panel.add(minuteLabel);
      panel.add(minuteField);
      panel.add(button);
      panel.add(controlPanel, BorderLayout.NORTH);
      panel.add(component,BorderLayout.CENTER);
      add(panel);
   }
}


Is This A Good Question/Topic? 0
  • +

Replies To: Clock Face GUI, 2 Text Fields

#2 Swillis57  Icon User is offline

  • New D.I.C Head

Reputation: 8
  • View blog
  • Posts: 31
  • Joined: 14-January 11

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 12:36 PM

When you create your fields using createTextField(), you're not actually adding it to the frame. You're creating the field, but it gets garbage collected as soon as the method ends because there are no references outside of that method.

What you could do, is add a
this.add(hourfield); 
this.add(minutefield);



to the end of your createTextField() method. That will create and add the text fields to the ClockFrame object automatically when the constructor is called. You could also do the same thing for the relevant labels, if those are also broken.
Was This Post Helpful? 0
  • +
  • -

#3 AaronHopkins  Icon User is offline

  • D.I.C Head

Reputation: -1
  • View blog
  • Posts: 180
  • Joined: 01-March 11

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 12:42 PM

I added that just right now & it still didn't work.
Was This Post Helpful? 0
  • +
  • -

#4 pbl  Icon User is offline

  • There is nothing you can't do with a JTable
  • member icon

Reputation: 8346
  • View blog
  • Posts: 31,908
  • Joined: 06-March 08

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 02:38 PM

Same mistake as previous post
You never added your ClockViewerComonent component to the JFrame
Was This Post Helpful? 0
  • +
  • -

#5 AaronHopkins  Icon User is offline

  • D.I.C Head

Reputation: -1
  • View blog
  • Posts: 180
  • Joined: 01-March 11

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 05:29 PM

I don't really follow & don't really see where to add the ClockViewerComonent component.
Was This Post Helpful? 0
  • +
  • -

#6 AaronHopkins  Icon User is offline

  • D.I.C Head

Reputation: -1
  • View blog
  • Posts: 180
  • Joined: 01-March 11

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 08:03 PM

I modified my createPanel() method & it works, but the clock ends up at the very bottom of the frame when in reality, it should be just right under the 2 text fields. Any ideas on how to fix this?

panel = new JPanel();
	      JPanel inputPanel = new JPanel ();
	      panel.setLayout (new GridLayout (2, 1));
	      inputPanel.add(hourLabel);
	      inputPanel.add(hourField);
	      inputPanel.add(minuteLabel);
	      inputPanel.add(minuteField);
	      inputPanel.add(button);
	      panel.add (inputPanel);
	      panel.add(component);
	      this.getContentPane ().add(panel);

Was This Post Helpful? 0
  • +
  • -

#7 pbl  Icon User is offline

  • There is nothing you can't do with a JTable
  • member icon

Reputation: 8346
  • View blog
  • Posts: 31,908
  • Joined: 06-March 08

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 08:16 PM

Quote

it should be just right under the 2 text fields


This is what you claim, or wish :)

How to mix everbody !!!
           panel = new JPanel();  
           JPanel inputPanel = new JPanel ();  
           panel.setLayout (new GridLayout (2, 1));  



OK inputPanel is a FlowLayout
panel a GridLayout(2,1) so split into 2 equal parts verticaly

the labels and fiels and buttons are on the top half
the ClockViewerComponet in the bottom half

this ClockViewerComponent drws itself based on RADIUS which is a contant coming from a definition that may have nothing to do with the actual GridLayout bottom half size
Was This Post Helpful? 0
  • +
  • -

#8 AaronHopkins  Icon User is offline

  • D.I.C Head

Reputation: -1
  • View blog
  • Posts: 180
  • Joined: 01-March 11

Re: Clock Face GUI, 2 Text Fields

Posted 14 November 2012 - 08:22 PM

Really? What was your first solution that you told me in that I never added your ClockViewerComonent component to the JFrame?
Was This Post Helpful? 0
  • +
  • -

#9 pbl  Icon User is offline

  • There is nothing you can't do with a JTable
  • member icon

Reputation: 8346
  • View blog
  • Posts: 31,908
  • Joined: 06-March 08

Re: Clock Face GUI, 2 Text Fields

Posted 15 November 2012 - 09:29 AM

What doi you mean ?
It didn't appear because you didn't added it so you fixed that following my recommendation

Now you complaint that it is not where you want it, I told you your values like RADIUS are hardcoded. Have you try to resize your JFrame dragging one of its sides ? Your clock will always have the same size but at a certain moment it will be centered. So I just told you not to harcode value like RADIUS but rather calculate it based on the component getHeight() and getWidth() at run time in your paint() method.
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1