Prevent automatic JScrollPane viewport change on content resize - java

I have a JScrollPane with a custom JPanel as the content. The scrollpane has a mouse wheel handler, so when the user scrolls, the content is 'zoomed', and the JPanel becomes larger in height.
I need to ensure that the user's viewport maintains position on the current row of pixels on the JPanel that are currently under the mouse. However, when I manually try and set the viewport in the wheel handler, I can't ensure consistent focus, as sometimes the JScrollPane overrides my changes with the default behaviour for when JScrollPane's content becomes larger.
I've made a simple example showing the structure of my program as below, however the example only tries to ensure the viewport focus remains on the bottom of the JPanel when scrolling in as the panel doubles in size. The scroll wheel causes the JPanel to double/halve in height.
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Rectangle;
import java.awt.event.MouseEvent;
import java.awt.event.MouseWheelEvent;
import java.awt.event.MouseWheelListener;
import javax.swing.*;
public class Test extends JFrame{
public static void main(String[] args){
Test t= new Test();
t.show();
}
public Test()
{
BorderLayout blm = new BorderLayout();
setLayout(blm);
getContentPane().add(new MyScroller(), BorderLayout.CENTER);
this.setPreferredSize(new Dimension(300, 300));
this.setMinimumSize(new Dimension(300, 300));
pack();
setLocationRelativeTo(null);
setVisible(true);
}
static class MyScroller extends JScrollPane implements MouseWheelListener
{
static InnerPanel controlGrid = new InnerPanel();
int panelHeight = 200;
public MyScroller()
{
super(controlGrid, JScrollPane.VERTICAL_SCROLLBAR_ALWAYS, JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
this.setBackground(Color.blue);
this.addMouseWheelListener(this);
this.setPreferredSize(new Dimension(300, 300));
this.setMinimumSize(new Dimension(300, 300));
}
#Override
public void revalidate()
{
super.revalidate();
if (controlGrid != null)
{
controlGrid.revalidate();
}
}
#Override
public void paintComponent(Graphics g)
{
super.paintComponent(g);
draw(g);
}
public void draw(Graphics g)
{
}
public void mouseWheelMoved(MouseWheelEvent e) {
String message;
int direction = 1;
int notches = e.getWheelRotation();
if (notches < 0) {
panelHeight += panelHeight;
} else {
panelHeight -= (panelHeight > panelHeight ? panelHeight : 0);
}
controlGrid.setPreferredSize(new Dimension(20, panelHeight));
controlGrid.setMinimumSize(new Dimension(20, panelHeight));
repaint();
this.getViewport().setViewPosition(new java.awt.Point(0, panelHeight));
}
static class InnerPanel extends JPanel
{
public InnerPanel(){
this.setBackground(Color.red);
this.setPreferredSize(new Dimension(100, 600));
this.setMinimumSize(new Dimension(100, 600));
}
}
}
}

Related

Why is JPanel size is wrong?

There is constructor of class extending JFrame:
import java.awt.*;
import javax.swing.*;
public class ChessFrame extends JFrame {
public ChessFrame () {
setSize(520, 520);
setResizable(false);
setLocationRelativeTo(null);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLayout(new GridLayout(1, 1));
// Add components
getContentPane().add(new Board());
pack();
setVisible(true);
}
}
And class extending JPanel:
import javax.swing.*;
public class Board extends JPanel {
public Board() {
setSize(new Dimension(520, 520));
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
g.fillRect(0, 0, 520, 520);
}
#Override
public Dimension getPreferredSize() {
return new Dimension(520, 520);
}
}
As a result rectangle smaller then 520x520.
Size of black rectangle is about 496x510. There is more:
getWidth() and getHegiht() written inside the Board class, returns 0 and 0 (so size of this JPanel into JFrame is 0x0)
If I remove pack(), size of frame becomes 496x510 (black rectangle size)
It's actually copypaste of official java tutorial: https://docs.oracle.com/javase/tutorial/uiswing/painting/step2.html.
Do I do something wrong or it's something related with java? If it's second, why does this happen?
Any help would be appreciated.
This example only tries to establish the panel size once the frame (and panel) are visible on-screen. It returns the exact size (300 pixels) set in the code.
import java.awt.*;
import javax.swing.*;
public class ChessBoard extends JPanel {
int size = 300;
JLabel sizeLabel = new JLabel();
ChessBoard() {
setBackground(Color.CYAN);
setLayout(new GridBagLayout());
add(sizeLabel);
}
public void showSize() {
sizeLabel.setText(String.format("%1sx%1s", getWidth(), getHeight()));
}
#Override
public Dimension getPreferredSize() {
return new Dimension(size,size);
}
public static void main(String[] args) {
Runnable r = () -> {
ChessBoard cb = new ChessBoard();
JFrame f = new JFrame(cb.getClass().getSimpleName());
f.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
f.setLocationByPlatform(true);
f.setContentPane(cb);
f.pack();
f.setMinimumSize(f.getSize());
f.setVisible(true);
// delay showing size until app. is on-screen
Runnable r1 = cb::showSize;
SwingUtilities.invokeLater(r1);
};
SwingUtilities.invokeLater(r);
}
}

How do I draw shape on the JPanel, also linking the shape with an event control?

I've made a code to draw a simple oval in a panel and then according to the button clicked (left or right) or arrow button, it will move accordingly. This code I have here doesn't seem to make the shape appear in the yellow background. Is there anything that I can change?
Also, I will also link the made oval into two separate keyboard and button click events. Is using KeyAdaptor method and lambda expression on the mouse event a good measure here? Thank you in advance!
private JButton btnLeftMvmt, btnRightMvmt;
class MyPanel extends JPanel {
public void paintComponent(Graphics g) {
super.paintComponents(g);
int width = getWidth()/2;
int top = (getHeight() - HEIGHT) / 2;
/* Code above is a vain attempt to center the oval to the yellow
background.
Is this correct, as well?*/
g.fillOval(width, top, 150, 150);
g.setColor(Color.RED);
}
}
public MyFrame(){
setTitle("Red Oval Translator");
setSize(500, 200);
setLayout(new BorderLayout());
JPanel panel1, panel2;
panel1 = new JPanel();
panel2 = new JPanel();
panel1.add(new MyPanel());
panel1.setBackground(Color.YELLOW);
btnLeftMvmt = new JButton("Left Translation");
btnRightMvmt = new JButton("Right Translation");
panel2.add(btnLeftMvmt);
panel2.add(btnRightMvmt);
add(panel1);
add(panel2, BorderLayout.SOUTH);
setLocationRelativeTo(null);
setVisible(true);
I assume you wanted something like that:
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
class MyPanel extends JPanel {
public MyPanel() {
setPreferredSize(new Dimension(300, 250));
}
#Override
public void paintComponent(Graphics g) {
super.paintComponents(g);
int width = getWidth()/2;
int top = (getHeight() - HEIGHT) / 2;
g.setColor(Color.RED); //need to apply color before painting
g.fillOval(width, top, 150, 150);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(()->new MyFrame());
}
}
class MyFrame extends JFrame{
private JButton btnLeftMvmt, btnRightMvmt;
public MyFrame() {
setTitle("Red Oval Translator");
setLayout(new BorderLayout()); //BorderLayout for JFrame
JPanel panel2 = new JPanel();
btnLeftMvmt = new JButton("Left Translation");
btnRightMvmt = new JButton("Right Translation");
panel2.add(btnLeftMvmt);
panel2.add(btnRightMvmt);
add(new MyPanel());
add(panel2, BorderLayout.SOUTH);
setLocationRelativeTo(null);
pack();
setVisible(true);
}
}
Always post mcve
One problem with your code is that you should swap the order of g.fillOval(width, top, 150, 150); and g.setColor(Color.RED); to get a red oval and not a default-colored oval.

What prevents java swing components from being painted when added to a JComponent?

JTextField, JSlider, JComboBox, etc added to a JComponent are not displayed in the JFrame containing the JComponent. It seems only drawing by the Graphics parameter allows painting. The included test program compares using JPanel to JComponent in my efforts to discover how to display components added to a JComponent. Is there any way to get such components displayed?
public class TestPaints {
public static void main(String[] args) {
new TestPaints();
}
JTextField _text1;
JLabel _label1 = new JLabel("Text1");
JTextField _text2;
JLabel _label2 = new JLabel("Text2");
TestPaints() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
JFrame frame = new JFrame("Paint a Widget");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new GridLayout(3, 2));
GridBagConstraints grid = new GridBagConstraints();
frame.add(new JLabel("TextField in JComponent "));
grid.gridx = 2;
frame.add(new JLabel("TextField in JPanel"), grid);
grid.gridy = 2;
grid.gridx = 1;
frame.add(new TestJComponent(), grid);
grid.gridx = 2;
frame.add(new TestJPanel(), grid);
grid.gridy = 3;
grid.gridx = 1;
/* tabbing between the two TextFields shows that keystrokes are seen */
frame.add(_label1, grid);
grid.gridx = 2;
frame.add(_label2, grid);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestJComponent extends JComponent {
public TestJComponent() {
setPreferredSize(new Dimension(100, 30));
_text1 = new JTextField(6);
_text1.addKeyListener(new KeyAdapter() {
public void keyPressed(KeyEvent e) {
_label1.setText(_text1.getText());
_label1.repaint();
}
});
_text1.setOpaque(true);
_text1.setVisible(true);
add(_text1);
/* This doesn't work
JPanel panel = new JPanel();
panel.add(_text1);
add(panel); */
setOpaque(true);
setVisible(true);
setBackground(Color.green);
}
public void paint(Graphics g) {
super.paint(g); // did not do background. Rectangle r = g.getClipBounds(); // needs this
g.setColor(getBackground());
g.fillRect(r.x, r.y, r.width, r.height);
/* Variations such as these don't work */
_text1.setOpaque(true);
_text1.setVisible(true);
_text1.paintComponents(g);
}
}
class TestJPanel extends JPanel {
TestJPanel() {
_text2 = new JTextField(6);
_text2.addKeyListener(new KeyAdapter() {
public void keyPressed(KeyEvent e) {
_label2.setText(_text2.getText());
_label2.repaint();
}
});
add(_text2);
setBackground(Color.blue);
}
}
}
Edit: you need to give your JComponent a layout such as FlowLayout for components to show properly since it does not have a default layout like JPanel has. So add setLayout(new FlowLayout()) into your JComponent's constructor
You have:
frame.setLayout(new GridLayout(3, 2));
and then try to add components to the JFrame's contentPane using GridBagConstraints, and this doesn't make sense. If you want to use these constraints, then the container needs to use GridBagLayout, not GridLayout.
Also this is dangerous code:
public void paint(Graphics g) {
super.paint(g); // did not do background. Rectangle r = g.getClipBounds(); // needs this
g.setColor(getBackground());
g.fillRect(r.x, r.y, r.width, r.height);
/* Variations such as these don't work */
_text1.setOpaque(true);
_text1.setVisible(true);
_text1.paintComponents(g);
}
You should be overriding JComponent's paintComponent method, not its paint method (call super.paintComponent) and should not be setting component visibility or calling a component's paintComponents method directly within any painting method.
Another issue: don't use KeyListeners within Swing text components but rather add a DocumentListener to the component's Document. Otherwise you risk breaking some of the functionality of the text component, and also your listener won't work for copy/paste, while the DocumentListener will.
And another issue, your main issue: you need to give the JComponent a layout. It does not default to FlowLayout like a JPanel does. This is why the added components are not showing within it.
For example:
import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.GridLayout;
import javax.swing.BorderFactory;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.SwingUtilities;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
import javax.swing.text.BadLocationException;
import javax.swing.text.Document;
public class TestPaints2 {
private JTextField textField1 = new JTextField(8);
private JTextField textField2 = new JTextField(8);
private JLabel label1 = new JLabel("Text1");
private JLabel label2 = new JLabel("Text2");
public TestPaints2() {
textField1.getDocument().addDocumentListener(new MyDocListener(label1));
textField2.getDocument().addDocumentListener(new MyDocListener(label2));
TestJComponent2 jComponent = new TestJComponent2();
jComponent.add(textField1);
TestJPanel2 jPanel = new TestJPanel2();
jPanel.add(textField2);
JPanel mainPanel = new JPanel(new GridLayout(0, 2));
mainPanel.add(new JLabel("JComponent"));
mainPanel.add(new JLabel("JPanel"));
mainPanel.add(jComponent);
mainPanel.add(jPanel);
mainPanel.add(label1);
mainPanel.add(label2);
JFrame frame = new JFrame("Test");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(mainPanel);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
private class MyDocListener implements DocumentListener {
private JLabel label;
public MyDocListener(JLabel label) {
this.label = label;
}
#Override
public void changedUpdate(DocumentEvent e) {
updateLabel(e);
}
#Override
public void insertUpdate(DocumentEvent e) {
updateLabel(e);
}
#Override
public void removeUpdate(DocumentEvent e) {
updateLabel(e);
}
private void updateLabel(DocumentEvent e) {
Document doc = e.getDocument();
int offset = doc.getLength();
try {
String text = doc.getText(0, offset);
label.setText(text);
} catch (BadLocationException e1) {
e1.printStackTrace();
}
}
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> new TestPaints2());
}
}
class TestJComponent2 extends JComponent {
private static final Color BG = Color.GREEN;
private static final int GAP = 5;
public TestJComponent2() {
setOpaque(true);
setBackground(BG);
setLayout(new FlowLayout());
setBorder(BorderFactory.createEmptyBorder(GAP, GAP, GAP, GAP));
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
g.setColor(getBackground());
g.fillRect(0, 0, getWidth(), getHeight());
}
}
class TestJPanel2 extends JPanel {
private static final Color BG = Color.BLUE;
private static final int GAP = 5;
public TestJPanel2() {
setBackground(BG);
setBorder(BorderFactory.createEmptyBorder(GAP, GAP, GAP, GAP));
}
}

Unable to add other components to window after creating background using JLabel in Java

I want to create a java Application like a widget. Here is my code below
package newpackage;
public class MainFrame extends JFrame {
JLabel imageLabel = new JLabel();
public MainFrame() {
try {
this.setUndecorated(true);
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(new Dimension(360, 360));
ImageIcon ii = new ImageIcon(this.getClass().getResource("imageexcel.gif"));
imageLabel.setIcon(ii);
add(imageLabel, java.awt.BorderLayout.CENTER);
this.setVisible(true);
Shape shape=new Ellipse2D.Float(0,0,360,360);
AWTUtilities.setWindowShape(this, shape);
AWTUtilities.setWindowOpaque(this, false);
imageLabel.add(new JButton("START"));
} catch (Exception exception) {
exception.printStackTrace();
}
}
public static void main(String[] args) {
new MainFrame();
}
}
In the above code, I have done the following:
Created a Frame
Removed the Title Bar
Added the Background using JLabel
Changed the shape of window as circle according to the shape of image
Now I would like to add some components in to it and perform some action with them but no component is visible after adding.
I have tried adding to Frame as well as JLabel and no use from either.
This is the image i used for background
Please help me to proceed further....
Thanking you
JLabels use null layouts by default, and so your button will default to size 0,0. Try giving it a decent layout manager, even FlowLayout would likely work. Another solution is to keep the null layout and set the sizes and positions of added components, but this route is a dangerous route and one I don't recommend.
Actually a GridBagLayout works nice to center the components. Also add all components before calling setVisible(true):
imageLabel.setLayout(new GridBagLayout());
this.setUndecorated(true);
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(new Dimension(360, 360));
ImageIcon ii = new ImageIcon(this.getClass().getResource("imageexcel.gif"));
imageLabel.setIcon(ii);
add(imageLabel, java.awt.BorderLayout.CENTER);
imageLabel.add(new JButton("START"));
this.setVisible(true);
or better?
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.GridBagLayout;
import java.awt.Image;
import java.awt.Shape;
import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.awt.geom.Ellipse2D;
import java.net.URL;
import javax.swing.*;
import com.sun.awt.AWTUtilities;
#SuppressWarnings("serial")
public class MainPanelOvalFrame extends JPanel {
private static final String RESOURCE_PATH = "imageexcel.gif";
private Window window;
private Image img;
public MainPanelOvalFrame(Window window, Image image) {
this.window = window;
this.img = image;
setLayout(new GridBagLayout());
add(new JButton(new StartAction("Start", KeyEvent.VK_S)));
int w = image.getWidth(this);
int h = image.getHeight(this);
Shape shape = new Ellipse2D.Float(0, 0, w, h);
AWTUtilities.setWindowShape(window, shape);
AWTUtilities.setWindowOpaque(window, false);
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
if (img != null) {
g.drawImage(img, 0, 0, this);
}
}
#Override
public Dimension getPreferredSize() {
if (isPreferredSizeSet() || img == null) {
return super.getPreferredSize();
}
int w = img.getWidth(this);
int h = img.getHeight(this);
return new Dimension(w, h);
}
private class StartAction extends AbstractAction {
public StartAction(String name, int mnemonic) {
super(name);
putValue(MNEMONIC_KEY, mnemonic);
}
#Override
public void actionPerformed(ActionEvent e) {
window.dispose();
}
}
private static void createAndShowGui() {
JFrame frame = new JFrame();
frame.setUndecorated(true);
URL imgUrl = MainPanelOvalFrame.class.getResource(RESOURCE_PATH);
Image image = new ImageIcon(imgUrl).getImage();
MainPanelOvalFrame mainPanel = new MainPanelOvalFrame(frame, image);
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
You just need to set a Layout manager for imageLabel ,or use null as the Layout manager, then set the size and location of the JButton manually.
to use Layout Manager
imageLabel.setIcon(ii);
imageLabel.setLayout(new FlowLayout());
imageLabel.add(new JButton("START"));
//need to setLayout and add JButton before setVisible(true)
add(imageLabel, java.awt.BorderLayout.CENTER);
this.setVisible(true);
to use null layout
JButton j=new JButton("START");
j.setSize(100,50);
j.setLocation(imageLabel.getWidth()/2-j.getWidth()/2, imageLabel.getHeight()/2-j.getHeight()/2);
//then add Button into imageLabel
imageLabel.add(j);
Layout manager is usually recommended because it can fit different environment.

Why do I have one scrollPanel which works and another which doesn't?

I have the one big panel on the left with a scrollPanel wrapped around it and it works fine; but in the upper right corner I have a panel which is also supposed to have a scrollPanel, but I cant seem to get it so that the scrollbars can actually move. They just stay full and unmovable. Can someone please help me work out why this is?
This scrollPanel is the one causing issues:
public MapBuilderSidePanel(Dimension size){
tileSetPanel = new MapBuilderTileSetPanel(new Dimension(tileSetPanelWidth,tileSetPanelHeight),6,17, tileSetPanelHeight, tileSetPanelWidth, this);
scrollPane = new JScrollPane(tileSetPanel, JScrollPane.VERTICAL_SCROLLBAR_ALWAYS, JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
//add(tileSet, BorderLayout.NORTH);
add(scrollPane, BorderLayout.CENTER);
setPreferredSize(size);
setBorder(new BevelBorder(BevelBorder.LOWERED));
setVisible(true);
}
This is the code for my little application, I've tried to strip out as much as possible. It is copy paste compile and runnable.
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Rectangle;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.border.BevelBorder;
public class MapBuilderFrame extends JFrame {
/**
* #param args
*/
private String frameTitle = "Yoonsio Map Editor";
private int frameWidth = 1000;
private int frameHeight = 1000;
private MapBuilderPanel mainPanel;
private MapBuilderSidePanel myLeftSidePanel;
private MapBuilderSidePanel myRightSidePanel;
private JScrollPane scrollPane;
public MapBuilderFrame() {
myRightSidePanel = new MapBuilderSidePanel(new Dimension(200,2000));
mainPanel = new MapBuilderPanel(myRightSidePanel);
setTitle(frameTitle);
setSize(frameWidth,frameHeight);
setDefaultCloseOperation(EXIT_ON_CLOSE);
setVisible(true);
setPreferredSize(new Dimension(450, 110));
setResizable(false);
scrollPane = new JScrollPane(mainPanel,JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
add(scrollPane, BorderLayout.CENTER);
add(myRightSidePanel, BorderLayout.EAST);
}
public static void main(String[] args) {
new MapBuilderFrame();
}
}
/***************************************************************************/
class MapBuilderPanel extends JPanel {
/**
* #param args
*/
private final int NUMERIC_TO_ASCII_OFFSET = 96;
private MapBuilderSidePanel mySidePanel;
private Rectangle hoverRect;
public MapBuilderPanel(MapBuilderSidePanel mySidePanel){
this.mySidePanel = mySidePanel;
setPreferredSize(new Dimension(2000,2000));
setBackground(new Color(0x00006595));
}
public void refresh(){
this.repaint();
}
public void paint(Graphics g){
g.setColor(new Color(0x00006595));
g.fillRect(0, 0, 2000, 2000);
}
}
/***************************************************************************/
class MapBuilderSidePanel extends JPanel {
/* Ypos = the Y position counter used to draw the grid*/
private MapBuilderTileSetPanel tileSetPanel;
/* Width and Heights pertaining to the tileset grid */
private int tileSetPanelHeight = 400;
private int tileSetPanelWidth = 175;
private JScrollPane scrollPane;
/*only constructor needed*/
public MapBuilderSidePanel(Dimension size){
tileSetPanel = new MapBuilderTileSetPanel(new Dimension(tileSetPanelWidth,tileSetPanelHeight),6,17, tileSetPanelHeight, tileSetPanelWidth, this);
scrollPane = new JScrollPane(tileSetPanel, JScrollPane.VERTICAL_SCROLLBAR_ALWAYS, JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
//add(tileSet, BorderLayout.NORTH);
add(scrollPane, BorderLayout.CENTER);
setPreferredSize(size);
setBorder(new BevelBorder(BevelBorder.LOWERED));
setVisible(true);
}
// Remember override paintComponent(); NOT paint().
public void paintComponent(Graphics g){
}
public void loadTileSet(String filename, int r, int c){
//tileSet.loadTileSet(filename, r, c);
}
public void refresh(){
tileSetPanel.repaint();
}
}
/***************************************************************************/
class MapBuilderTileSetPanel extends JPanel{
private MapBuilderSidePanel myParent;
MapBuilderTileSetPanel(Dimension size, int columns, int rows, int parentPanelHeight, int parentPanelWidth, MapBuilderSidePanel mp){
this.myParent = mp;
setBackground(Color.BLACK);
setPreferredSize(size);
setSize(1000,1000);
setBorder(new BevelBorder(BevelBorder.LOWERED));
}
public void loadTileSet(String filename, int c, int r){
}
public void paintComponent(Graphics g){
g.setColor(new Color(0x00550055));
g.drawRect(25, 25, 25, 25);
g.setColor(new Color(0x0000FF00));
g.drawRect(30, 30, 200, 500);
}
public MapBuilderTileSetPanel returnThis() {
return this;
}
}
You may be looking for JScrollNavigator, examined here.
Notes on your SSCCE:
Swing GUI objects should be constructed and manipulated only on the event dispatch thread.
"Swing programs should override paintComponent() instead of overriding paint()."—Painting in AWT and Swing: The Paint Methods.
Don't use setPreferredSize() when you really mean to override getPreferredSize(), as discussed here.
The scrollbar will appear automatically whenever the scrollpane is smaller than the enclosed component, as noted here.
Your scrollPane have no preffered size, so it is scaling to inner component.
Add:
scrollPane.setPreferredSize( new Dimension(200, 200));
Also as mKorbel pointed, call upper class method when you ovveride it.

Categories