Thanh Tran Van
Thanh Tran Van

Reputation: 23

how to make a jscrollpane scroll from the start to the end?

I'm trying to make a jscorllpane automatic scroll from the start to the end. I use set value method for verticalbar but it's doesn't work. How can i make it scroll ? Here is my code: When i run this code it just jump to the end of the jscorllpane instead of scorlling step by step

import java.awt.event.*;
import javax.swing.*;

import java.awt.BorderLayout;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

class JScrollPaneToTopAction implements ActionListener {
    JScrollPane scrollPane;

    public JScrollPaneToTopAction(JScrollPane scrollPane) {
        if (scrollPane == null) {
            throw new IllegalArgumentException("JScrollPaneToTopAction: null JScrollPane");
        }
        this.scrollPane = scrollPane;
    }

    public void actionPerformed(ActionEvent actionEvent) {
        run();
    }

    public void run() {
        JScrollBar verticalBar = scrollPane.getVerticalScrollBar();
        int i = verticalBar.getMinimum();
        while (i < verticalBar.getMaximum()) {
            verticalBar.setValue(verticalBar.getMinimum()+i);
            i += 50;
            try {
                Thread.sleep(100);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            scrollPane.getParent().invalidate();
            scrollPane.repaint();
            scrollPane.invalidate();
            System.out.println("changing " + i);
        }
    }

}

public class Draft20 {

    public static void main(String args[]) {
        JFrame frame = new JFrame("Tabbed Pane Sample");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JTextArea tr = new JTextArea();

        JLabel label = new JLabel("Label");
        label.setPreferredSize(new Dimension(1000, 1000));
        JScrollPane jScrollPane = new JScrollPane(label);

        JButton bn = new JButton("Move");

        bn.addActionListener(new JScrollPaneToTopAction(jScrollPane));

        frame.add(bn, BorderLayout.SOUTH);
        frame.add(jScrollPane, BorderLayout.CENTER);
        frame.setSize(400, 150);
        frame.setVisible(true);
    }
}

Upvotes: 0

Views: 413

Answers (1)

Dario
Dario

Reputation: 548

I think the problem is your calls to repaint are queued for computation by EDT, but EDT is busy executing your actionPerformed. EDT will execute your repaint requests only after your run() completes. That's why you can see only the final result.

I'm not sure I can make it clear... check this code, it works for me:

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

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JScrollBar;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.SwingUtilities;

class JScrollPaneToTopAction implements ActionListener, Runnable {

    JScrollPane scrollPane;

    public JScrollPaneToTopAction(JScrollPane scrollPane) {
        if (scrollPane == null) {
            throw new IllegalArgumentException("JScrollPaneToTopAction: null     JScrollPane");
        }
        this.scrollPane = scrollPane;
    }

    @Override
    public void actionPerformed(ActionEvent actionEvent) {
        new Thread(this).start();
    }

    @Override
    public void run() {
        JScrollBar verticalBar = scrollPane.getVerticalScrollBar();
        int i = verticalBar.getMinimum();
        while (i < verticalBar.getMaximum()) {
            verticalBar.setValue(verticalBar.getMinimum() + i);
            i += 50;
            try {
                Thread.sleep(100);
            }
            catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            SwingUtilities.invokeLater(new Runnable() {

                @Override
                public void run() {
                    scrollPane.getParent().invalidate();
                    scrollPane.repaint();
                    scrollPane.invalidate();
                }
            });
            System.out.println("changing " + i);
        }
    }
}

public class Draft20 {

    public static void main(String args[]) {
        JFrame frame = new JFrame("Tabbed Pane Sample");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JTextArea tr = new JTextArea();

        JLabel label = new JLabel("Label");
        label.setPreferredSize(new Dimension(1000, 1000));
        JScrollPane jScrollPane = new JScrollPane(label);

        JButton bn = new JButton("Move");

        bn.addActionListener(new JScrollPaneToTopAction(jScrollPane));

        frame.add(bn, BorderLayout.SOUTH);
        frame.add(jScrollPane, BorderLayout.CENTER);
        frame.setSize(400, 150);
        frame.setVisible(true);
    }
}

I hope it helps.

Upvotes: 2

Related Questions