[英]repaint method not working java
我有这段代码,我想让它重新绘制,以便当用户输入详细信息时,它会打印出加速度和油耗(在另一个类中计算),因为我有system.out.println来显示值,所以我可以看到它是有效的但它们不会更新到我的JFrame。
在另一个类的另一个构造函数中调用window(),JFrame可以正常打开,但不会更新
有任何想法吗?
谢谢
public class Vehicle extends JFrame {
protected static double horsepower;
protected static double aerodynamics;
protected static double weight;
protected static double acceleration;
protected static double topspeed;
protected double fuelconsumption;
protected String userHorsepower;
protected String userWeight;
protected String userTopspeed;
protected String userInput = "No Current Selection";
JPanel panel = new JPanel();
JButton Van = new JButton("Add Van");
public Vehicle(double horsepower, double weight, double aerodynamics, double topspeed){
super();
}
public void window(){
JButton Van = new JButton("Add Van Car");
Van.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
userHorsepower = JOptionPane.showInputDialog("Enter Horsepower");
horsepower = Double.parseDouble(userHorsepower);
userWeight = JOptionPane.showInputDialog("Enter Weight");
weight = Double.parseDouble(userWeight);
userTopspeed = JOptionPane.showInputDialog("Enter Topspeed");
topspeed = Double.parseDouble(userTopspeed);
aerodynamics = 0.9;
userInput = "Van";
TestConsumption.printVan();
repaint();
return;
}});
JButton SportCar = new JButton("Add Sports Car");
SportCar.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
userHorsepower = JOptionPane.showInputDialog("Enter Horsepower");
horsepower = Double.parseDouble(userHorsepower);
userWeight = JOptionPane.showInputDialog("Enter Weight");
weight = Double.parseDouble(userWeight);
userTopspeed = JOptionPane.showInputDialog("Enter Topspeed");
topspeed = Double.parseDouble(userTopspeed);
aerodynamics = 0.5;
userInput = "Sports Car";
TestConsumption.printCar();
panel.repaint();
}});
JLabel userChoice = new JLabel(userInput);
JLabel accel = new JLabel("Acceleration: " + acceleration);
JLabel fuel = new JLabel("Fuel Consumption: " + fuelconsumption);
panel.setLayout(new GridLayout(5,5,0,0));
panel.add(Van);
panel.add(SportCar);
panel.add(userChoice);
panel.add(accel);
panel.add(fuel);
add(panel);
pack();
setTitle("Title Here");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setResizable(true);
setSize(300,200);
setLocationRelativeTo(null);
setVisible(true);
repaint();
}
窗口在此类中被称为
public class TestConsumption extends Vehicle {
public TestConsumption(double horsepower, double weight, double aerodynamics, double topspeed) {
super(horsepower, weight, aerodynamics, topspeed);
}
public static void main(String [] args){
Vehicle vh = new Vehicle(500, 500, 500, 500);
vh.window();
}
public static void printCar(){
Vehicle Car = new SportCar(horsepower,weight,aerodynamics,topspeed);
Car.acceleration();
Car.showFuelConsumption();
}
public static void printVan(){
Vehicle FirstVan = new Van(horsepower,weight,aerodynamics,topspeed);
FirstVan.acceleration();
FirstVan.showFuelConsumption();
}
}
在constructor Vehicle(double horsepower, double weight, double aerodynamics, double topspeed)
调用window()
constructor Vehicle(double horsepower, double weight, double aerodynamics, double topspeed)
据我们所知,您永远不会更新JLabel的文本。 在为该标签计算新的对应值之后,需要在每个JLabel
上调用setText
。
但是,根据您的情况,您会在window()
方法中将JLabel
对象创建为局部范围变量,因此它们不再易于访问(从技术上讲,由于您已将它们添加到JPanel
,因此有一种访问它们的方法,但这就是不必要的麻烦)。
由于TestConsumption.printVan()
显然用于计算加速度和油耗,为了使生活更轻松,我建议将JLabel accel
和JLabel fuel
提升为实例变量,然后采用单独的方法来计算TestConsumption
的两个值。 因此,您的动作事件可能看起来像这样:
sportCar.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
userHorsepower = JOptionPane.showInputDialog("Enter Horsepower");
horsepower = Double.parseDouble(userHorsepower);
userWeight = JOptionPane.showInputDialog("Enter Weight");
weight = Double.parseDouble(userWeight);
userTopspeed = JOptionPane.showInputDialog("Enter Topspeed");
topspeed = Double.parseDouble(userTopspeed);
aerodynamics = 0.5;
userInput = "Sports Car";
// These static methods would be added to your TestConsumption class
acceleration = TestConsumption.calculateAcceleration(...whatever params required for this calculation...);
fuelConsumption = TestConsumption.calculateFuelConsumption(...whatever params required for this calculation...);
accel.setText("Acceleration: " + acceleration);
fuel.setText("Fuel Consumption: " + fuelConsumption);
panel.repaint();
}});
另外,您也不必将JLabel提升为实例变量。 只要在为两个按钮设置ActionListener
之前在window()
方法的顶部声明accel
和fuel
,它们就可以通过actionPerformed
方法的作用域附件在事件操作中访问。
一些注意事项:
请记住,变量名的Java命名约定是以小写字母开头。 因此,您的Van
和SportCar
变量应为van
和sportCar
。 我已经在示例中将它们写成这样。 从语法上讲,虽然它不会引起任何问题,但使人们一眼便知道是在看一个类还是在看变量名是很困难的。
据我所知,您的TestConsumption
类不需要扩展Vehicle
。 它不是车辆; 它似乎既是应用程序的起点,也是助手类(静态方法)。
这似乎是学校的任务,所以我不确定是否明确要求您以这种方式设计程序,但是从设计的角度来看,您正在将概念性的“视图”和“模型”组合在一起。 JFrame
不是车辆。 它是一个窗口,一个视图元素,用于帮助表示您的数据。 您可能会发现它将特定于车辆的字段和方法(例如acceleration
,最高topspeed
等)提取到一个名为Vehicle
的单独类中,将有助于清理代码,然后您可以将其与SportCar
和Van
子类化(您似乎按照TestConsumption
指示进行TestConsumption
。 您的JFrame
子类(我们称其为MainWindow
或类似名称)仅负责更新其数据表示形式(在这种情况下,这意味着我们的accel
和fuel
JLabel)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.