Search code examples
javaapache-pivot

Sizing Apache Pivot GUI components to the window


This question, Java Swing: Vertical Layout with fixed width and variable height, gave me an opportunity to try Apache Pivot. I have exactly one day's experience with Pivot.

Here's the GUI I've been able to create.

Segments GUI

My questions are:

  1. How do I size the TextArea that's part of the Expander, so that the Expander, ScrollPane, and TextArea fill the width of the window, and the TextArea is tall enough to hold an arbitrary amount of text?

  2. How do I size the height of the ScrollPane of the Expander so that when all of the text areas are expanded, the 3 Expanders fit the height of the window?

Here is the source code that created the GUI. I'm using version 2.0.2 of Apache Pivot.

import java.io.IOException;
import java.io.Reader;
import java.io.StringReader;
import java.util.ArrayList;
import java.util.List;

import org.apache.pivot.collections.Map;
import org.apache.pivot.wtk.Application;
import org.apache.pivot.wtk.BoxPane;
import org.apache.pivot.wtk.DesktopApplicationContext;
import org.apache.pivot.wtk.Display;
import org.apache.pivot.wtk.Expander;
import org.apache.pivot.wtk.Orientation;
import org.apache.pivot.wtk.ScrollPane;
import org.apache.pivot.wtk.TextArea;
import org.apache.pivot.wtk.Window;

public class Segments implements Application {

    protected SectionCollection collection;

    protected Window window;

    @Override
    public void startup(Display display, Map<String, String> properties) {
        collection = new SectionCollection();
        new SectionCollectionCreator(collection);

        window = new Window();
        window.setTitle("Segments");
        window.setMaximized(true);

        BoxPane boxPane = new BoxPane();
        boxPane.setOrientation(Orientation.VERTICAL);

        for (int i = 0; i < collection.size(); i++) {
            SectionText sectionText = collection.get(i);

            TextArea textArea = new TextArea();
            textArea.setEditable(false);
            textArea.setPreferredSize(400, 220);
            try {
                textArea.setText(sectionText.getTopic());
            } catch (IOException e) {
                e.printStackTrace();
            }

            ScrollPane textScrollPane = new ScrollPane();
            textScrollPane.setPreferredSize(420, 100);
            textScrollPane.setVerticalScrollBarPolicy(
                    ScrollPane.ScrollBarPolicy.AUTO);
            textScrollPane.setView(textArea);

            Expander expander = new Expander();
            expander.setTitle(sectionText.getTitle());
            expander.setContent(textScrollPane);
            expander.setExpanded(false);

            boxPane.add(expander);  
        }

        ScrollPane expanderScrollPane = new ScrollPane();
        expanderScrollPane.setHorizontalScrollBarPolicy(
                ScrollPane.ScrollBarPolicy.AUTO);
        expanderScrollPane.setVerticalScrollBarPolicy(
                ScrollPane.ScrollBarPolicy.AUTO);
        expanderScrollPane.setView(boxPane);

        window.setContent(expanderScrollPane);
        window.open(display);
    }

    @Override
    public boolean shutdown(boolean optional) {
        if (window != null) {
            window.close();
        }
        return false;
    }

    @Override
    public void suspend() {
    }

    @Override
    public void resume() {
    }

    public static void main(String[] args) {
        DesktopApplicationContext.main(Segments.class, args);
    }

    public class SectionText {
        protected String title;
        protected Reader topic;

        public SectionText(String title, Reader topic) {
            this.title = title;
            this.topic = topic;
        }

        public String getTitle() {
            return title;
        }

        public Reader getTopic() {
            return topic;
        }
    }

    public class SectionCollection {
        protected List<SectionText> collection;

        public SectionCollection() {
            this.collection = new ArrayList<SectionText>();
        }

        public void add(SectionText sectionText) {
            collection.add(sectionText);
        }

        public int size() {
            return collection.size();
        }

        public SectionText get(int index) {
            return collection.get(index);
        }
    }   

    public class SectionCollectionCreator {
        protected SectionCollection collection;

        protected static final String text = "Attributes, Styles and Style Contexts\n\n"
                + "The simple PlainDocument class that you saw in the previous "
                + "chapter is only capable of holding text. The more complex text "
                + "components use a more sophisticated model that implements the "
                + "StyledDocument interface. StyledDocument is a sub-interface of "
                + "Document that contains methods for manipulating attributes that "
                + "control the way in which the text in the document is displayed. "
                + "The Swing text package contains a concrete implementation of "
                + "StyledDocument called DefaultStyledDocument that is used as the "
                + "default model for JTextPane and is also the base class from which "
                + "more specific models, such as the HTMLDocument class that handles "
                + "input in HTML format, can be created. In order to make use of "
                + "DefaultStyledDocument and JTextPane, you need to understand how "
                + "Swing represents and uses attributes.";

        public SectionCollectionCreator(SectionCollection collection) {
            this.collection = collection;

            String title = "Title ";

            for (int i = 1; i <= 3; i++) {
                SectionText sectionText = new SectionText(title + i, 
                        new StringReader(text));
                collection.add(sectionText);
            }
        }   
    }

}

Solution

  • You might also want to consider putting your components inside a FillPane, which causes them to be sized to fill the available area. This seems to be the Pivot way of doing things.