* Copyright (c) 2012, 煙臺大學計算機學院學生
* All rights reserved.
* 作 者: 劉鎮
* 完成日期: 2012 年 11 月 09日
* 版 本 號: 2.013
* 對任務及求解方法的描述部分
* 問題描述:模擬一個信號燈的軟件。在JFrame的北面添加一個下拉列表,該下拉列表有“默認無信號”、“紅燈”、“綠燈”和“黃燈”選項。當用戶在下拉列表選擇某項後,產生相應的信號燈。
*代碼部分:
MySignal.java:
package lz_11w;
import java.awt.*;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.awt.image.ImageObserver;
import javax.swing.JFrame;
class MyCanvas extends Canvas
{
private int x, y, r;
private Color color;
public Color getColor() {
return color;
}
public void setColor(Color color) {
this.color = color;
}
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
public int getR() {
return r;
}
public void setR(int r) {
this.r = r;
}
MyCanvas()
{
setBackground(Color.white);
x = 300;
y = 50;
r = 0;
color = Color.white;
}
public void paint(Graphics g)
{
g.setColor(Color.black);
g.fillRect(290, 90, 120, 320);
g.setColor(color);
g.fillOval(x, y, r, r);
}
}
public class MySignal extends JFrame implements ItemListener{
Choice choice;
MyCanvas oval;
Panel panel;
MySignal()
{
this.setTitle("我的信號燈");
choice = new Choice();
choice.add("無信號");
choice.add("紅");
choice.add("黃");
choice.add("綠");
choice.addItemListener(this);
oval = new MyCanvas();
panel = new Panel();
panel.add(choice);
this.add(panel, BorderLayout.NORTH);
this.add(oval, BorderLayout.CENTER);
setBounds(300, 80, 750, 550);
setExtendedState(Frame.MAXIMIZED_VERT);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setVisible(true);
validate();
}
public void itemStateChanged(ItemEvent e) {
if(choice.getSelectedItem().equals("無信號"))
{
oval.setR(0);
oval.repaint();
}
else if(choice.getSelectedItem().equals("紅"))
{
oval.setY(100);
oval.setR(100);
oval.setColor(Color.red);
oval.repaint();
}
else if(choice.getSelectedItem().equals("黃"))
{
oval.setY(200);
oval.setR(100);
oval.setColor(Color.yellow);
oval.repaint();
}
else if(choice.getSelectedItem().equals("綠"))
{
oval.setY(300);
oval.setR(100);
oval.setColor(Color.green);
oval.repaint();
}
}
}
TestSignel.java:
package lz_11w;
public class TestSignal {
public static void main(String[] args) {
MySignal s = new MySignal();
}
}
測試結果:
心得經驗:
一、對於佈局的處理:我嘗試過開始用一段setLayout(new FlowLayout());設置佈局;結果只是顯示了choice控件的內容,後來發現是在add(,)中有設置了BorderLayout,因此一直產生了不能生成Canvas內容問題。
二、對於Panel:我嘗試過將Canvas放入一個畫布Panel中,將Choice放入另一個Panel中,並分別將兩個Panel添加到JFrame中;結果也是不能產生畫布內容;但如果將Canvas直接添加到JFrame,將一個包含Choice的畫布panel再加到JFrame中,問題就解決了。
三、涉及到處理時間問題:當選中某一個單選選項;就執行什麼算法,糾結於怎樣才能讓產生的圓動起來,後來發現不就可以通過修改位置,(Canvas中的paint()中的位置)來實現指示燈的變換;剩下的問題就是怎樣處理位置的座標:也產生了一點小小問題,我打算在外部加一個類似外殼的矩形,可調整fillRect(x, y, width, height)x和y,其實應該講其變小一些,但總覺得應該把顯示的整體矩形變大;結果就出現圓指示燈漏出,後來體會出x,y是類似初始座標點,而後兩個參數纔是實際的大小控制;
四、如何將圓“噴”顏色:燈在變,可就是一個白框框,啥也不代表。本來覺得應該有處理所花圖像顏色的方法,殘酷的現實就是沒有填充的方法,在網上搜也沒結果,後來發現除了課本中提到的drawOval可以畫圓(我覺得根本不能出稱得上是圓而是一個圓框而已),而fillOval卻也能實現畫圓的目的,並且圓都是有顏色的,根據API所說:“使用當前顏色填充外接指定矩形框的橢圓。”不就是我要找的,所以可以在之前將默認顏色改爲自己想的,用到setColor(),然後再fillOval()就完成了。
五、在無意中發現自己所處理的JVM都在資源管理器中有運行,而且數量龐大,但確實關閉了,但只說明只是表面現象;突然想到課本有一段關於“setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);”就嘗試了一下,發現再也沒有發生關閉後在後臺運行。
其中我認爲自己還應多瞭解的內容有:Graphics這個圖像類(repaint()方法就應該瞭解怎樣實現重畫);JFrame及Frame的設置方法Set....。