In this code , I have used 3 classes all of them which extend the JPanel class , whose instances are added to a JFrame in the JForm3 class's constructor.
I am wondering if there's a way to display the text present in the text field(instance of JTextField declared in TextPanel class) in the printTextOnConsole() method in the ButtonPanel class.
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class JForm3
{
JFrame frame;
ButtonPanel bP;
TextPanel tP;
LabelPanel lP;
public JForm3()
{
frame = new JFrame("Java Window.");
bP = new ButtonPanel();
tP = new TextPanel();
lP = new LabelPanel();
frame.setSize(500,100);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(BorderLayout.CENTER,tP);
frame.getContentPane().add(BorderLayout.EAST,bP);
frame.getContentPane().add(BorderLayout.WEST,lP);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args)
{
new JForm3();
}
}
class ButtonPanel extends JPanel implements ActionListener
{
JButton quitButton;
JButton printButton;
public ButtonPanel()
{
quitButton = new JButton("Quit");
printButton = new JButton("Print");
quitButton.addActionListener(this);
printButton.addActionListener(this);
this.setLayout(new BoxLayout(this,BoxLayout.Y_AXIS));
this.add(quitButton);
this.add(printButton);
}
public void actionPerformed(ActionEvent event)
{
if(event.getSource() == quitButton)
System.exit(0);
else
printTextOnConsole();
}
public void printTextOnConsole()
{
}
}
class LabelPanel extends JPanel
{
JLabel label;
public LabelPanel()
{
this.setLayout(new BorderLayout());
label = new JLabel("Enter Some Text :");
this.add(BorderLayout.CENTER,label);
this.setVisible(true);
}
}
class TextPanel extends JPanel
{
JTextField textField;
public TextPanel()
{
this.setLayout(new BorderLayout());
textField = new JTextField("Enter text here");
this.add(BorderLayout.CENTER,textField);
this.requestFocus();
textField.select(0,textField.getText().length());
this.setVisible(true);
}
}
Use an interface to loose couple the text functionality between JPanels.
interface TextRetriever {
String getText();
}
Then pass the instance of the TextRetriever (TextPanel) to ButtonPanel
class ButtonPanel extends JPanel implements ActionListener {
private TextRetriever textRetriever;
public ButtonPanel(TextRetriever textRetriever) {
this.textRetriever = textRetriever
...
}
public void printTextOnConsole() {
String text = textRetriever.getText();
}
}
Related
I am trying to implement a GUI in Java Swing (I am new to Swing). I have a parent panel that holds 2 panels. A left panel and a right panel. The left panel has a JComboBox dropdown menu. The right panel is a CardLayout with 7 cards. I want to change the card displayed in the right panel based on the choice in the JComboBox in the left panel. All 3 panels are separate classes: LeftPanel.java, RightPanel.java, and ParentPanel.java. I am having a hard time finding a place to put the action listeners for this action. The LeftPanel can't see the CardLayout of the RightPanel and the ParentPanel isn't able to access the CardLayout of the child RightPanel either. I saw some posts about accessing CardLayout of another JPanel but none of the approaches have worked for me so far. Is there a flaw in my design? Or is it possible to achieve this?
EDIT
Thanks for the advice so far. Given below is my MCVE. Please note that each class is in its own (.java) file. I did that instead of putting everything in the Frame class just for ease of maintenance. I had everything in one class previously and it worked fine but it became one long file with 2000+ lines of code and 20+ panels.
//Class MainFrame containing the Main method:
package tempgui;
public class MainFrame extends JFrame{
JFrame Frame1;
public static void main(String[] args){
new MainFrame();
}
public MainFrame(){
Frame1 = new JFrame();
Frame1.setDefaultCloseOperation(EXIT_ON_CLOSE);
Frame1.getContentPane().add(new ParentPanel(), BorderLayout.CENTER);
Frame1.setSize(800, 600);
Frame1.setLocationRelativeTo(null);
Frame1.pack();
Frame1.setVisible(true);
}
}
//Class ParentPanel:
public class ParentPanel extends JPanel{
private JPanel ParentPanel;
private LeftPanel LP;
private RightPanel RP;
public ParentPanel(){
ParentPanel = new JPanel();
LP = new LeftPanel();
RP = new RightPanel();
ParentPanel.setLayout(new GridLayout(1,2));
ParentPanel.add(LP);
ParentPanel.add(RP);
add(ParentPanel);
}
}
//Class LeftPanel:
public class LeftPanel extends JPanel{
private JPanel LeftPanel;
private JComboBox J1;
public LeftPanel(){
LeftPanel = new JPanel();
String[] Arr = {"RP1","RP2"};
J1 = new JComboBox(Arr);
LeftPanel.add(J1);
add(LeftPanel);
}
}
//Class RightPanel:
public class RightPanel extends JPanel{
private JPanel RightPanel;
private RP1Panel RP1;
private RP2Panel RP2;
private CardLayout C1;
public RightPanel(){
RightPanel = new JPanel();
RP1 = new RP1Panel();
RP2 = new RP2Panel();
C1 = new CardLayout();
RightPanel.setLayout(C1);
RightPanel.add(RP1, "RP1");
RightPanel.add(RP2, "RP2");
C1.show(RightPanel, "RP1");
add(RightPanel);
}
}
//Class RP1Panel:
public class RP1Panel extends JPanel{
private JPanel RP1;
private JLabel JRP1;
public RP1Panel(){
RP1 = new JPanel();
JRP1 = new JLabel("RP1 Panel");
RP1.add(JRP1);
add(RP1);
}
}
//Class RP2Panel:
public class RP2Panel extends JPanel{
private JPanel RP2;
private JLabel JRP2;
public RP2Panel(){
RP2 = new JPanel();
JRP2 = new JLabel("RP2 Panel");
RP2.add(JRP2);
add(RP2);
}
}
I would try to give my classes methods that allow other classes to extract "state" information from them, such as the state of the combobox, and allow other classes to mutate them, such as allowing listeners to be added to the combobox. For instance:
// Class LeftPanel:
class LeftPanel extends JPanel {
private JPanel leftPanel;
private JComboBox<String> comboBox; //!!
// !!
public LeftPanel(String[] comboTexts) {
leftPanel = new JPanel();
comboBox = new JComboBox<>(comboTexts); // !!
leftPanel.add(comboBox);
add(leftPanel);
}
// !!
public String getComboSelection() {
return comboBox.getSelectedItem().toString();
}
// !!
public void comboAddActionListener(ActionListener listener) {
comboBox.addActionListener(listener);
}
}
Then other classes can listen for changes to the combo box, and extract the selection when needed. The right panel would likewise have a method to allow change of the "card" JPanel that it displays. Something like:
// Class RightPanel:
class RightPanel extends JPanel {
private JPanel rightPanel;
private RP1Panel rightPanel1;
private RP2Panel rightPanel2;
private CardLayout cardLayout;
public RightPanel() {
rightPanel = new JPanel();
rightPanel1 = new RP1Panel();
rightPanel2 = new RP2Panel();
cardLayout = new CardLayout();
rightPanel.setLayout(cardLayout);
rightPanel.add(rightPanel1, RP1Panel.NAME); //!!
rightPanel.add(rightPanel2, RP2Panel.NAME); // !!
cardLayout.show(rightPanel, RP1Panel.NAME); // !!
add(rightPanel);
}
// !!
public void showCard(String name) {
cardLayout.show(rightPanel, name);
}
}
And they could be tied together in the main:
// Class ParentPanel:
class ParentPanel extends JPanel {
private JPanel ParentPanel;
private LeftPanel leftPanel;
private RightPanel rightPanel;
public ParentPanel() {
ParentPanel = new JPanel();
leftPanel = new LeftPanel(new String[] {RP1Panel.NAME, RP2Panel.NAME});
rightPanel = new RightPanel();
ParentPanel.setLayout(new GridLayout(1, 2));
ParentPanel.add(leftPanel);
ParentPanel.add(rightPanel);
add(ParentPanel);
// !!
leftPanel.comboAddActionListener(e -> {
String selection = leftPanel.getComboSelection();
rightPanel.showCard(selection);
});
}
}
The whole MCVE could look like:
import java.awt.BorderLayout;
import java.awt.CardLayout;
import java.awt.GridLayout;
import java.awt.event.ActionListener;
import javax.swing.*;
public class FooGui {
public static void main(String[] args) {
new MainFrame();
}
}
class MainFrame extends JFrame {
JFrame Frame1;
public MainFrame() {
Frame1 = new JFrame();
Frame1.setDefaultCloseOperation(EXIT_ON_CLOSE);
Frame1.getContentPane().add(new ParentPanel(), BorderLayout.CENTER);
Frame1.setSize(800, 600);
Frame1.setLocationRelativeTo(null);
Frame1.pack();
Frame1.setVisible(true);
}
}
// Class ParentPanel:
class ParentPanel extends JPanel {
private JPanel ParentPanel;
private LeftPanel leftPanel;
private RightPanel rightPanel;
public ParentPanel() {
ParentPanel = new JPanel();
leftPanel = new LeftPanel(new String[] {RP1Panel.NAME, RP2Panel.NAME});
rightPanel = new RightPanel();
ParentPanel.setLayout(new GridLayout(1, 2));
ParentPanel.add(leftPanel);
ParentPanel.add(rightPanel);
add(ParentPanel);
// !!
leftPanel.comboAddActionListener(e -> {
String selection = leftPanel.getComboSelection();
rightPanel.showCard(selection);
});
}
}
// Class LeftPanel:
class LeftPanel extends JPanel {
private JPanel leftPanel;
private JComboBox<String> comboBox; //!!
// !!
public LeftPanel(String[] comboTexts) {
leftPanel = new JPanel();
comboBox = new JComboBox<>(comboTexts); // !!
leftPanel.add(comboBox);
add(leftPanel);
}
// !!
public String getComboSelection() {
return comboBox.getSelectedItem().toString();
}
// !!
public void comboAddActionListener(ActionListener listener) {
comboBox.addActionListener(listener);
}
}
// Class RightPanel:
class RightPanel extends JPanel {
private JPanel rightPanel;
private RP1Panel rightPanel1;
private RP2Panel rightPanel2;
private CardLayout cardLayout;
public RightPanel() {
rightPanel = new JPanel();
rightPanel1 = new RP1Panel();
rightPanel2 = new RP2Panel();
cardLayout = new CardLayout();
rightPanel.setLayout(cardLayout);
rightPanel.add(rightPanel1, RP1Panel.NAME); //!!
rightPanel.add(rightPanel2, RP2Panel.NAME); // !!
cardLayout.show(rightPanel, RP1Panel.NAME); // !!
add(rightPanel);
}
// !!
public void showCard(String name) {
cardLayout.show(rightPanel, name);
}
}
// Class RP1Panel:
class RP1Panel extends JPanel {
// !!
public static final String NAME = "right panel 1";
private JPanel RP1;
private JLabel JRP1;
public RP1Panel() {
setName(NAME);
RP1 = new JPanel();
JRP1 = new JLabel("RP1 Panel");
RP1.add(JRP1);
add(RP1);
}
}
// Class RP2Panel:
class RP2Panel extends JPanel {
// !!
public static final String NAME = "right panel 2";
private JPanel RP2;
private JLabel JRP2;
public RP2Panel() {
setName(NAME);
RP2 = new JPanel();
JRP2 = new JLabel("RP2 Panel");
RP2.add(JRP2);
add(RP2);
}
}
I have a class BasicInfoWindow that gets the user information such as name, address, etc. I then have another class ReviewandSubmit where it show the the texts the user entered from BasicInfoWindow in the JTextArea. I am using card layout to switch between each panel. I am not sure how to send the info from BasicInfoWindow and receive it from ReviewandSubmit. Here is my code so far:
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
public class Main extends JPanel
{
private static void createAndShowGUI()
{
final Main test = new Main();
JPanel buttonPanel = new JPanel(new BorderLayout());
JPanel southPanel = new JPanel();
buttonPanel.add(southPanel, BorderLayout.SOUTH);
final JButton btnNext = new JButton("NEXT");
final JButton btnPrev = new JButton("PREVIOUS");
buttonPanel.add(btnNext, BorderLayout.EAST);
buttonPanel.add(btnPrev, BorderLayout.WEST);
btnNext.addActionListener(new ActionListener()
{
#Override
public void actionPerformed(ActionEvent e)
{
test.nextCard();
}
});
btnPrev.addActionListener(new ActionListener()
{
#Override
public void actionPerformed(ActionEvent e)
{
test.prevCard();
}
});
JFrame frame = new JFrame("Employment Application");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(test);
frame.getContentPane().add(buttonPanel, BorderLayout.SOUTH);
//frame.setSize(750,500);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setResizable(false);
frame.setVisible(true);
}
public static void main(String [] args)
{
SwingUtilities.invokeLater(new Runnable()
{
#Override
public void run()
{
createAndShowGUI();
}
});
}
private CardLayout cardLayout = new CardLayout();
private JPanel cardShowingPanel = new JPanel(cardLayout);
public Main()
{
BasicInfoWindow window1 = new BasicInfoWindow();
cardShowingPanel.add(window1, "1");
EmploymentHistoryWindow window2 = new EmploymentHistoryWindow();
cardShowingPanel.add(window2, "2");
EducationAndAvailbleWindow window3 = new EducationAndAvailbleWindow();
cardShowingPanel.add(window3, "3");
ReviewAndSubmitWindow window4 = new ReviewAndSubmitWindow();
cardShowingPanel.add(window4, "4");
setLayout(new BorderLayout());
add(cardShowingPanel, BorderLayout.CENTER);
}
public void nextCard()
{
cardLayout.next(cardShowingPanel);
}
public void prevCard()
{
cardLayout.previous(cardShowingPanel);
}
public void showCard(String key)
{
cardLayout.show(cardShowingPanel, key);
}
}
BasicInfo Class
ommitted some methods
public class BasicInfoWindow extends JPanel
{
private JTextField txtName, txtAddress, txtCity, txtState, txtZipCode, txtPhoneNumber, txtEmail;
private JComboBox cbDate, cbYear, cbMonth;
private JLabel labelName, labelAddress, labelCity, labelState, labelZipCode, labelPhoneNumber, labelEmail, labelDOB;
private JButton btnClear;
public BasicInfoWindow()
{
createView();
}
private void createView()
{
JPanel panel = new JPanel();
panel.setLayout(new BorderLayout());
add(panel);
northPanel(panel);
centerPanel(panel);
southPanel(panel);
}
public ArrayList<HiringPersonInfo> sendInfo()
{
String name = txtName.getText();
String address = txtAddress.getText();
String city = txtCity.getText();
String state = txtState.getText();
String zip = txtZipCode.getText();
String phone = txtPhoneNumber.getText();
String email = txtEmail.getText();
String DOB = cbMonth.getSelectedItem() + " " + cbDate.getSelectedItem() + " " + cbYear.getSelectedItem();
HiringPersonInfo addNewInfo = new HiringPersonInfo(name, address, city, state, zip, phone, email, DOB);
ArrayList<HiringPersonInfo> personInfo = new ArrayList();
personInfo.add(addNewInfo);
return personInfo;
}
ReviewAndSubmit class
public class ReviewAndSubmitWindow extends JPanel
{
private JButton btnSubmit;
public ReviewAndSubmitWindow()
{
createView();
}
private void createView()
{
JPanel panel = new JPanel();
panel.setLayout(new BorderLayout());
add(panel);
northPanel(panel);
centerPanel(panel);
southPanel(panel);
}
private void northPanel(JPanel panel)
{
JPanel northPanel = new JPanel();
panel.add(northPanel, BorderLayout.NORTH);
JLabel labelMessage = new JLabel("Review and Submit");
labelMessage.setFont(new Font("Serif", Font.BOLD, 25));
northPanel.add(labelMessage, BorderLayout.CENTER);
}
private void centerPanel(JPanel panel)
{
JPanel centerPanel = new JPanel();
JTextArea showReview = new JTextArea();
showReview.setLineWrap(true);
showReview.setWrapStyleWord(true);
showReview.setEditable(false);
JScrollPane scrollPane = new JScrollPane(showReview);
scrollPane.setPreferredSize(new Dimension(600, 385));
centerPanel.add(scrollPane, BorderLayout.CENTER);
BasicInfoWindow getInfo = new BasicInfoWindow();
showReview.append(getInfo.sendInfo().toString());
panel.add(centerPanel);
}
private void southPanel(JPanel panel)
{
JPanel southPanel = new JPanel();
panel.add(southPanel, BorderLayout.SOUTH);
btnSubmit = new JButton("SUBMIT");
// creates a new file
southPanel.add(btnSubmit);
}
}
You could use a Singleton Pattern in the HiringPersonInfo class to instantiate one instance of the class and then during the submit you could add that instance of that class to an ArrayList.
Singleton Patterns can be used to create one instance of the object that can be shared by all the classes in that package. You can think of it like a "global" variable in a way for OOP.
I know that this kind of issue has been discussed here many times, but I'm confused. I'm totally beginner in Java and I honestly don't know what to do and I admit that I don't have that much time to read whole documentation provided by Oracle. Here's my problem:
I'm trying to program a GUI for my program that will be show interference of acoustic waves. Mathematical functionality doesn't matter in here. I've got two classes called Window and Sliders. Window is intended to be a 'main GUI class' and Sliders is supposed to inherit (?) from it.
This comes from another issue that I need to implement ActionListener in class Window and ChangeListener in Sliders class. I heard that one class can't implement several classes that's why I made two.
Now, I wrote a little bit chaotic those two classes, but I don't know how to combine them. It's really silly, but after C++ I'm pretty confused how to tell the program that it is supposed to show in one frame either buttons defined in Window class and sliders defined in Sliders class. Currently it shows only buttons I want to make it showing sliders too.
I'm very sorry for chaotic pseudo code, please help. Please, try to explain as simply as you can/possible. Please feel free to ignore overrided methods, they're not finished yet.
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.*;
public class Window extends JFrame implements ActionListener
{
private JButton showChord, playSound, getSample, getPlot;
private JLabel chordInfo;
private JPanel basicFunctions;
public Window()
{
init();
}
private void init()
{
setVisible(true);
setSize(new Dimension(1000,500));
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
basicFunctions = new JPanel();
FlowLayout basicLayout = new FlowLayout();
basicFunctions.setLayout(basicLayout);
showChord = new JButton("Akord");
playSound = new JButton("Odtwórz");
getSample = new JButton("Pobierz dźwięk");
getPlot = new JButton("Pobierz wykres");
showChord.addActionListener(this);
playSound.addActionListener(this);
getSample.addActionListener(this);
getPlot.addActionListener(this);
basicFunctions.add(showChord);
basicFunctions.add(playSound);
basicFunctions.add(getSample);
basicFunctions.add(getPlot);
add(basicFunctions);
Sliders param = new Sliders();
}
public static void main(String[] args)
{
Window frame = new Window();
}
//Action Listener
#Override
public void actionPerformed(ActionEvent a)
{
Object event = a.getSource();
if(event == showChord)
{
}
else if(event == playSound)
{
}
else if(event == getSample)
{
}
else if(event == getPlot)
{
}
}
}
import java.awt.*;
import javax.swing.event.ChangeEvent;
import javax.swing.*;
import javax.swing.event.ChangeListener;
public class Sliders extends Window implements ChangeListener
{
private JPanel sliders, sliderSub;
private JTextField accAmplitude, accFrequency, accPhase;
private JSlider amplitude, frequency, phase;
private double amplitudeValue, frequencyValue, phaseValue;
public Sliders()
{
sliders = new JPanel();
sliders.setLayout(new FlowLayout());
amplitude = new JSlider(0,100,0);
amplitude.setMajorTickSpacing(10);
amplitude.setMinorTickSpacing(5);
amplitude.setPaintTicks(true);
amplitude.setPaintLabels(true);
frequency = new JSlider(0,10,0);
frequency.setMajorTickSpacing(1);
frequency.setMinorTickSpacing(1/10);
frequency.setPaintTicks(true);
frequency.setPaintLabels(true);
phase = new JSlider(0,1,0);
phase.setMinorTickSpacing(2/10);
phase.setPaintTicks(true);
phase.setPaintLabels(true);
accAmplitude = new JTextField();
accFrequency = new JTextField();
accPhase = new JTextField();
sliders.add(amplitude, BorderLayout.NORTH);
sliders.add(frequency, BorderLayout.CENTER);
sliders.add(phase, BorderLayout.SOUTH);
add(sliders);
}
#Override
public void stateChanged(ChangeEvent arg0)
{
}
}
I've done this so far, but those text fields just stopped showing sliders values and I don't know why. They are defined in the Parameters class and Window class. Can someone help? Additionally in the future I'd like to make those text fields editable so that you can set slider value by typing it in the text field.
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.border.BevelBorder;
import javax.swing.event.*;
public class Window extends JPanel
{
private JMenuBar mainMenu = new JMenuBar();
private Plot plot = new Plot();
private Parameters param = new Parameters();
private JComboBox chooseChord = new JComboBox();
private JButton playSound = new JButton("Odtwórz");
private JButton getSample = new JButton("Pobierz dźwięk");
private JButton getPlot = new JButton("Pobierz wykres");
private JPanel mainPanel = new JPanel();
private JPanel subPanel = new JPanel();
private JPanel buttonsPanel = new JPanel();
private JPanel slidersPanel = new JPanel();
private JLabel chord = new JLabel("Akord:");
private JTextField aValue = new JTextField();
private JTextField fValue = new JTextField();
private JTextField pValue = new JTextField();
public Window()
{
mainPanel.setLayout(new FlowLayout());
buttonsPanel.setLayout(new BoxLayout(buttonsPanel, BoxLayout.Y_AXIS));
slidersPanel.setLayout(new BorderLayout());
subPanel.setLayout(new BorderLayout());
chooseChord.addItem("A");
chooseChord.addItem("A#");
chooseChord.addItem("Ab");
chooseChord.addItem("B");
chooseChord.addItem("Bb");
chooseChord.addItem("C");
chooseChord.addItem("C#");
chooseChord.addItem("Cb");
chooseChord.addItem("D");
chooseChord.addItem("D#");
chooseChord.addItem("E");
chooseChord.addItem("F");
chooseChord.addItem("F#");
buttonsPanel.add(chord);
buttonsPanel.add(chooseChord);
buttonsPanel.add(Box.createRigidArea(new Dimension(0,10)));
buttonsPanel.add(playSound);
buttonsPanel.add(Box.createRigidArea(new Dimension(0,10)));
buttonsPanel.add(getSample);
buttonsPanel.add(Box.createRigidArea(new Dimension(0,10)));
buttonsPanel.add(getPlot);
buttonsPanel.setBorder(BorderFactory.createTitledBorder("Menu"));
slidersPanel.add(param);
JMenu langMenu = new JMenu("Język");
mainMenu.add(langMenu);
subPanel.add(buttonsPanel, BorderLayout.NORTH);
subPanel.add(slidersPanel, BorderLayout.SOUTH);
mainPanel.add(subPanel);
mainPanel.add(plot);
add(mainPanel);
param.addAmplitudeListener(new ChangeListener()
{
public void stateChanged(ChangeEvent a)
{
double ampValue = param.getAmplitudeValue();
aValue.setText(String.valueOf(ampValue));
}
}
);
param.addFrequencyListener(new ChangeListener()
{
public void stateChanged(ChangeEvent f)
{
double frValue = param.getFrequencyValue();
fValue.setText(String.valueOf(frValue));
}
}
);
param.addPhaseListener(new ChangeListener()
{
public void stateChanged(ChangeEvent p)
{
double phValue = param.getPhaseValue();
pValue.setText(String.valueOf(phValue));
}
}
);
}
public JMenuBar getmainMenu()
{
return mainMenu;
}
private static void GUI()
{
Window mainPanel = new Window();
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.setJMenuBar(mainPanel.getmainMenu());
frame.pack();
frame.setVisible(true);
}
public static void main(String[] args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
GUI();
}
}
);
}
}
class Parameters extends JPanel
{
private JPanel pane = new JPanel();
private JPanel ampPanel = new JPanel();
private JPanel frPanel = new JPanel();
private JPanel phPanel = new JPanel();
private JSlider amplitude = new JSlider(0,100,0);
private JSlider frequency = new JSlider(0,10000,0);
private JSlider phase = new JSlider(0,180,0);
private JLabel pLabel = new JLabel("Faza");
private JLabel aLabel = new JLabel("Amplituda (dB)");
private JLabel fLabel = new JLabel("Częstotliwość (Hz)");
private JTextField preciseAmplitude = new JTextField(3);
private JTextField preciseFrequency = new JTextField(4);
private JTextField precisePhase = new JTextField(3);
public Parameters()
{
preciseAmplitude.setEditable(true);
preciseFrequency.setEditable(true);
precisePhase.setEditable(true);
pane.setLayout(new BoxLayout(pane, BoxLayout.PAGE_AXIS));
ampPanel.setLayout(new FlowLayout());
frPanel.setLayout(new FlowLayout());
phPanel.setLayout(new FlowLayout());
amplitude.setMajorTickSpacing(10);
amplitude.setMinorTickSpacing(5);
amplitude.setPaintTicks(true);
amplitude.setPaintLabels(true);
frequency.setMajorTickSpacing(2000);
frequency.setMinorTickSpacing(100);
frequency.setPaintTicks(true);
frequency.setPaintLabels(true);
phase.setMajorTickSpacing(2/10);
phase.setPaintTicks(true);
phase.setPaintLabels(true);
setBorder(BorderFactory.createTitledBorder("Parametry fali"));
ampPanel.add(aLabel);
ampPanel.add(preciseAmplitude);
pane.add(ampPanel);
pane.add(Box.createRigidArea(new Dimension(0,5)));
pane.add(amplitude);
pane.add(Box.createRigidArea(new Dimension(0,10)));
frPanel.add(fLabel);
frPanel.add(preciseFrequency);
pane.add(frPanel);
pane.add(Box.createRigidArea(new Dimension(0,5)));
pane.add(frequency);
pane.add(Box.createRigidArea(new Dimension(0,10)));
phPanel.add(pLabel);
phPanel.add(precisePhase);
pane.add(phPanel);
pane.add(Box.createRigidArea(new Dimension(0,5)));
pane.add(phase);
pane.add(Box.createRigidArea(new Dimension(0,10)));
add(pane);
}
public int getAmplitudeValue()
{
return amplitude.getValue();
}
public int getFrequencyValue()
{
return frequency.getValue();
}
public int getPhaseValue()
{
return phase.getValue();
}
public void addAmplitudeListener(ChangeListener ampListener)
{
amplitude.addChangeListener(ampListener);
}
public void addFrequencyListener(ChangeListener frListener)
{
frequency.addChangeListener(frListener);
}
public void addPhaseListener(ChangeListener phListener)
{
phase.addChangeListener(phListener);
}
}
class Plot extends JPanel
{
private JPanel componentWave = new JPanel();
private JPanel netWave = new JPanel();
private JLabel componentLabel = new JLabel("Fale składowe");
private JLabel netLabel = new JLabel("Fala wypadkowa");
private JLabel wave = new JLabel("Wybierz falę składową");
private JPanel labels = new JPanel();
private JComboBox chooseWave = new JComboBox();
public Plot()
{
labels.setLayout(new BoxLayout(labels, BoxLayout.PAGE_AXIS));
componentWave.setBackground(new Color(255,255,255));
netWave.setBackground(new Color(255,255,255));
componentWave.setBorder(BorderFactory.createBevelBorder(BevelBorder.LOWERED));
netWave.setBorder(BorderFactory.createBevelBorder(BevelBorder.LOWERED));
componentWave.setPreferredSize(new Dimension(400,200));
netWave.setPreferredSize(new Dimension(400,200));
labels.add(wave);
labels.add(Box.createRigidArea(new Dimension(0,10)));
labels.add(chooseWave);
labels.add(componentLabel);
labels.add(componentWave);
labels.add(Box.createRigidArea(new Dimension(0,20)));
labels.add(netLabel);
labels.add(netWave);
add(labels);
}
}
Window is intended to be a 'main GUI class' and Sliders is supposed to inherit (?) from it.
Nope: this is a misuse of inheritance and will only lead to problems since the Windows instance that Sliders inherently is, is completely distinct from the displayed Windows instance. What you need to do is to pass references.
For example, the following code uses outside classes for the JButton and JMenuItem Actions (Actions are like ActionListeners on steroids), and uses a class that holds a JSlider that allows itside classes to attach listeners to the slider.
import java.awt.Component;
import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import javax.swing.*;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
public class Foo extends JPanel {
private static final long serialVersionUID = 1L;
private Action helloAction = new HelloAction("Hello", KeyEvent.VK_H);
private Action exitAction = new ExitAction("Exit", KeyEvent.VK_X);
private JMenuBar menuBar = new JMenuBar();
private JTextField sliderValueField = new JTextField(10);
private Bar bar = new Bar();
public Foo() {
sliderValueField.setEditable(false);
sliderValueField.setFocusable(false);
add(new JButton(helloAction));
add(new JButton(exitAction));
add(new JLabel("Slider Value: "));
add(sliderValueField);
add(bar);
JMenu fileMenu = new JMenu("File");
fileMenu.setMnemonic(KeyEvent.VK_F);
fileMenu.add(new JMenuItem(exitAction));
fileMenu.add(new JMenuItem(helloAction));
menuBar.add(fileMenu);
bar.addSliderListener(new ChangeListener() {
#Override
public void stateChanged(ChangeEvent e) {
int sliderValue = bar.getSliderValue();
sliderValueField.setText(String.valueOf(sliderValue));
}
});
}
public JMenuBar getJMenuBar() {
return menuBar;
}
private static void createAndShowGui() {
Foo mainPanel = new Foo();
JFrame frame = new JFrame("Foo");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.setJMenuBar(mainPanel.getJMenuBar());
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
class HelloAction extends AbstractAction {
public HelloAction(String name, int mnemonic) {
super(name); // sets name property and gives button its title
putValue(MNEMONIC_KEY, mnemonic);
}
#Override
public void actionPerformed(ActionEvent e) {
JOptionPane.showMessageDialog(null, "Hello!");
}
}
class ExitAction extends AbstractAction {
private static final long serialVersionUID = 1L;
public ExitAction(String name, int mnemonic) {
super(name);
putValue(MNEMONIC_KEY, mnemonic);
}
#Override
public void actionPerformed(ActionEvent e) {
Component component = (Component) e.getSource();
Window win = SwingUtilities.getWindowAncestor(component);
if (win == null) {
// if no window, then a JMenuItem held in a JPopupMenu
JPopupMenu popup = (JPopupMenu) component.getParent();
component = popup.getInvoker();
win = SwingUtilities.getWindowAncestor(component);
}
win.dispose();
}
}
class Bar extends JPanel {
private JSlider slider = new JSlider(0, 100, 50);
public Bar() {
slider.setPaintLabels(true);
slider.setPaintTicks(true);
slider.setMajorTickSpacing(20);
slider.setMinorTickSpacing(5);
slider.setSnapToTicks(true);
setBorder(BorderFactory.createTitledBorder("Slider Panel"));
add(slider);
}
public int getSliderValue() {
return slider.getValue();
}
// one way to let outside classes listen for changes
public void addSliderListener(ChangeListener listener) {
slider.addChangeListener(listener);
}
}
You ask about decimal labels, and yes this can be done but requires use of a label table. For example,
JSlider slider = new JSlider(0, 100, 50);
slider.setPaintLabels(true);
slider.setPaintTicks(true);
slider.setMajorTickSpacing(20);
slider.setMinorTickSpacing(2);
Dictionary<Integer, JLabel> labels = new Hashtable<>();
for (int i = 0; i <= 100; i += 20) {
labels.put(i, new JLabel(String.format("%.1f", i / 200.0)));
}
slider.setLabelTable(labels);
Which displays as:
You would also have to translate the value back from int to its corresponding floating point number.
This is the JPanel
public class DisplayBoard {
public static void main (String[] args) {
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//The main panel
JPanel main = new JPanel();
main.setPreferredSize(new Dimension(600,800) );
main.setLayout(new BorderLayout());
//The title panel
JPanel title = new JPanel();
title.setPreferredSize(new Dimension(400, 120));
title.setBackground(Color.YELLOW);
JLabel test1 = new JLabel("Title goes here");
title.add(test1);
//The side bar panel
JPanel sidebar = new JPanel();
sidebar.setPreferredSize(new Dimension(200, 800));
sidebar.add(AddSubtract);
sidebar.setBackground(Color.GREEN);
JLabel test2 = new JLabel("Sidebar goes here");
sidebar.add(test2);
//The panel that displays all the cards
JPanel cardBoard = new JPanel();
cardBoard.setPreferredSize(new Dimension(400,640) );
//adding panels to the main panel
main.add(cardBoard, BorderLayout.CENTER);
main.add(title, BorderLayout.NORTH);
main.add(sidebar, BorderLayout.WEST);
frame.setContentPane(main);
frame.pack();
frame.setVisible(true);
}
}
and I want to add this class into the sidebar panel
public class AddSubtract {
int Number = 0;
private JFrame Frame = new JFrame("Math");
private JPanel ContentPane = new JPanel();
private JButton Button1 = new JButton("Add");
private JButton Button2 = new JButton("Subtract");
private JLabel Num = new JLabel ("Number: " + Integer.toString (Number));
public AddSubtract() {
Frame.setContentPane(ContentPane);
ContentPane.add(Button1);
ContentPane.add(Button2);
ContentPane.add(Num);
Button1.addActionListener(new Adding());
Button2.addActionListener(new Subtracting());
}
public class Adding implements ActionListener {
public void actionPerformed(ActionEvent e) {
Number++;
Num.setText ("Number: " + Integer.toString (Number));
}
}
public class Subtracting implements ActionListener {
public void actionPerformed(ActionEvent e) {
Number--;
Num.setText ("Number: " + Integer.toString (Number));
}
}
public void launchFrame(){
Frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
Frame.pack();
Frame.setVisible(true);
}
public static void main(String args[]){
AddSubtract Test = new AddSubtract();
Test.launchFrame();
}
}
Can someone explain to me how I can do this ?
I have a feeling that this is not going to work, but I really want to learn the way to do it.
This definately is not going to work. For starters, you have two main() methods. Second, if you want to add a class to your Frame, it should extend from JComponent. Basically, your code should look like this:
public class MainFrame extends JFrame {
public MainFrame() {
this.add(new MainPanel())
//insert all settings here.
}
}
public class MainPanel extends JPanel {
public MainPanel() {
this.add(new AddSubtract());
this.add(/*more panels*/)
}
}
public class AddSubtract extends JPanel {
public AddSubtract() {
//add buttons and stuff here
}
}
and variables do NOT start with capitals.
Edit: And when you have some JFrame, it's usually best to have a main() method with just one line:
public static void main(String[] args) {
new MainFrame();
}
just set the settings and configuration of the JFrame in the constructor.
I know it's something to do with how I've set it up and the actionlistener not being correctly set to the frame or something but I just can't get my hear around it. If someone could point me in the right direction I'd be much obliged. Sorry for noob question.
Here's what I have:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class Main implements ActionListener {
JPanel cardHolder;
public static final String HOME_CARD = "Home";
public static final String BLUE_PANEL = "Blue Panel";
public static final String RED_PANEL = "Red Panel";
public static final String ORANGE_PANEL = "Orange Panel";
public static JButton home = new JButton("Home");
public static JButton bluePanel = new JButton("Blue Card");
public static JButton redPanel = new JButton("Red Panel");
public static JButton orangePanel = new JButton("Orange Panel");
public static JPanel createCardHolderPanel() {
JPanel cardHolder = new JPanel(new CardLayout());
cardHolder.setBorder(BorderFactory.createTitledBorder("Card Holder Panel"));
cardHolder.add(createHomeCard(), HOME_CARD);
cardHolder.add(createBluePanel(), BLUE_PANEL);
cardHolder.add(createRedPanel(), RED_PANEL);
cardHolder.add(createOrangePanel(), ORANGE_PANEL);
return cardHolder;
}
private static JPanel createOrangePanel() {
JPanel orangePanel = new JPanel();
orangePanel.setBackground(Color.orange);
return orangePanel;
}
private static Component createRedPanel() {
JPanel redPanel = new JPanel();
redPanel.setBackground(Color.red);
return redPanel;
}
private static Component createBluePanel() {
JPanel bluePanel = new JPanel();
bluePanel.setBackground(Color.blue);
return bluePanel;
}
private static Component createHomeCard() {
JPanel homePanel = new JPanel();
homePanel.setBackground(Color.GRAY);
return homePanel;
}
public static JPanel createButtonPanel() {
JPanel buttonPanel = new JPanel(new GridLayout(4, 0, 5, 5));
buttonPanel.setBorder(BorderFactory.createTitledBorder("Button Panel"));
buttonPanel.add(home);
buttonPanel.add(bluePanel);
buttonPanel.add(redPanel);
buttonPanel.add(orangePanel);
return buttonPanel;
}
public static JPanel createContentPane() {
JPanel contentPane = new JPanel(new BorderLayout());
contentPane.setBorder(BorderFactory.createTitledBorder("Main Content Pane"));
contentPane.setBackground(Color.WHITE);
contentPane.setPreferredSize(new Dimension(499, 288));
contentPane.add(createButtonPanel(), BorderLayout.WEST);
contentPane.add(createCardHolderPanel(),BorderLayout.CENTER);
return contentPane;
}
public static JMenuBar createMenuBar() {
JMenuBar menuBar = new JMenuBar();
JMenu file = new JMenu("File");
JMenu users = new JMenu("Users");
JMenu options = new JMenu("Options");
JMenu help = new JMenu("Help");
menuBar.add(file);
menuBar.add(users);
menuBar.add(options);
menuBar.add(help);
return menuBar;
}
public static void createAndShowGUI() {
JFrame frame = new JFrame("Simple CardLayout Program");
frame.setContentPane(createContentPane());
frame.setJMenuBar(createMenuBar());
frame.pack();
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGUI();
}
});
}
#Override
public void actionPerformed(ActionEvent e) {
if (e.getSource() == home) {
CardLayout cardLayout = (CardLayout) (cardHolder.getLayout());
cardLayout.show(cardHolder, HOME_CARD);
}
if (e.getSource() == bluePanel) {
CardLayout cardLayout = (CardLayout) (cardHolder.getLayout());
cardLayout.show(cardHolder, BLUE_PANEL);
}
if (e.getSource() == redPanel) {
CardLayout cardLayout = (CardLayout) (cardHolder.getLayout());
cardLayout.show(cardHolder, RED_PANEL);
}
if (e.getSource() == orangePanel) {
CardLayout cardLayout = (CardLayout) (cardHolder.getLayout());
cardLayout.show(cardHolder, ORANGE_PANEL);
}
}
}
Others have suggested listening to the buttons; in addition:
Prefer the lowest accessibility consistent with use, e.g. private rather than public.
Don't make everything static.
Use static for immutable constants used throughout the class.
Use class variables rather than static members for content.
Don't repeat your self, e.g. initialize cardLayout just once in your actionPerformed)().
Use parameters rather than separate methods for each color, e.g.
private JPanel createColorPanel(Color color) {...}
Revised code:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class Main implements ActionListener {
private static final String HOME_CARD = "Home";
private static final String BLUE_PANEL = "Blue Panel";
private static final String RED_PANEL = "Red Panel";
private static final String ORANGE_PANEL = "Orange Panel";
private JPanel cardHolder;
private JButton homeButton = new JButton("Home");
private JButton blueButton = new JButton("Blue Card");
private JButton redButton = new JButton("Red Panel");
private JButton orangeButton = new JButton("Orange Panel");
public JPanel createCardHolderPanel() {
cardHolder = new JPanel(new CardLayout());
cardHolder.setBorder(BorderFactory.createTitledBorder("Card Holder Panel"));
cardHolder.add(createColorPanel(Color.gray), HOME_CARD);
cardHolder.add(createColorPanel(Color.blue), BLUE_PANEL);
cardHolder.add(createColorPanel(Color.red), RED_PANEL);
cardHolder.add(createColorPanel(Color.orange), ORANGE_PANEL);
return cardHolder;
}
private JPanel createColorPanel(Color color) {
JPanel panel = new JPanel();
panel.setBackground(color);
return panel;
}
public JPanel createButtonPanel() {
JPanel buttonPanel = new JPanel(new GridLayout(4, 0, 5, 5));
buttonPanel.setBorder(BorderFactory.createTitledBorder("Button Panel"));
buttonPanel.add(homeButton);
buttonPanel.add(blueButton);
buttonPanel.add(redButton);
buttonPanel.add(orangeButton);
homeButton.addActionListener(this);
blueButton.addActionListener(this);
redButton.addActionListener(this);
orangeButton.addActionListener(this);
return buttonPanel;
}
public JPanel createContentPane() {
JPanel panel = new JPanel(new BorderLayout());
panel.setBorder(BorderFactory.createTitledBorder("Main Content Pane"));
panel.setBackground(Color.WHITE);
panel.setPreferredSize(new Dimension(499, 288));
panel.add(createButtonPanel(), BorderLayout.WEST);
panel.add(createCardHolderPanel(), BorderLayout.CENTER);
return panel;
}
public JMenuBar createMenuBar() {
JMenuBar menuBar = new JMenuBar();
JMenu file = new JMenu("File");
JMenu users = new JMenu("Users");
JMenu options = new JMenu("Options");
JMenu help = new JMenu("Help");
menuBar.add(file);
menuBar.add(users);
menuBar.add(options);
menuBar.add(help);
return menuBar;
}
#Override
public void actionPerformed(ActionEvent e) {
CardLayout cardLayout = (CardLayout) (cardHolder.getLayout());
if (e.getSource() == homeButton) {
cardLayout.show(cardHolder, HOME_CARD);
}
if (e.getSource() == blueButton) {
cardLayout.show(cardHolder, BLUE_PANEL);
}
if (e.getSource() == redButton) {
cardLayout.show(cardHolder, RED_PANEL);
}
if (e.getSource() == orangeButton) {
cardLayout.show(cardHolder, ORANGE_PANEL);
}
}
public static void createAndShowGUI() {
JFrame frame = new JFrame("Simple CardLayout Program");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
Main main = new Main();
frame.setJMenuBar(main.createMenuBar());
frame.add(main.createContentPane());
frame.pack();
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
createAndShowGUI();
}
});
}
}
You have not set an action listener for any of the buttons. Implementing the actionPerformed method of the interface does not automatically set an action listener for the buttons. You have to call the addActionListener method which in your case would look like the following since your class implements the ActionListener Interface.
public static JButton home = new JButton("Home").addActionListener(this);
public static JButton bluePanel = new JButton("Blue Card").addActionListener(this);
public static JButton redPanel = new JButton("Red Panel").addActionListener(this);
public static JButton orangePanel = new JButton("Orange Panel").addActionListener(this);