2016-03-31 6 views
3

Während ich an einem Programm arbeitete, machte ich einige meiner Felder statisch, d. H. JTextField für E-Number. Aber jetzt verhält sich dieses Feld nicht wie erwartet, auf einigen meiner Seiten erscheint es, auf einigen anderen verschwindet es. Da ich mit sehr viel Statik nicht sehr viel Erfahrung habe, könnte es ein Konzept geben, das ich nicht verstehe.JTextField verschwindet auf einigen Seiten, wenn es statisch ist, während es auf anderen erscheint

Ich habe ein sehr vereinfachtes, aber funktionierendes Beispiel meines Programms erstellt (MCVE), wenn Sie es testen möchten.

Es zeigt zunächst meine Übersichtsseite - die E-Number JTextField fehlt.

Wenn Sie auf die Suchschaltfläche klicken, wird die Tracking-Seite angezeigt - mit der E-Number JTextField-Anzeige.

Beide Seiten enthalten das gleicheworkNumberPanel und ich finde keinen Unterschied, das würde das Verhalten erklären.

Warum ist die E-Number JTextField auf der Übersichtsseite und fehlt auf der Tracking-Seite? Jede Hilfe/Erklärung wird geschätzt!

Static JTextField disappears

MainProgram.java

import java.awt.CardLayout; 
import java.awt.EventQueue; 

import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.UIManager; 

import net.miginfocom.swing.MigLayout; 

public class MainProgram extends JFrame { 
    private static final long serialVersionUID = 1L; 

    public static JPanel centerPanel = new JPanel(); 

    public static CardLayout contentCardsLayout = new CardLayout(); 

    OverviewPage overviewPage = new OverviewPage(); 
    TrackingPage trackingPage = new TrackingPage(); 

    public void initialize() { 
     createCenterPanel(); 
    } 

    private void createCenterPanel() { 
     centerPanel.setLayout(contentCardsLayout); 

     overviewPage.setName("overviewPage"); 
     trackingPage.setName("trackingPage"); 

     centerPanel.add(overviewPage, "overviewPage"); 
     centerPanel.add(trackingPage, "trackingPage"); 

     add(centerPanel, "growx, wrap"); 
    } 

    public MainProgram() { 
     setBounds(300, 50, 1200, 900); 
     setLayout(new MigLayout()); 
     setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    } 

    public static void main(String[] args) { 
     EventQueue.invokeLater(new Runnable() { 
      public void run() { 
       try { 
        UIManager.setLookAndFeel("com.sun.java.swing.plaf.nimbus.NimbusLookAndFeel"); 
        MainProgram window = new MainProgram(); 
         window.setVisible(true); 
         window.initialize(); 
       } catch (Exception e) { 
        e.printStackTrace(); 
       } 
      } 
     }); 
    } 
} 

OverviewPage.java

import javax.swing.JPanel; 

import net.miginfocom.swing.MigLayout; 

public class OverviewPage extends JPanel { 
    WorkNumberPanel workNumberPanel = new WorkNumberPanel(); 

    private static final long serialVersionUID = 1L; 

    public OverviewPage() { 
     setLayout(new MigLayout()); 
     add(workNumberPanel, "wrap, growx"); 
    } 
} 

TrackingPage.java

import javax.swing.JPanel; 

import net.miginfocom.swing.MigLayout; 

public class TrackingPage extends JPanel { 
    private static final long serialVersionUID = 1L; 

    WorkNumberPanel equipmentNumberPanel = new WorkNumberPanel(); 

    public TrackingPage(){ 
     setLayout(new MigLayout("", "grow, fill")); 
     add(equipmentNumberPanel, "wrap, growx"); 
    } 
} 

WorkNumberPanel.java

import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 

import javax.swing.JButton; 
import javax.swing.JLabel; 
import javax.swing.JPanel; 
import javax.swing.JTextField; 

import net.miginfocom.swing.MigLayout; 

public class WorkNumberPanel extends JPanel { 
    private static final long serialVersionUID = 1L; 
    private static final Integer TEXTFIELD_LENGTH = 20; 

    JPanel mainWorkNumberPanel = new JPanel(); 

    JLabel lblWorkNumber = new JLabel("E-Nr: "); 
    JLabel lblN_Number = new JLabel("N-Nr.: "); 
    JLabel lblSNumber = new JLabel("W-Nr.: "); 

    public static JTextField txtWorkNumber = new JTextField(TEXTFIELD_LENGTH); 
    JTextField txtNNumber = new JTextField(TEXTFIELD_LENGTH); 
    JTextField txtSNumber = new JTextField(TEXTFIELD_LENGTH); 

    JButton btnSearchEntry = new JButton("Search"); 

    public WorkNumberPanel() { 
     createEquipmentNumberPanel(); 
     btnSearchEntry.addActionListener(new ActionListener() { 
      @Override 
      public void actionPerformed(ActionEvent e) { 
       MainProgram.contentCardsLayout.show(MainProgram.centerPanel, "trackingPage"); 
      } 
     }); 
    } 

    private void createEquipmentNumberPanel() { 
     setLayout(new MigLayout()); 
     mainWorkNumberPanel.setLayout(new MigLayout("", "[][grow, fill][][grow, fill][][grow, fill][]")); 
     mainWorkNumberPanel.add(lblWorkNumber); 
     mainWorkNumberPanel.add(txtWorkNumber); 
     mainWorkNumberPanel.add(lblN_Number); 
     mainWorkNumberPanel.add(txtNNumber); 
     mainWorkNumberPanel.add(lblSNumber); 
     mainWorkNumberPanel.add(txtSNumber); 
     mainWorkNumberPanel.add(btnSearchEntry); 

     add(mainWorkNumberPanel, "push, span, growx"); 
    } 
} 

Antwort

3

Wahrscheinlich, weil, wenn Sie Ihre "Seiten" mit diesem Code erstellen

OverviewPage overviewPage = new OverviewPage(); 
TrackingPage trackingPage = new TrackingPage(); 

die TrackingPage wird die letzte sein, die folgende Zeile auszuführen

mainWorkNumberPanel.add(txtWorkNumber); 

in private void createEquipmentNumberPanel(), und daher wird Panel das JTextField "besitzen". Es macht nur Sinn, dass eine UI-Komponente nur an einem Ort zu einem bestimmten Zeitpunkt sein kann, sonst würden die Dinge sehr seltsam bekommen :)

Ihre Aussage

Beiden Seiten die gleiche workNumberPanel enthalten und ich kann eine finden Unterschied, das würde das Verhalten erklären.

ist einfach nicht wahr.Sie sind eine neue Instanz von WorkNumberPanel sowohl OverViewPage Erstellen und TrackingPage, wenn Sie die folgende Zeile ausführen

WorkNumberPanel equipmentNumberPanel = new WorkNumberPanel(); 

Also meine Empfehlung ist, dass Sie eine andere Art und Weise der Umsetzung finden, was Sie wollen, ohne eine statische JTextField (oder andere UI Komponente für diese Angelegenheit).

+0

Beide Antworten machen es sehr deutlich, was mein Fehler war. Jetzt muss ich einen Weg finden, das 'JTextField' ohne Statik zu verwenden. Ich erstelle ein 'OrderObject', das ich von der Übersichtsseite an die Tracking-Seite sende. Dort möchte ich die Bestellnummer (E-Nummer) im 'JTextField' anzeigen. Aber ich habe noch nicht herausgefunden, wie die Übersichtsseite der Verfolgungsseite mitteilen kann, den Text auf die E-Nummer zu setzen, daher meine Verwendung von statisch, da dies einfach zu sein scheint, aber falsch? – hamena314

+0

Ja, "statisch" auf diese Weise zu verwenden, ist keine Lösung. Sie müssen das Ergebnis des ersten Dialogs erhalten und es in den zweiten einfügen. Dies kann auf verschiedene Arten geschehen, ich bevorzuge [diese Methode] (http://stackoverflow.com/a/4089370/930640). – BadCash

+0

Das sind keine Dialoge. Ich habe eine Seite, auf der ein Navigationsbereich (linke Seite), Nummernbereich (Header) und der Rest ist Inhalt (Mitte).Ich benutze ein Cardlayout, um von einer Seite zu einer anderen zu wechseln und habe die Notwendigkeit, die gleichen Zahlen im Nummernfeld in der Kopfzeile jeder Seite zu behalten, da sie alle zur selben Reihenfolge gehören. – hamena314

2

Hier instanziieren Sie eine OverviewPage, dann eine TrackingPage.

OverviewPage overviewPage = new OverviewPage(); 
TrackingPage trackingPage = new TrackingPage(); 

instanziiert Beide Klassen eine WorkNumberPanel.

WorkNumberPanel fügen den statischen JTextField (txtWorkNumber) in die Anzeigetafel (mainWorkNumberPanel).

Ein einzelner Component kann nicht zu mehreren Container Objekten hinzugefügt werden. Dies passiert mit Ihrem Textfeld, da es static und keine Instanzvariable ist.

Die letzte Addition wird gewinnen, daher erscheint das Textfeld nur in TrackingPage und nicht mehr in OverviewPage.

Machen Sie es einfach nicht static.

+1

Mein Missverständnis scheint zu sein, 'statisch' zu missbrauchen als eine einfache Möglichkeit, Informationen/Daten von einer Klasse zu einer anderen zu übertragen. Ich muss herausfinden, wann ich Instanzen/Objekte erstellen und ihnen die Informationen geben soll, die sie benötigen. – hamena314

1

Zunächst müssen Sie verstehen, was ein statisches Feld ist. Ein statisches Feld bezieht sich nicht auf eine bestimmte Instanz eines Objekts. Das Feld bezieht sich auf die Klasse selbst.
Es gibt eine ziemlich gute Erklärung here und here.


Jetzt in Bezug auf Ihren Fall. A JComponent kann immer nur zu einem Panel hinzugefügt werden. Wenn Sie es einem anderen hinzufügen, wird es vom ersten entfernt.

In Ihrem Code erstellen Sie mehrere Instanzen von 'WorkingNumberPanel'. Wenn Sie dies tun, fügen Sie dem Panel die Textfelder einschließlich das static Textfeld txtWorkNumber hinzu. Da das Feld txtWorkNumber statisch ist, fügen Sie dasselbe Objekt zu mehreren Komponenten hinzu, die, wie ich oben erwähnt habe, es von überall entfernen, wo es zuvor hinzugefügt wurde.

Eine mögliche Lösung wäre, den Wert von txtWorkNumber in einer statischen Variablen zu speichern und ein neues Textfeld für die Instanz (nicht statisch) zu erstellen, das dem Panel hinzugefügt werden soll.

Verwandte Themen