0

現在、RFID を使用して入力を取得し、Java Swing インターフェイスを使用してその情報を表示するプログラムを作成しています。

ここでの問題は、RFID に入力があるかどうかを継続的にチェックし、Swing を使用して表示する関数を作成したことですが、アプリケーションの起動時にその関数を実行する必要があります。

jlabel.setText※パブリック関数を使ってみたのですが、静的に実行しているため他の関数が使えません。

車輪を回転させるためだけにスタートボタンを追加することを検討していますが、インターフェイスがきれいになるようにボタンを使用しないことを好みます。

package com.domain.test;

import java.io.IOException;
import java.io.InputStream;

public class SerialReader implements Runnable {

    InputStream in;

    public SerialReader(InputStream in) {
        this.in = in;
    }

    public void run() {
        byte[] buffer = new byte[1024];
        String dataHolder;
        String IDnumber = new String();
        int incomingData = -1;
        int ctr = 0;
        try {

            while ((incomingData = this.in.read(buffer)) > -1) {
                dataHolder = new String(buffer, 0, incomingData);

                if (incomingData >= 1) {


                    ctr++;

                    IDnumber = IDnumber + dataHolder;
                    if (IDnumber.length()==14) {

                        System.out.println(IDnumber);
                        log display = new log();
                        display.setLabel(IDnumber.substring(1, IDnumber.length() - 1));
                        IDnumber = new String();
                        ctr = 0;

                    }

                } 

            }

        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

私がする必要があるのは、この関数に送信されているデータを渡し、それをこの Swing 関数 (setText) に渡すことです。

 public void setLabel(String studNum){
   sNum = studNum;
   jName.setText(sNum);
}

問題は、データを渡すことはできますが、それを使用してインターフェイスに表示できないことです。そのため、アプリケーションの起動時に実行される関数 (Swing と通信できる) を作成する方法を尋ねています。

また、Swing にデータを渡す方法について別の方法を教えてください。

4

3 に答える 3

2

入力を探すためにポーリングを実装できます

http://download.oracle.com/javase/tutorial/uiswing/misc/timer.htmlから

Swingタイマー(のインスタンス javax.swing.Timer)は、指定された遅延の後に1つ以上のアクションイベントを発生させます。Swingタイマーを、リリース1.3でjava.utilパッケージに追加された汎用タイマー機能と混同しないでください。このページでは、Swingタイマーについてのみ説明します。

一般に、GUI関連のタスクには汎用タイマーではなくSwingタイマーを使用することをお勧めします。これは、Swingタイマーはすべて同じ既存のタイマースレッドを共有し、GUI関連のタスクはイベントディスパッチスレッドで自動的に実行されるためです。ただし、タイマーからGUIに触れる予定がない場合、または長時間の処理を実行する必要がある場合は、汎用タイマーを使用できます。

于 2013-01-17T10:44:15.453 に答える
2

そのRFIDフィードを開始して確認するには、スレッド、タイマー、またはエグゼキュータサービスが必要です。

アプリを作成するときに、スレッドをインスタンス化して開始できないのはなぜですか?ボタンは必要ないと思います。

Swingスレッドではこの操作を行いません。結果はUIに表示されますが、操作は実際にはSwingの問題ではありません。

于 2013-01-17T10:44:30.153 に答える
0

まず、GUI が IDNumber をレンダリングしているときにリーダー スレッドがブロックされないように、GUI をレンダリングして IDNumber を表示するための別のスレッドが必要です。


次に、IDNumber の同時表示と、入力ストリームからのメッセージの読み取りが必要です。


SwingWorkerが提供する APIを使用することで、上記の両方の要件を達成できます。Swing.

最後に、Reader が GUI (表示) の開始後にのみ実行を開始するようにするにはvolatile、実行中にコードを最適化する口実で JVM がコードのシーケンスを変更しないようにするためのキーワードが必要です。


ここでは、これらすべてを実現するためのコード スニペットを投稿しています。お役に立てれば幸いです。

import javax.swing.*;
import java.awt.*;
import java.util.List;
class SerialReader extends SwingWorker<Void,String>
{
    Log display ;
    String messages[] =     {
                    "Java supports OOPS!!",
                    "JRE is the bundle of JVM and java Class liberary",
                    "JVM executes the java bytecode.",
                    "JIT converts code at runtime prior to executing it natively",
                    "Stay here I'll be back after reading more about java!!!! :)"
                };
    private SerialReader(){}//To avoid construction of object without parameter
    public SerialReader(Log display)
    {   
        this.display = display;
    }
    @Override
    protected Void doInBackground()
    {
        try
        {
            //Reading Messages one by one till the end
            for(int i=0;i<messages.length;i++)
            {
                String message = messages[i];
                publish(message);
                Thread.sleep(600);//I have added this much delay in compensation to the time 
                        //that would be taken when u are formating data from inputstream.
            }           //You must sleep the Thread for at least 1 ms so that change in 
                        //display could be visualized.
        }catch(Exception ex){ex.printStackTrace();}
        finally
        {
            return null;
        }
    }

    @Override
    protected void process(List<String> chunks)
    {
        for(String msg: chunks)
        {
            display.setLabel(msg);
        }
    }

    @Override
    protected void done()
    {}
}
class Log extends JFrame
{
    private JLabel label = new JLabel("");
    public Log()
    {
        super("Display");
    }
    public void prepareAndDisplay()
    {
        getContentPane().setLayout(new FlowLayout());
        getContentPane().add(label);    
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setSize(400,100);
        setVisible(true);
    }
    public void setLabel(final String value)
    {
        label.setText(value);
    }
}
public class MainClass 
{
    private static volatile Log log;
    private static volatile SerialReader reader;
    public static void main(String st[])
    {
        SwingUtilities.invokeLater( new Runnable()
        {
            @Override
            public void run()
            {
                log = new Log();
                log.prepareAndDisplay();
                log.setLabel("Display is ready Please Wait for incoming message...");
                try
                {
                    Thread.sleep(100);//Delayed the start of Reader by 100 ms
                }catch(Exception ex){}
                reader = new SerialReader(log);
                reader.execute();
            }       
        });                                 
    }
}


SwingWorkerAPI の詳細については、ここをクリックしてください。使用方法については、SwingWorkerここをクリックしてください

于 2013-01-18T20:36:58.183 に答える