package com.zmx;import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Calendar;
import java.util.GregorianCalendar;import javax.swing.Timer;import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.custom.CLabel;
import org.eclipse.swt.graphics.Font;public class closecomputer { private Shell sShell = null;  //  @jve:decl-index=0:visual-constraint="10,10"
private Composite timecomposite = null;
private CLabel currenttimeLabel = null;
private CLabel closetimeLabel = null;
/**
 * This method initializes timecomposite
 *
 */
private void createTimecomposite() {
timecomposite = new Composite(sShell, SWT.NONE);
currenttimeLabel = new CLabel(timecomposite, SWT.CENTER);
currenttimeLabel.setText("现在时间是:");
currenttimeLabel.setFont(new Font(Display.getDefault(), "\u5b8b\u4f53", 12, SWT.NORMAL));
currenttimeLabel.setBackground(Display.getCurrent().getSystemColor(SWT.COLOR_WHITE));
timeAction listener = new timeAction();
Timer timer = new Timer(1000,listener);
timer.start();
closetimeLabel = new CLabel(timecomposite, SWT.CENTER);
closetimeLabel.setText("关机时间是:");
closetimeLabel.setForeground(Display.getCurrent().getSystemColor(SWT.COLOR_RED));
closetimeLabel.setFont(new Font(Display.getDefault(), "\u5b8b\u4f53", 12, SWT.NORMAL));
closetimeLabel.setBackground(Display.getCurrent().getSystemColor(SWT.COLOR_WHITE));
FillLayout layout= new FillLayout(SWT.VERTICAL);
timecomposite.setLayout(layout);
timecomposite.setBackground(Display.getCurrent().getSystemColor(SWT.COLOR_WHITE));
timecomposite.setBounds(new Rectangle(21, 8, 350, 53));
}
private class timeAction implements ActionListener{
public void actionPerformed(ActionEvent arg0) {
// TODO 自动生成方法存根
GregorianCalendar calendar = new GregorianCalendar();
int year= calendar.get(Calendar.YEAR);
int month=calendar.get(Calendar.MONTH);
int day= calendar.get(Calendar.DAY_OF_MONTH);
int hour= calendar.get(Calendar.HOUR);
int minute= calendar.get(Calendar.MINUTE);
int second= calendar.get(Calendar.SECOND);
currenttimeLabel.setText("现在时间是:"+year+"年"+month+"月"+day+"日 "+hour+"时"+minute+"分"+second+"秒");
}
}
/**
 * @param args
 */
public static void main(String[] args) {
// TODO 自动生成方法存根
/* Before this is run, be sure to set up the launch configuration (Arguments->VM Arguments)
 * for the correct SWT library path in order to run with the SWT dlls. 
 * The dlls are located in the SWT plugin jar.  
 * For example, on Windows the Eclipse SWT 3.1 plugin jar is:
 *       installation_directory\plugins\org.eclipse.swt.win32_3.1.0.jar
 */
Display display = Display.getDefault();
closecomputer thisClass = new closecomputer();
thisClass.createSShell();
thisClass.sShell.open(); while (!thisClass.sShell.isDisposed()) {
if (!display.readAndDispatch())
display.sleep();
}
display.dispose();
} /**
 * This method initializes sShell
 */
private void createSShell() {
sShell = new Shell();
sShell.setText("zmx定时关机器 V1.0");
sShell.setBackground(Display.getCurrent().getSystemColor(SWT.COLOR_WHITE));
createTimecomposite();
sShell.setSize(new Point(404, 212));
sShell.setLayout(null);
}}错误如下:
Exception in thread "AWT-EventQueue-0" org.eclipse.swt.SWTException: Invalid thread access
at org.eclipse.swt.SWT.error(SWT.java:3374)
at org.eclipse.swt.SWT.error(SWT.java:3297)
at org.eclipse.swt.SWT.error(SWT.java:3268)
at org.eclipse.swt.widgets.Widget.error(Widget.java:435)
at org.eclipse.swt.widgets.Widget.checkWidget(Widget.java:331)
at org.eclipse.swt.custom.CLabel.setText(CLabel.java:731)
at com.zmx.closecomputer$timeAction.actionPerformed(closecomputer.java:61)
at javax.swing.Timer.fireActionPerformed(Timer.java:271)出错的那一行是    currenttimeLabel.setText("现在时间是:"+year+"年"+month+"月"+day+"日 "+hour+"时"+minute+"分"+second+"秒");烦恼了很多天了,到底是什么原因?有什么解决办法吗?

解决方案 »

  1.   

    太晚了,要睡了
    http://blog.csdn.net/sunyujia/archive/2007/12/09/1926007.aspx明天没人回我再来回吧。
      

  2.   

    抢个先机.楼主,没有深入看你的代码,只看到了那一句new Timer, 感觉上你是在每一秒new一个新的对象出来.
    如果理解错你的意思,不要喷我啊.如果那样,请不要那样做,我不知道垃圾收集器多少时间工作一次,但是相信时间间隔不短,如果老让你回收垃圾了,我正常的业务还处理不处理?
    你每一次new一个出来,内存多久会泄露?我没有计算,不过可能比较快.建议的做法是你设置一个成员变量,时间类型,拿到它的long值,然后每次加个数,显示的时候拿回去再显示.
    这样可能还是有些问题,瞌睡了,脑袋转不动了.可能我说的转换还是比较繁琐.
      

  3.   

    报“Invalid thread access”是因为你用“非界面线程”访问界面组件,SWT的组件必须是界面线程去访问。解决办法:
    1,给你的class追加一个全局的变量private static Display display;
    2,main方法的第一句改成:private static Display display;
    3,timeAction 得方法actionPerformed(ActionEvent arg0)中的代码用
    display.asyncExec(new Runnable(){
    public void run() {}
    });包起来。也就是下面    
        private class timeAction implements ActionListener{
            public void actionPerformed(ActionEvent arg0) {
                // TODO 自动生成方法存根
             display.asyncExec(new Runnable(){
    public void run() {
    // TODO 自動生成されたメソッド・スタブ
                GregorianCalendar calendar = new GregorianCalendar();
                int year= calendar.get(Calendar.YEAR);
                int month=calendar.get(Calendar.MONTH);
                int day= calendar.get(Calendar.DAY_OF_MONTH);
                int hour= calendar.get(Calendar.HOUR);
                int minute= calendar.get(Calendar.MINUTE);
                int second= calendar.get(Calendar.SECOND);
                currenttimeLabel.setText("现在时间是:"+year+"年"+month+"月"+day+"日 "+hour+"时"+minute+"分"+second+"秒");
    }});
            }
        }4,ok!!!!
      

  4.   

    楼上
    2,main方法的第一句改成:private static Display display;
    应该是
    2,main方法的第一句改成:display = Display.getDefault();
      

  5.   

    Timer线程是不能直接更新GUI的。
      

  6.   


    为什么关闭界面之后出现如下错误:
    Exception in thread "main" org.eclipse.swt.SWTException: Widget is disposed
    at org.eclipse.swt.SWT.error(SWT.java:3374)
    at org.eclipse.swt.SWT.error(SWT.java:3297)
    at org.eclipse.swt.SWT.error(SWT.java:3268)
    at org.eclipse.swt.widgets.Widget.error(Widget.java:435)
    at org.eclipse.swt.widgets.Widget.checkWidget(Widget.java:330)
    at org.eclipse.swt.custom.CLabel.setText(CLabel.java:731)
    at com.zmx.closecomputer$timeAction$1.run(closecomputer.java:65)
    at org.eclipse.swt.widgets.RunnableLock.run(RunnableLock.java:35)
    at org.eclipse.swt.widgets.Synchronizer.runAsyncMessages(Synchronizer.java:123)
    at org.eclipse.swt.widgets.Display.runAsyncMessages(Display.java:3325)
    at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java:2971)
    at org.eclipse.swt.widgets.Display.release(Display.java:3020)
    at org.eclipse.swt.graphics.Device.dispose(Device.java:262)
    at com.zmx.closecomputer.main(closecomputer.java:90)com.zmx.closecomputer.main(closecomputer.java:90)  的语句是  display.dispose();
      

  7.   

    另外一个
    SWT怎么打包成JAR格式的文件?
    我如果直接源文件打包的话
    会出现找不到MAIN函数
    如果用另外一个函数间接执行的话,程序点下去就马上自动关闭(这个是在进程里面看到的)
      

  8.   

    打包的时候选main Class
    不用贴图了吧,你用eclipse导出,的时候有个界面会看到main class选项,选中启动程序的类。
    原来的问题解决了吧,解决了我就不回了。
      

  9.   

    关于6楼
    出现错误:Exception in thread "main" org.eclipse.swt.SWTException: Widget is disposed
    是因为关闭画面之后,你的Timer还在访问界面组件,这时候界面组件已经被销毁了,你还去访问他,就报错了。
    下面是提供的解决办法:
    第一步:方法createTimecomposite()里的Timer做成全局的变量
    也就是下面两步骤:
    --1,private static Timer timer = null;
    --2 createTimecomposite()方法里的Timer timer = new Timer(1000,listener);
    改成:timer = new Timer(1000,listener);
    第二步:display.dispose();语句之前调用timer.stop();
      

  10.   

    解决方法就是3楼的方法。建议你去看看SWT 的GUI线程相关的资料。SWT和SWING是不一样的