Search code examples
javaswingjscrollpanejtextareajscrollbar

How to set scrollbar on TextArea in Java Swing?


I am working on a project which uses the Swing library in Java. Within my window, the TextArea is filled in with some content.

However, the TextArea is static and there is no scrollbar, because of which it only shows some of the content before the content overflows.

How can I add scrollability to my TextArea and/or make it dynamic?

PS- I am very new to Swing and GUI in Java.

I scavenged for a solution on the internet and found plenty, but none worked on implementation.

I tried out using a ScrollPane, a Scrollbar. I even set a Layout manager to BorderLayout() and GridBagLayout, but that just messed the window up and did not solve my problem of the static TextArea.

package crawler;

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.nio.charset.StandardCharsets;

public class WebCrawler extends JFrame {

    public WebCrawler() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setTitle("WebCrawlerWindow");
        setLocationRelativeTo(null);
        setSize(800, 600);

        JTextField urlName = new JTextField();
        urlName.setName("UrlTextField");
        urlName.setBounds(50,20,600,20);
        add(urlName);

        JTextArea jlb = new JTextArea("HTML code?");//this is the TextArea that needs to be scrollable
        jlb.setName("HtmlTextArea");
        jlb.setBounds(50,45,700,1000);
        jlb.setAutoscrolls(true);
        jlb.setLineWrap(true);
        jlb.setWrapStyleWord(true);
        jlb.disable();
        add(jlb, BorderLayout.CENTER);

        JButton download = new JButton();
        download.setName("RunButton");
        download.setBounds(660,20,70,20);
        download.setText("Get Code");

        var LINE_SEPARATOR = System.getProperty("line.separator");

        download.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                String url = urlName.getText().toLowerCase();/* Get url from JTextField */
                try {
                    if(!url.substring(0,7).equals("https://"))
                        url = String.join("","https://", url);

                    final InputStream inputStream = new URL(url).openStream();
                    final BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream, StandardCharsets.UTF_8));
                    final StringBuilder stringBuilder = new StringBuilder();

                    String nextLine;
                    while ((nextLine = reader.readLine()) != null) {
                        stringBuilder.append(nextLine);
                        stringBuilder.append(LINE_SEPARATOR);
                    }

                    final String siteText = stringBuilder.toString();
                    jlb.setText(siteText);
                } catch(Exception ex) {
                    jlb.setText("Link Not Found");
                }
            }
        });
        add(download);

        setLayout(null);
        setVisible(true);
    }
}

Solution

  • jlb.setAutoscrolls(true);
    ...
    add(jlb, BorderLayout.CENTER);
    

    The setAutoScrolls(...) method does not make the text area scrollable.

    You need to add the text area to a JScrollPane and add the scroll pane to the frame:

    //jlb.setAutoscrolls(true);
    ...
    //add(jlb, BorderLayout.CENTER);
    JScrollPane scrollPane = new JScrollPane( jlb );
    add(scrollPane, BorderLayout.CENTER);
    

    Also you should NOT be using a null layout. Swing was designed to be used with layout managers.

    add(download, BorderLayout.PAGE_START);
    //add(download);
    //setLayout(null);
    

    Read the section from the Swing tutorial on How to Use Border Layout to understand how the above suggestions affect the layout.