Using the cut() method in java - java

I would like to implement the cut method in java to provide the cut and paste functionality.I have already used StringSelection and getSystemClipboard() to provide the cut functionality(code below),but I wanna know how I can use java's inbuilt cut() method for it.
Code for cut functionality.
String t = qu.getText();
StringSelection s = new StringSelection(t);
this.getToolkit().getSystemClipboard().setContents(s, s);
qu.setText("");
I expected something like this to work but it didn't
qu.cut();
Thanks in advance.

If Swing just use the Actions available from the DefaultEditorKit:
new DefaultEditorKit.CutAction()
For example, a small program that uses default actions in a menu, a component-specific pop-up menu, and in buttons:
import java.awt.BorderLayout;
import java.awt.GridLayout;
import java.awt.event.FocusAdapter;
import java.awt.event.FocusEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import javax.swing.*;
import javax.swing.text.*;
public class TestActions {
private String[] texts = {
"Hello", "Goodbye", "What the f***?", "Heck if I know", "Peace out man!"
};
private JTextArea textArea = new JTextArea(10, 30);
private Action[] textActions = { new DefaultEditorKit.CutAction(),
new DefaultEditorKit.CopyAction(), new DefaultEditorKit.PasteAction(), };
private JPanel mainPanel = new JPanel();
private JMenuBar menubar = new JMenuBar();
private JPopupMenu popup = new JPopupMenu();
private PopupListener popupListener = new PopupListener();
public TestActions() {
JPanel btnPanel = new JPanel(new GridLayout(1, 0, 5, 5));
JMenu menu = new JMenu("Edit");
for (Action textAction : textActions) {
btnPanel.add(new JButton(textAction));
menu.add(new JMenuItem(textAction));
popup.add(new JMenuItem(textAction));
}
menubar.add(menu);
JPanel textFieldPanel = new JPanel(new GridLayout(0, 1, 5, 5));
for (String text: texts) {
JTextField textField = new JTextField(text, 15);
textField.addMouseListener(popupListener);
textFieldPanel.add(textField);
textField.addFocusListener(new FocusAdapter() {
#Override
public void focusGained(FocusEvent e) {
((JTextComponent)e.getSource()).selectAll();
}
});
}
textArea.addMouseListener(popupListener);
JScrollPane scrollPane = new JScrollPane(textArea);
JPanel textFieldPanelWrapper = new JPanel(new BorderLayout());
textFieldPanelWrapper.add(textFieldPanel, BorderLayout.NORTH);
mainPanel.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));
mainPanel.setLayout(new BorderLayout(5, 5));
mainPanel.add(btnPanel, BorderLayout.NORTH);
mainPanel.add(scrollPane, BorderLayout.CENTER);
mainPanel.add(textFieldPanelWrapper, BorderLayout.EAST);
}
public JComponent getMainPanel() {
return mainPanel;
}
private JMenuBar getMenuBar() {
return menubar;
}
private class PopupListener extends MouseAdapter {
public void mousePressed(MouseEvent e) {
maybeShowPopup(e);
}
public void mouseReleased(MouseEvent e) {
maybeShowPopup(e);
}
private void maybeShowPopup(MouseEvent e) {
if (e.isPopupTrigger()) {
popup.show(e.getComponent(),
e.getX(), e.getY());
}
}
}
private static void createAndShowGui() {
TestActions testActions = new TestActions();
JFrame frame = new JFrame("Test Actions");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(testActions.getMainPanel());
frame.setJMenuBar(testActions.getMenuBar());
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}

It is because cut() method requires a selection in the text field. Try the following code:
qu.selectAll();
qu.cut();

Related

JScrollpane on JPanel doesn't work

I am trying to add jscrollpane on my jframe through the jpanel but it doesn't work. The problem is that if i dont add a scroll bar and the string i want to display on the frame is too long, it won't be displayed and will be cut off.However, when i add the scrollpane the jframe doesn't display the string at all.To "draw" the string on the window, i am using setText(). This is my code:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
import java.net.*;
import javax.swing.border.LineBorder;
public class LabelFrame extends JFrame {
private final JTextField urlString;
private final JButton loadButton;
String content;
JTextArea textArea = new JTextArea();
public LabelFrame() {
super("WebStalker");
setSize(600, 600);
addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
});
setLayout(new FlowLayout());
urlString = new JTextField("https:Search",30);
loadButton = new JButton("Load");
JPanel panel = new JPanel();
JLabel label = new JLabel("URL");
panel.add(label);
panel.add(urlString);
panel.add(loadButton);
JScrollPane jp = new JScrollPane(textArea,JScrollPane.VERTICAL_SCROLLBAR_ALWAYS, JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
panel.add(jp);
this.add(panel);
pack(); // JFrame στο ελάχιστο μέγεθος με όλα τα περιεχόμενα
setLocationRelativeTo(null); //τοποθετεί στο κέντρο το παράθυρο
TextFieldHandler tHandler = new TextFieldHandler();
ButtonHandler bHandler = new ButtonHandler();
urlString.addActionListener(tHandler);
loadButton.addActionListener(bHandler);
urlString.addMouseListener(new MouseAdapter(){
#Override
public void mouseClicked(MouseEvent e){
urlString.setText("");
}
});
}
private class TextFieldHandler implements ActionListener {
#Override
public void actionPerformed(ActionEvent event){
try {
content = URLReaderFinal.Reading(event.getActionCommand());
textArea.setText(content);
textArea.setWrapStyleWord(true);
textArea.setLineWrap(true);
textArea.setOpaque(false);
textArea.setEditable(false);
textArea.setFocusable(false);
textArea.setBackgroung(UIManager.getColor("Label.background");
textArea.setFont(UIManager.getFont("Label.font"));
textArea.setBorder(UIManager.getBorder("Label.border"));
getContentPane().add(textArea, BorderLayout.CENTER);
}
catch(Exception e) {
JOptionPane.showMessageDialog(null, "This url doesnt exist","Error", JOptionPane.ERROR_MESSAGE);
}
}
}
private class ButtonHandler implements ActionListener {
#Override
public void actionPerformed(ActionEvent event) {
try {
content = URLReaderFinal.Reading(urlString.getText());
textArea.setText(content);
textArea.setWrapStyleWord(true);
textArea.setLineWrap(true);
textArea.setOpaque(false);
textArea.setEditable(false);
textArea.setFocusable(false);
textArea.setBackground(UIManager.getColor("Label.background"));
textArea.setFont(UIManager.getFont("Label.font"));
textArea.setBorder(UIManager.getBorder("Label.border"));
getContentPane().add(textArea, BorderLayout.CENTER);
} catch (Exception e) {
System.out.println("Unable to load page");
JOptionPane.showMessageDialog(null, "Unable to load page","Error", JOptionPane.ERROR_MESSAGE);
}
}
}
}
In your button handlers you are re-adding a JTextArea to the GUI without its JScrollPane:
getContentPane().add(textArea, BorderLayout.CENTER);
which is essentially removing it from the JScrollPane just when you need it inside of it -- don't do that as this will totally mess you up and will remove the JScrollPane from view. Instead leave the JTextArea where it is, don't try to re-add components to your JFrame's contentPane, and simply add text to the JTextArea as needed.
Also, don't forget to give your JTextArea column and row properties, something that can easily be done by using the constructor that takes two ints. And leave the contentPane's layout as BorderLayout:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.util.*;
import java.net.*;
import javax.swing.border.LineBorder;
#SuppressWarnings("serial")
public class LabelFrame extends JFrame {
private static final int ROWS = 30;
private static final int COLS = 80;
private final JTextField urlString;
private final JButton loadButton;
String content;
JTextArea textArea = new JTextArea(ROWS, COLS);
public LabelFrame() {
super("WebStalker");
// setSize(600, 600);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
// setLayout(new FlowLayout()); // !! no
textArea.setWrapStyleWord(true);
textArea.setLineWrap(true);
textArea.setOpaque(false);
textArea.setEditable(false);
textArea.setFocusable(false);
textArea.setBackground(UIManager.getColor("Label.background"));
textArea.setFont(UIManager.getFont("Label.font"));
textArea.setBorder(UIManager.getBorder("Label.border"));
urlString = new JTextField("https:Search", 30);
loadButton = new JButton("Load");
JPanel panel = new JPanel();
JLabel label = new JLabel("URL");
panel.add(label);
panel.add(urlString);
panel.add(loadButton);
JScrollPane jp = new JScrollPane(textArea, JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,
JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
// panel.add(jp);
this.add(panel, BorderLayout.PAGE_START);
add(jp);
pack(); // JFrame στο ελάχιστο μέγεθος με όλα τα περιεχόμενα
setLocationRelativeTo(null); // τοποθετεί στο κέντρο το παράθυρο
TextFieldHandler tHandler = new TextFieldHandler();
ButtonHandler bHandler = new ButtonHandler();
urlString.addActionListener(tHandler);
loadButton.addActionListener(bHandler);
urlString.addMouseListener(new MouseAdapter() {
#Override
public void mouseClicked(MouseEvent e) {
urlString.setText("");
}
});
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
new LabelFrame().setVisible(true);
});
}
private class TextFieldHandler implements ActionListener {
#Override
public void actionPerformed(ActionEvent event) {
try {
content = URLReaderFinal.Reading(event.getActionCommand());
textArea.setText(content);
// !! getContentPane().add(textArea, BorderLayout.CENTER);
} catch (Exception e) {
JOptionPane.showMessageDialog(null, "This url doesnt exist", "Error", JOptionPane.ERROR_MESSAGE);
}
}
}
private class ButtonHandler implements ActionListener {
#Override
public void actionPerformed(ActionEvent event) {
try {
content = URLReaderFinal.Reading(urlString.getText());
textArea.setText(content);
// getContentPane().add(textArea, BorderLayout.CENTER);
} catch (Exception e) {
System.out.println("Unable to load page");
JOptionPane.showMessageDialog(null, "Unable to load page", "Error", JOptionPane.ERROR_MESSAGE);
}
}
}
}
edit: don't use a MouseListener on a JTextField. Perhaps you want to use a FocusListener instead.
Instead do something like:
public class LabelFrame extends JFrame {
private static final int ROWS = 30;
private static final int COLS = 80;
private static final String HTTPS_SEARCH = "https:Search";
// .....
public LabelFrame() {
// ....
urlString = new JTextField(HTTPS_SEARCH, 30);
//.....
urlString.addFocusListener(new FocusAdapter() {
#Override
public void focusGained(FocusEvent e) {
JTextField textField = (JTextField) e.getComponent();
String text = textField.getText();
if (text.equals(HTTPS_SEARCH)) {
textField.setText("");
}
}
});

Calling method from one class in other

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.

How to refresh JFrame

I know there were similar questions but I have some different problem...
I'd like to remove all elements of JFrame after clicking a button:
It works:
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent arg0)
{
frame.getContentPane().removeAll();
frame.revalidate();
frame.repaint();
}
});
All elements disappeared. But after that I need to putelements on this JFrame... After these 3 lines above (below frame.repaint()) I call method initialize (method that I call when I create my window at the beginning):
private void initialize()
{
frame = new JFrame();
frame.setBounds(100, 100, 1454, 860);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().setLayout(null);
JButton btnNewSubject = new JButton("New subject");
btnNewSubject.setBounds(647, 788, 137, 23);
frame.getContentPane().add(btnNewSubject);
JButton btnRefresh = new JButton("Refresh");
btnRefresh.setBounds(1339, 788, 89, 23);
frame.getContentPane().add(btnRefresh);
JLabel lblNewLabel = new JLabel("Subject");
lblNewLabel.setBounds(235, 11, 75, 14);
frame.getContentPane().add(lblNewLabel);
JLabel lblOwner = new JLabel("Owner");
lblOwner.setBounds(662, 11, 46, 14);
frame.getContentPane().add(lblOwner);
JLabel lblStatus = new JLabel("Status");
lblStatus.setBounds(883, 11, 46, 14);
frame.getContentPane().add(lblStatus);
JLabel lblDateOfAdded = new JLabel("Date of added");
lblDateOfAdded.setBounds(1104, 11, 116, 14);
frame.getContentPane().add(lblDateOfAdded);
}
Nothing happens. :( JFrame is still empty. Even if I call revalidate and repaint().
What is wrong?
You are creating a completely new JFrame in your method here
frame = new JFrame();
and you never display it, you never call setVisible(true) on it, and so it will remain invisible. It almost sounds as if you're creating two JFrames without realizing it, that you are adding components to the second non-displayed JFrame, but are leaving displaying just the first one, the one without new components.
More importantly, you will want to use a CardLayout to help you swap your JPanel views as this situation is exactly what it's built for. Also, Your program uses null layout and setBounds(...) something that results in a rigid GUI that may look good on one system but will usually look poor on any other system or screen resolution. Programs created this way are very hard to debug, maintain and upgrade. Instead use the layout managers as this is what they excel at: at creating complex flexible GUI's that can be enhanced and changed easily.
Note that your removeAll() call does not remove the root pane as Ludovic is stating because you're calling this on the contentPane not the JFrame, and the contentPane does not contain the root pane.
Edit
For example,
import java.awt.BorderLayout;
import java.awt.CardLayout;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import javax.swing.*;
import javax.swing.table.DefaultTableModel;
public class CardLayoutEg extends JPanel {
private CardLayout cardlayout = new CardLayout();
private TitlePanel titlePanel = new TitlePanel(this);
private SubjectPanel subjectPanel = new SubjectPanel(this);
public CardLayoutEg() {
setLayout(cardlayout);
add(titlePanel, titlePanel.getName());
add(subjectPanel, subjectPanel.getName());
}
public void nextCard() {
cardlayout.next(this);
}
public void showCard(String key) {
cardlayout.show(this, key);
}
private static void createAndShowGui() {
JFrame frame = new JFrame("CardLayout Example");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(new CardLayoutEg());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
class TitlePanel extends JPanel {
public static final String TITLE_PANEL = "title panel";
private static final int PREF_W = 900;
private static final int PREF_H = 750;
private static final String TITLE = "My Application Title";
private static final float POINTS = 46f;
private CardLayoutEg cardLayoutEg;
public TitlePanel(CardLayoutEg cardLayoutEg) {
setName(TITLE_PANEL);
this.cardLayoutEg = cardLayoutEg;
JLabel titleLabel = new JLabel(TITLE, SwingConstants.CENTER);
titleLabel.setFont(titleLabel.getFont().deriveFont(Font.BOLD, POINTS));
JButton subjectButton = new JButton(new SubjectAction("Subjects"));
JPanel buttonPanel = new JPanel();
buttonPanel.add(subjectButton);
setLayout(new BorderLayout());
add(titleLabel, BorderLayout.CENTER);
add(buttonPanel, BorderLayout.PAGE_END);
}
#Override
public Dimension getPreferredSize() {
if (isPreferredSizeSet()) {
return super.getPreferredSize();
}
return new Dimension(PREF_W, PREF_H);
}
private class SubjectAction extends AbstractAction {
public SubjectAction(String name) {
super(name);
int mnemonic = (int) name.charAt(0);
putValue(MNEMONIC_KEY, mnemonic);
}
#Override
public void actionPerformed(ActionEvent e) {
cardLayoutEg.showCard(SubjectPanel.SUBJECT_PANEL);
}
}
}
class SubjectPanel extends JPanel {
public static final String SUBJECT_PANEL = "subject panel";
private static final String[] COLUMN_NAMES = {"Subject", "Owner", "Status", "Date Added"};
DefaultTableModel tableModel = new DefaultTableModel(COLUMN_NAMES, 10);
private JTable table = new JTable(tableModel);
private CardLayoutEg cardLayoutEg;
public SubjectPanel(CardLayoutEg cardLayoutEg) {
setBorder(BorderFactory.createTitledBorder("Subject Panel"));
setName(SUBJECT_PANEL);
this.cardLayoutEg = cardLayoutEg;
JPanel buttonPanel = new JPanel();
buttonPanel.setLayout(new GridLayout(1, 0, 10, 0));
buttonPanel.add(new JButton("New Subject"));
buttonPanel.add(new JButton("Refresh"));
buttonPanel.add(new JButton(new TitleAction("Title")));
buttonPanel.add(new JButton(new ExitAction("Exit")));
JPanel bottomPanel = new JPanel();
bottomPanel.setLayout(new BoxLayout(bottomPanel, BoxLayout.LINE_AXIS));
bottomPanel.add(Box.createHorizontalGlue());
bottomPanel.add(buttonPanel);
setLayout(new BorderLayout());
add(new JScrollPane(table), BorderLayout.CENTER);
add(bottomPanel, BorderLayout.PAGE_END);
}
private class TitleAction extends AbstractAction {
public TitleAction(String name) {
super(name);
int mnemonic = (int) name.charAt(0);
putValue(MNEMONIC_KEY, mnemonic);
}
#Override
public void actionPerformed(ActionEvent e) {
cardLayoutEg.showCard(TitlePanel.TITLE_PANEL);
}
}
private class ExitAction extends AbstractAction {
public ExitAction(String name) {
super(name);
int mnemonic = KeyEvent.VK_X;
putValue(MNEMONIC_KEY, mnemonic);
}
#Override
public void actionPerformed(ActionEvent e) {
Component component = (Component) e.getSource();
Window win = SwingUtilities.getWindowAncestor(component);
win.dispose();
}
}
}

update components based on which tab its called from

Hello Guru's I am a beginner Java swing developer and am trying to build a simple app... here is a simplified version.
Setup: 1 JFrame, 2 BorderLayout based tabbed panels (A and B) each has 1 textfiled, shared JPanel class with combo box and ItemListener initialized in each tab's (North)
Issue: How to control updates to textfield's text based on which panel it came from eg. if I select Apples in TabA, the Item Listener updates the TextField on TabB as well. What I would like to accomplish is determine where the call came from TabA or TabB and only update the textfield associated with that tab.
Hope this makes some sense
public class Main extends JFrame {
private static final long serialVersionUID = 1L;
private JPanel contentPane;
public JTextField tfPanelA;
public JTextField tfPanelB;
/**
* Launch the application.
*/
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
Main frame = new Main();
frame.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
/**
* Create the frame.
*/
public Main() {
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setBounds(100, 100, 450, 300);
contentPane = new JPanel();
contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
contentPane.setLayout(new BorderLayout(0, 0));
setContentPane(contentPane);
JTabbedPane tabbedPane = new JTabbedPane(JTabbedPane.TOP);
contentPane.add(tabbedPane, BorderLayout.CENTER);
JPanel panelA = new JPanel();
tabbedPane.addTab("Tab A", null, panelA, null);
panelA.setLayout(new BorderLayout(0, 0));
sharedPanel s1 = new sharedPanel(this);
panelA.add(s1, BorderLayout.NORTH);
tfPanelA = new JTextField();
panelA.add(tfPanelA);
tfPanelA.setColumns(10);
JPanel panelB = new JPanel();
tabbedPane.addTab("Tab B", null, panelB, null);
panelB.setLayout(new BorderLayout(0, 0));
sharedPanel s2 = new sharedPanel(this);
panelB.add(s2, BorderLayout.NORTH);
tfPanelB = new JTextField();
panelB.add(tfPanelB);
tfPanelB.setColumns(10);
}
}
// Shared Class...
public class sharedPanel extends JPanel {
private Main app;
private String[] clist = {"Apples","Oranges","Bananas"};
/**
* Create the panel.
*/
public sharedPanel(final Main app) {
this.app=app;
setLayout(new FlowLayout(FlowLayout.CENTER, 5, 5));
JComboBox<String> comboBox = new JComboBox<String>();
comboBox.setModel(new DefaultComboBoxModel<String>(clist));
comboBox.addItemListener(new ItemListener() {
public void itemStateChanged(ItemEvent e) {
//update PanelA's textfield ONLY if called from PanelA
// do this if called from PanelA
app.tfPanelA.setText(e.getItem().toString());
// do this if called from PanelB
app.tfPanelB.setText(e.getItem().toString());
}
});
add(comboBox);
}
}
Since you have create a new instance of sharedPanel for each tab, simply provide a reference to the text field you want to be updated to it...
Which you end up with something more like...
public class sharedPanel extends JPanel {
private JTextField field;
private String[] clist = {"Apples","Oranges","Bananas"};
public sharedPanel(final JTextField field) {
this.field=field;
setLayout(new FlowLayout(FlowLayout.CENTER, 5, 5));
JComboBox<String> comboBox = new JComboBox<String>();
comboBox.setModel(new DefaultComboBoxModel<String>(clist));
comboBox.addItemListener(new ItemListener() {
public void itemStateChanged(ItemEvent e) {
sharedPanel.this.field.setText(e.getItem().toString());
}
});
add(comboBox);
}
}
Updated with a "model" example
This is very basic example of just one possible use of a model to bridge the changes between the common panel and other panels. This means that the common panel doesn't care about anything else and updates the supplied model, which fires events to interested parties who can take appropriate action as required.
import java.awt.BorderLayout;
import java.awt.EventQueue;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.util.ArrayList;
import java.util.List;
import javax.swing.DefaultComboBoxModel;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JTabbedPane;
import javax.swing.JTextField;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
public class TabbedModel {
protected static final String[] MAIN_LIST = {"Apples","Oranges","Bananas"};
public static void main(String[] args) {
new TabbedModel();
}
public TabbedModel() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
}
JTabbedPane tabPane = new JTabbedPane();
tabPane.addTab("A", new ATab());
tabPane.addTab("B", new ATab());
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new BorderLayout());
frame.add(tabPane);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class DefaultCommonModel implements CommonModel {
private List<ChangeListener> listeners;
private String value;
public DefaultCommonModel() {
listeners = new ArrayList<>(25);
}
#Override
public void addChangeListener(ChangeListener listener) {
listeners.add(listener);
}
#Override
public void removeChangeListener(ChangeListener listener) {
listeners.remove(listener);
}
#Override
public void setValue(String aValue) {
if (aValue == null ? value != null : !aValue.equals(value)) {
value = aValue;
fireStateChanged();
}
}
#Override
public String getValue() {
return value;
}
protected void fireStateChanged() {
if (!listeners.isEmpty()) {
ChangeEvent evt = new ChangeEvent(this);
for (ChangeListener listener : listeners) {
listener.stateChanged(evt);
}
}
}
}
public interface CommonModel {
public void addChangeListener(ChangeListener listener);
public void removeChangeListener(ChangeListener listener);
public void setValue(String value);
public String getValue();
}
public class CommonPanel extends JPanel {
private CommonModel model;
private JComboBox comboBox;
public CommonPanel(CommonModel model) {
this.model = model;
setLayout(new GridBagLayout());
comboBox = new JComboBox(new DefaultComboBoxModel<>(MAIN_LIST));
comboBox.addItemListener(new ItemListener() {
#Override
public void itemStateChanged(ItemEvent e) {
String value = (String) e.getItem();
CommonPanel.this.model.setValue(value);
}
});
add(comboBox);
}
}
public class ATab extends JPanel {
private List<JTextField> fields;
public ATab() {
setLayout(new GridBagLayout());
GridBagConstraints gbc = new GridBagConstraints();
gbc.gridwidth = GridBagConstraints.REMAINDER;
DefaultCommonModel model = new DefaultCommonModel();
model.addChangeListener(new ChangeListener() {
#Override
public void stateChanged(ChangeEvent e) {
CommonModel model = (CommonModel) e.getSource();
for (JTextField field : fields) {
field.setText(model.getValue());
}
}
});
CommonPanel commonPanel = new CommonPanel(model);
add(commonPanel, gbc);
fields = new ArrayList<>(25);
for (int index = 0; index < random(); index++) {
JTextField field = new JTextField(10);
add(field, gbc);
fields.add(field);
}
}
protected int random() {
return (int)Math.round(Math.random() * 9) + 1;
}
}
}
Since you have two instances of your SharedPanel you can add the textfield to be updated as a reference to the constructor:
SharedPanel s1 = new SharedPanel(this, tfPanelA);
and
public SharedPanel(final Main app, final JTextField tf) {
...
comboBox.addItemListener(new ItemListener() {
public void itemStateChanged(ItemEvent e) {
tf.setText(e.getItem().toString());
}
});
...
}

JProgressbar width using Grid/FlowLayout

I'm working on a downloader which looks like this at the moment:
The JFrame uses a BorderLayout.
In the NORTH, I have a JPanel(FlowLayout). In the SOUTH there is also a JPanel(FlowLayout), in the WEST I just have a JTextArea (in a JScrollPane). This is all shown correctly. However, in the EAST I currently have a JPanel(GridLayout(10, 1)).
I want to show up to 10 JProgressBars in the EAST section which are added and removed from the panel dynamically. The problem is, I can not get them to look like I want to them to look: I want the JProgressBars' width to fill up the entire EAST section because 1) This gives the app a more symmetrical look and 2) The ProgressBars may contain long strings that don't fit at the moment. I've tried putting the JPanel that contains the GridLayout(10, 1) in a flowlayout and then put that flowlayout in the EAST section, but that didn't work either.
My code (SSCCE) is currently as follows:
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.HashMap;
import java.util.Map;
public class Main {
public static void main(String[] args) {
new DownloadFrame();
}
private static class DownloadFrame extends JFrame {
private JButton downloadButton;
private JTextField threadIdTextField;
private JTextArea downloadStatusTextArea;
private JScrollPane scrollPane;
private JTextField downloadLocationTextField;
private JButton downloadLocationButton;
private JPanel North;
private JPanel South;
private JPanel ProgressBarPanel;
private Map<String, JProgressBar> progressBarMap;
public DownloadFrame() {
InitComponents();
InitLayout();
AddComponents();
AddActionListeners();
setVisible(true);
setSize(700, 300);
}
private void InitComponents() {
downloadButton = new JButton("Dowload");
threadIdTextField = new JTextField(6);
downloadStatusTextArea = new JTextArea(10, 30);
scrollPane = new JScrollPane(downloadStatusTextArea, ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
downloadLocationTextField = new JTextField(40);
downloadLocationButton = new JButton("...");
North = new JPanel();
South = new JPanel();
ProgressBarPanel = new JPanel();
progressBarMap = new HashMap<String, JProgressBar>();
}
private void InitLayout() {
North.setLayout(new FlowLayout());
South.setLayout(new FlowLayout());
ProgressBarPanel.setLayout(new GridLayout(10, 1));
}
private void AddComponents() {
North.add(threadIdTextField);
North.add(downloadButton);
add(North, BorderLayout.NORTH);
add(ProgressBarPanel, BorderLayout.EAST);
South.add(downloadLocationTextField);
South.add(downloadLocationButton);
add(South, BorderLayout.SOUTH);
add(scrollPane, BorderLayout.WEST);
}
private void AddActionListeners() {
downloadButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
addNewProgessBar(threadIdTextField.getText());
}
});
}
public void addNewProgessBar(String threadId) {
JProgressBar progressBar = new JProgressBar();
progressBar.setStringPainted(true);
progressBarMap.put(threadId, progressBar);
drawProgessBars();
}
void drawProgessBars() {
ProgressBarPanel.removeAll();
for (JProgressBar progressBar : progressBarMap.values()) {
ProgressBarPanel.add(progressBar);
}
validate();
repaint();
}
}
}
Thanks in advance.
EDIT
Easiest solution: change
add(ProgressBarPanel, BorderLayout.EAST);
to
add(ProgressBarPanel, BorderLayout.CENTER);
import javax.swing.*;
import javax.swing.border.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.HashMap;
import java.util.Map;
public class Main {
public static void main(String[] args) {
new DownloadFrame();
}
private static class DownloadFrame extends JFrame {
private JButton downloadButton;
private JTextField threadIdTextField;
private JTextArea downloadStatusTextArea;
private JScrollPane scrollPane;
private JTextField downloadLocationTextField;
private JButton downloadLocationButton;
private JPanel North;
private JPanel South;
private JPanel ProgressBarPanel;
private Map<String, JProgressBar> progressBarMap;
public DownloadFrame() {
InitComponents();
AddComponents();
AddActionListeners();
pack();
setVisible(true);
//setSize(700, 300);
}
private void InitComponents() {
setLayout(new BorderLayout());
downloadButton = new JButton("Dowload");
threadIdTextField = new JTextField(6);
downloadStatusTextArea = new JTextArea(10, 30);
scrollPane = new JScrollPane(downloadStatusTextArea, ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
downloadLocationTextField = new JTextField(40);
downloadLocationButton = new JButton("...");
North = new JPanel(new FlowLayout());
South = new JPanel(new FlowLayout());
ProgressBarPanel = new JPanel(new GridLayout(0, 1));
ProgressBarPanel.setBorder(new LineBorder(Color.black));
ProgressBarPanel.setPreferredSize(new Dimension(300,20));
progressBarMap = new HashMap<String, JProgressBar>();
}
private void AddComponents() {
North.add(threadIdTextField);
North.add(downloadButton);
add(North, BorderLayout.NORTH);
add(ProgressBarPanel, BorderLayout.EAST);
South.add(downloadLocationTextField);
South.add(downloadLocationButton);
add(South, BorderLayout.SOUTH);
add(scrollPane, BorderLayout.WEST);
}
private void AddActionListeners() {
downloadButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
addNewProgessBar(threadIdTextField.getText());
}
});
}
public void addNewProgessBar(String threadId) {
JProgressBar progressBar = new JProgressBar();
progressBar.setStringPainted(true);
progressBarMap.put(threadId, progressBar);
drawProgessBars();
}
void drawProgessBars() {
ProgressBarPanel.removeAll();
for (JProgressBar progressBar : progressBarMap.values()) {
ProgressBarPanel.add(progressBar);
}
validate();
repaint();
}
}
}
well. that possible, but in your example CENTER area occupated some Rectangle, its hard to reduce/remove CENTER area to the zero Size
to the North JPanel (BorderLayout) place another JPanel and put it to the EAST (with LayoutManager would be GridLayout(1,2,10,10)) and put here two JComponents JTextField - threadIdTextField and JButton - downloadButton, there you are needed setPreferredSize 1) for JComponents (correct way) or 2) for whole JPanel (possible way too)
JScrollPane with JTextArea must be placed to the CENTER area
JPanel with JProgressBars place to EAST, but again set same PreferredSize as for JPanel with JTextField and JButton from the NORTH
SOUTH JPanel remains without changes
Please post a compilable runnable small program for the quickest best help, an SSCCE.
Suggestions include using GridLayout(0, 1) (variable number of rows, one column), or display the JProgressBars in a JList that uses a custom renderer that extends JProgressBar.
Edit 1:
I know that Andrew has already posted the accepted answer (and 1+ for an excellent answer), but I just wanted to demonstrate that this can be done readily with a JList, something like so:
import java.awt.*;
import java.awt.event.*;
import java.beans.*;
import java.util.Random;
import javax.swing.*;
public class EastProgressList extends JPanel {
private DefaultListModel myListModel = new DefaultListModel();
private JList myList = new JList(myListModel);
private JTextField downloadUrlField = new JTextField(10);
public EastProgressList() {
JButton downLoadBtn = new JButton("Download");
downLoadBtn.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
downloadAction();
}
});
JPanel northPanel = new JPanel();
northPanel.add(new JLabel("File to Download:"));
northPanel.add(downloadUrlField);
northPanel.add(Box.createHorizontalStrut(15));
northPanel.add(downLoadBtn);
myList.setCellRenderer(new ProgressBarCellRenderer());
JScrollPane eastSPane = new JScrollPane(myList);
eastSPane.setPreferredSize(new Dimension(200, 100));
setLayout(new BorderLayout());
add(new JScrollPane(new JTextArea(20, 30)), BorderLayout.CENTER);
add(northPanel, BorderLayout.NORTH);
add(eastSPane, BorderLayout.EAST);
}
private void downloadAction() {
String downloadUrl = downloadUrlField.getText();
final MyData myData = new MyData(downloadUrl);
myListModel.addElement(myData);
myData.addPropertyChangeListener(new PropertyChangeListener() {
public void propertyChange(PropertyChangeEvent evt) {
if (evt.getPropertyName().equals(MyData.VALUE)) {
myList.repaint();
if (myData.getValue() >= 100) {
myListModel.removeElement(myData);
}
}
}
});
}
private class ProgressBarCellRenderer extends JProgressBar implements ListCellRenderer {
protected ProgressBarCellRenderer() {
setBorder(BorderFactory.createLineBorder(Color.blue));
}
public Component getListCellRendererComponent(JList list, Object value,
int index, boolean isSelected, boolean cellHasFocus) {
//setText(value.toString());
MyData myData = (MyData)value;
setValue(myData.getValue());
setString(myData.getText());
setStringPainted(true);
return this;
}
}
private static void createAndShowUI() {
JFrame frame = new JFrame("EastProgressList");
frame.getContentPane().add(new EastProgressList());
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
createAndShowUI();
}
});
}
}
class MyData {
public static final int TIMER_DELAY = 300;
public static final String VALUE = "value";
protected static final int MAX_DELTA_VALUE = 5;
private String text;
private int value = 0;
private Random random = new Random();
private PropertyChangeSupport pcSupport = new PropertyChangeSupport(this);
public MyData(String text) {
this.text = text;
new Timer(TIMER_DELAY, new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
int deltaValue = random.nextInt(MAX_DELTA_VALUE);
int newValue = value + deltaValue;
if (newValue >= 100) {
newValue = 100;
((Timer)e.getSource()).stop();
}
setValue(newValue);
}
}).start();
}
public String getText() {
return text;
}
public int getValue() {
return value;
}
public void setValue(int value) {
int oldValue = this.value;
this.value = value;
PropertyChangeEvent pcEvent = new PropertyChangeEvent(this, VALUE, oldValue, value);
pcSupport.firePropertyChange(pcEvent);
}
public void addPropertyChangeListener(PropertyChangeListener pcListener) {
pcSupport.addPropertyChangeListener(pcListener);
}
}
This results in a GUI looking like so:

Categories

Resources