2009-08-07 13 views
1

Ich lese Daten von der seriellen Schnittstelle für durchschnittliche Intervall sagen 1 Sekunde, und zur gleichen Zeit schreiben Daten in TextArea und Textdatei, Problem ist, ich bekomme nicht die richtigen Daten zu einer bestimmten Zeit, kann sein, weil ich alle drei Prozesse in einem einzigen Programm mache, wie schreibe ich Textbereiche und Textdateien durch separate thred?Threads zum Lesen und Schreiben von Java

dies ist mein Code:

import java.io.BufferedWriter; 
import java.io.File; 

import java.io.FileWriter; 

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

import java.text.SimpleDateFormat; 

import java.util.Date; 
import java.util.Iterator; 

import java.util.TooManyListenersException; 
import java.util.TreeMap; 

import javax.comm.CommPortIdentifier; 
import javax.comm.SerialPort; 
import javax.comm.SerialPortEvent; 
import javax.comm.SerialPortEventListener; 
import javax.comm.UnsupportedCommOperationException; 
import javax.swing.JOptionPane; 

import com.pressure.constants.Constants; 

import com.pressure.online.OnlineStartWindow; 

public class SerailReader implements SerialPortEventListener { 

    // DECLARES INPUT STREAM TO READ SRIAL PORT 
    private InputStream inputStream; 
    // DECLARES PORT 
    private CommPortIdentifier port; 
    private SerialPort serialPort; 

    // DATE TO CREATE FILE NAME 
    private static final SimpleDateFormat SDF = new SimpleDateFormat("dd-MM-yy"); 


    private int index = 0; 

    private File file; 

    private OnlineStartWindow onlineStartwindow; 

    private int[] tempIntArray = new int[233]; 
    private int newData = 0; 

    private String outFolder; 

    private String filename = "0"; 

    private FileWriter fileWriter; 

    private BufferedWriter buffOut; 
    private StringBuffer line; 
    private String packetFilename; 

    TreeMap<Integer, Float> channelMap = new TreeMap<Integer, Float>(); 

    ThreadPrintsAndWrites p; 

    public FileWriter getFileWriter() { 
     return fileWriter; 
    } 

    public void setFileWriter(FileWriter fileWriter) { 
     this.fileWriter = fileWriter; 
    } 

    public BufferedWriter getBuffOut() { 
     return buffOut; 
    } 

    public void setBuffOut(BufferedWriter buffOut) { 
     this.buffOut = buffOut; 
    } 

    // SETTER GETTER TO OnlineStartwindow OBJECT 
    public OnlineStartWindow getOnlineStartwindow() { 
     return onlineStartwindow; 
    } 

    public void setOnlineStartwindow(OnlineStartWindow onlineStartwindow) { 
     this.onlineStartwindow = onlineStartwindow; 
    } 

    // SETTER GETTER TO SERIALPORT 
    public SerialPort getSerialPort() { 
     return serialPort; 
    } 

    public void setSerialPort(SerialPort serialPort) { 
     this.serialPort = serialPort; 
    } 

    // ********* connects to serial port ***********// 
    public void SerialReadmethod(OnlineStartWindow onlineStartwindow, 
      String outFolderPath) throws Exception { 

     setOnlineStartwindow(onlineStartwindow); 
     outFolder = outFolderPath; 
     // SELECTS PORT NAME SELECTED 

     port = CommPortIdentifier.getPortIdentifier(getOnlineStartwindow() 
       .getComPort()); 
     System.out.println("port name " + port); 

     // CHEAK WETHER SELECTED PORT AVAILABLE OR NOT 
     if (port.getPortType() == CommPortIdentifier.PORT_SERIAL) { 

      if (port.getName().equals(getOnlineStartwindow().getComPort())) { 

       JOptionPane.showMessageDialog(null, "Successpully opened port", 
         "Online Dump", JOptionPane.INFORMATION_MESSAGE); 

      } 

     } 

     // OPENS SERAIL PORT 
     serialPort = (SerialPort) port.open("SimpleReadApp1111", 1000); 

     // OPENS SERIAL PORT INPUT STREAM TO READ DATA 
     try { 
      inputStream = serialPort.getInputStream(); 

     } catch (IOException e) { 
      System.out.println("IO Exception"); 
     } 

     // ADDS LISTNER TO SERIALPORT 
     try { 
      serialPort.addEventListener(this); 

     } catch (TooManyListenersException e) { 
      System.out.println("Tooo many Listener exception"); 
     } 

     // EVENT GENERATED WHEN DATA WILL BE AVAILABELE ON SERIALPORT 
     // INPUTSTREAM 
     serialPort.notifyOnDataAvailable(true); 

     try { 

      // SETS SELECTED BAUDRATE 

      int BAUDRATE = Integer.parseInt((getOnlineStartwindow() 
        .getBaudRate()).trim()); 

      // SETS SELECTED DATA BITS 

      int DATABITS = Integer.parseInt(getOnlineStartwindow() 
        .getDataBits().trim()); 
      if (DATABITS == 8) { 
       DATABITS = SerialPort.DATABITS_8; 
      } else if (DATABITS == 7) { 
       DATABITS = SerialPort.DATABITS_7; 
      } else if (DATABITS == 6) { 
       DATABITS = SerialPort.DATABITS_6; 
      } else if (DATABITS == 5) { 
       DATABITS = SerialPort.DATABITS_5; 
      } 

      // SETS SELECTED STOPBITS 
      int STOPBITS = 0; 

      if (getOnlineStartwindow().getStopBits() == "1") { 
       STOPBITS = SerialPort.STOPBITS_1; 
      } else if (getOnlineStartwindow().getStopBits() == "1.5") { 
       STOPBITS = SerialPort.STOPBITS_1_5; 
      } else if (getOnlineStartwindow().getStopBits() == "2") { 
       STOPBITS = SerialPort.STOPBITS_2; 
      } 

      // SETS SELECTED PARITY 
      int PARITY = 0; 
      if (getOnlineStartwindow().getParity() == "NONE") { 
       PARITY = SerialPort.PARITY_NONE; 
      } else if (getOnlineStartwindow().getParity() == "EVEN") { 
       PARITY = SerialPort.PARITY_EVEN; 
      } else if (getOnlineStartwindow().getParity() == "ODD") { 
       PARITY = SerialPort.PARITY_ODD; 
      } 

      // SETS SELECTED FLOW CONTROL 
      int FLOWCONTROL = 0; 
      if (getOnlineStartwindow().getFlowControl() == "NONE") { 
       FLOWCONTROL = SerialPort.FLOWCONTROL_NONE; 
      } else if (getOnlineStartwindow().getFlowControl() == "XON/XOFF") { 
       FLOWCONTROL = SerialPort.FLOWCONTROL_XONXOFF_IN; 
      } 

      serialPort 
        .setSerialPortParams(BAUDRATE, DATABITS, STOPBITS, PARITY); 

      // no handshaking or other flow control 
      serialPort.setFlowControlMode(FLOWCONTROL); 


     } catch (UnsupportedCommOperationException e) { 
      System.out.println("UnSupported comm operation"); 
     } 

    } 

    // *********this method will automaticaly calls when u get data on port and 
    // arranges packet from start frame to end frame *************// 
    public void serialEvent(SerialPortEvent event) { 

//  switch (event.getEventType()) { 
// 
//  case SerialPortEvent.DATA_AVAILABLE: 

     if(event.getEventType()==SerialPortEvent.DATA_AVAILABLE){ 

       //dataAvailabel = inputStream.available(); 

       // READING DATA CHARECTER BY CHARECTER 

       while (newData != -1) { 
        try { 
         newData = inputStream.read(); 
         if (newData == -1) { 
          break; 
         } 
         if (Constants.SF == (char) newData) { 
          index = 0; 
          // System.out.println("start frame"); 
         } 
         tempIntArray[index] = newData; 

         if (Constants.EF == (char) newData) { 
          selectToDispalyAndWrite(tempIntArray); 
          // disp(tempIntArray); 

         } 
         index++; 

        } catch (IOException ex) { 
         System.err.println(ex); 
         // return; 
        } 
       } 
       // ///////////////// completes 
     } 




    } 

    // DISPLYS PACKET TO TEXT AREA AND CREATES .PSI FILE 
    public void selectToDispalyAndWrite(int[] readBufferArray) { 

     if (getOnlineStartwindow().getDump().isSelected()) { 
      packetFilename = Integer.toString(readBufferArray[1]) 
        + Integer.toString(readBufferArray[2]) 
        + Integer.toString(readBufferArray[3]); 


      try { 
       if (getOnlineStartwindow().getFileTypeSelection() == "text") { 

        displayAndWriteToTextFile(readBufferArray); 

       } else { 
        displayAndWriteToExcelFile(readBufferArray); 
       } 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 
     } else { 
      printToTextArea(readBufferArray); 
     } 
    } 

    public void printToTextArea(int[] readBufferArray) { 
     int i = 0; 
     int portname = 0; 
     Float portval = 0.0f; 


     int len = 0; 
     i = 0; 
    writeloop: while (len != readBufferArray.length) { 
      // while ((char) readBufferArray[i] != Constants.EF) { 
      if ((char) readBufferArray[i] == Constants.SF) { 

       // WRITES DASH LINE TO TEXT AREA 
       getOnlineStartwindow() 
         .getTextArea() 
         .append(
           "\r\n\r\n-----------------------------------------------------------------------\r\n"); 

       getOnlineStartwindow().getTextArea().append(
         "Time :" + readBufferArray[i + 4] + " Min " 
           + readBufferArray[i + 5] + " Sec."); 
       getOnlineStartwindow() 
         .getTextArea() 
         .append(
           "\r\n-----------------------------------------------------------------------\r\n"); 



      } 
      if ((char) readBufferArray[i] == Constants.EF) { 
       for (Iterator<Integer> iterator = channelMap.keySet() 
         .iterator(); iterator.hasNext();) { 

        int key = iterator.next(); 
        Float value = channelMap.get(key); 

        getOnlineStartwindow().getTextArea().append(
          "Port_" + key + "   " + value + "\r\n"); 

       } 
       channelMap.clear(); 
       break writeloop; 
      } 
      i++; 
     } 

    } 

    public void displayAndWriteToTextFile(int[] readBufferArray) 
      throws IOException { 
     int i = 0; 
     int portname = 0; 
     Float portval = 0.0f; 

     if (!(filename.equalsIgnoreCase(packetFilename))) { 
      filename = packetFilename; 
      if (buffOut != null && fileWriter != null) { 
       drawLine('*'); 
       buffOut.close(); 
       fileWriter.close(); 

      } 

      // GET CURRENT DATE 
      Date date = new Date(); 
      file = new File(outFolder + "\\" + SDF.format(date) + "-" 
        + packetFilename + ".txt"); 

      if (!file.exists()) { 
       fileWriter = new FileWriter(file, true); 
       buffOut = new BufferedWriter(fileWriter); 

       drawLine('*'); 

       drawLine('*'); 
      } else { 
       fileWriter = new FileWriter(file, true); 
       buffOut = new BufferedWriter(fileWriter); 
      } 

     } 

     // LOOP TO DISPLY ALL PORT NAME AND PRESSURE VALUES 
     int len = 0; 
     i = 0; 
     writeloop: while (len != readBufferArray.length) { 
      // while ((char) readBufferArray[i] != Constants.EF) { 
      if ((char) readBufferArray[i] == Constants.SF) { 

       // WRITES DASH LINE TO TEXT AREA 
       getOnlineStartwindow() 
         .getTextArea() 
         .append(
           "\r\n\r\n-----------------------------------------------------------------------\r\n"); 

       getOnlineStartwindow().getTextArea().append(
         "Time :" + readBufferArray[i + 4] + " Min " 
           + readBufferArray[i + 5] + " Sec."); 
       getOnlineStartwindow() 
         .getTextArea() 
         .append(
           "\r\n-----------------------------------------------------------------------\r\n"); 

       drawLine('-'); 
       buffOut.write("TIME: " + readBufferArray[i + 4] + " Min " 
         + readBufferArray[i + 5] + " Sec." + "\r\n\r\n"); 

      } 
      if ((char) readBufferArray[i] == Constants.ST) { 

       portname = readBufferArray[i + 1]; 
       portval = getFloatValue(i); 
       channelMap.put(portname, portval); 

      } 
      if ((char) readBufferArray[i] == Constants.EF) { 
       for (Iterator<Integer> iterator = channelMap.keySet() 
         .iterator(); iterator.hasNext();) { 

        int key = iterator.next(); 
        Float value = channelMap.get(key); 

        getOnlineStartwindow().getTextArea().append(
          "Port_" + key + "   " + value + "\r\n"); 



       } 
       channelMap.clear(); 
       break writeloop; 
      } 
      i++; 
     } 

    } 
} 

Vielen Dank im Voraus

Antwort

0

Ich habe den Eindruck, dass Java nicht serielle Schnittstelle für Windows nicht unterstützt, es tut es nur für Solaris oder Linux. Ihre Klasse sollte das Runnable Interface implementieren. und erstelle einen Thread, der in seiner run-Methode vom seriellen Port liest. Der Haupt-Thread konnte den schreibenden Teil zur TextArea machen. Möglicherweise müssen Sie eine Synchronisierung zwischen dem Hauptthread und dem Runnable durchführen, damit das Schreiben in die TextArea/Datei nur erfolgt, nachdem entsprechende Daten vom Port gelesen wurden.

1

Hier ein Ansatz vom Design Standpunkt.

  1. Erstellen Sie einen Klassentyp für die Daten. Dies wird ein Container (erben die entsprechende Warteschlange). Und innerhalb dieser Klasse, während Sie die Daten setzen und abrufen, stellen Sie sicher, dass Sie sperren.
  2. Erstellen Sie einen neuen Thread in main, um den seriellen Port zu starten und die Nachrichten zu lesen. Übergeben Sie dem Thread ein Objekt (Ihr Listenklassenobjekt). Der serielle Port speichert Daten in diese Liste. Dies wird im Objekt festgelegt.
  3. Ihr Haupt-Thread (das Fenster) wird einen Timer haben, der die Daten aus der Warteschlange auslöst und ausliest. Möglicherweise müssen Sie mit dem Timer etwas spielen. Sie möchten nicht, dass es zu oft zündet und Ihre gesamte Verarbeitungszeit im Hauptfenster verbraucht. Wenn es jedoch zu langsam ist, werden Sie möglicherweise nicht genügend aktualisieren und Nachrichten aus der Warteschlange abrufen, wenn sie verfügbar sind. Dieser Timer sollte alle Daten aus der Warteschlange abrufen und anzeigen.

Die Warteschlange und das Schloss sind hier der wichtige Teil. Die Warteschlange hält Nachrichten in der richtigen Reihenfolge. Die Sperre stellt sicher, dass Sie nicht versuchen, neue Daten in Ihre Warteschlange zu schreiben, während Sie gerade Daten lesen.

Verwandte Themen