Eclipse SWT ScrolledComposite refuses to scroll - java

I'm developing a plugin for eclipse and I'm struggling to use ScrolledComposite as well as making it take up the remaining space.
The parent layout is a 2-column Grid:
#Override
public void createPartControl(Composite parent) {
parent.setLayout(new GridLayout(2, false));
// other views etc
}
The ScrolledComposite is created like so (slightly abbreviated):
private void fillScroll() {
if (scroll != null) {
scroll.dispose();
}
scroll = new ScrolledComposite(parent, SWT.V_SCROLL | SWT.H_SCROLL | SWT.BORDER);
GridData gd = new GridData();
gd.horizontalSpan = 2;
scroll.setLayoutData(gd);
Composite innerContainer = new Composite(scroll, 0);
innerContainer.setLayout(new GridLayout(1, false));
// for loop that adds widgets to innerContainer
scroll.setExpandHorizontal(true);
scroll.setExpandVertical(true);
scroll.setContent(innerContainer);
scroll.setSize(innerContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT));
parent.layout(true);
}
The list of questions are the widgets added in the for loop and are contained by innerContainer.
Expectation: Since innerContainer is too large to fit in the parent, there should be scroll bars.
What actually happens: There are no scroll bars.
How do I fix this problem?

The GridData on the ScrolledComposite needs to have grabExcessVerticalSpace set to true. I suggest you to use the extended constructor in order to clearly define how it should be displayed, for example:
GridData gd = new GridData(SWT.FILL, SWT.FILL, true, true, 2, 1);
Option A: change scroll.setSize to scroll.setMinSize:
scroll.setMinSize(innerContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT));
or, Option B: remove scroll.setExpandHorizontal and scroll.setExpandVertical and change scroll.setSize to innerContainer.setSize:
innerContainer.setSize(innerContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT));

Related

How can I show Scroll on my UI, with JAVA, SWT?

I'm trying to put a ScrolledComposite on my UI with SWT.
but now it only shows blank area or something wrong.
The area to show ScrolledComposite is blank without the code,
"optionCompositeAtLeft.setSize(optionCompositeAtLeft.computeSize(SWT.DEFAULT, SWT.DEFAULT)); "
This is the pic of screenshot.
The optionTab should have the buttons with Scroll....
and with the code, it shows scroll, but too long height and narrow width.
Somehow, the upper is gone, but come back when I extend the size of window with scroll disappearing.
I set the color of background red to make it easier to see for you.
Can anyone help me make "optionCompositeAtLeft" filled in ScrolledComposite?
I want the left area of Option tab to be filled with a red background from "optionCompositeAtLef".
Below is my code.
private BomCloneDialog dialog = null;
private TabFolder tabFolder = null;
private TabItem tabOption = null;
public CreateOptionTab(TabFolder tabFolder, TabItem tabOption) {
this.tabFolder = tabFolder;
this.tabOption = tabOption;
}
public void createOptionTabUI() {
GridData gdWithFillBoth = new GridData(GridData.FILL_BOTH);
Composite optionComposite = new Composite(tabFolder, SWT.NONE);
optionComposite.setLayout(new GridLayout(2, true));
tabOption.setControl(optionComposite);
ScrolledComposite scrolledCompositeForOption = new ScrolledComposite(optionComposite,SWT.V_SCROLL | SWT.BORDER);
scrolledCompositeForOption.setLayoutData(gdWithFillBoth);
Composite optionCompositeAtLeft = new Composite(scrolledCompositeForOption, SWT.BORDER);
scrolledCompositeForOption.setContent(optionCompositeAtLeft);
optionCompositeAtLeft.setLayout(new GridLayout(1, true));
optionCompositeAtLeft.setLayoutData(gdWithFillBoth);
optionCompositeAtLeft.setBackground(new Color(Display.getCurrent(), 255,0,0));
Button b [] = new Button[30];
for(int a=0; a<30; a++){
b[a] = new Button(optionCompositeAtLeft, SWT.PUSH);
b[a].setText("button"+a);
}
**optionCompositeAtLeft.setSize(optionCompositeAtLeft.computeSize(SWT.DEFAULT, SWT.DEFAULT));**
Composite optionButtonComposite = new Composite(optionComposite, SWT.BORDER);
optionButtonComposite.setLayout(new GridLayout(1, true));
optionButtonComposite.setLayoutData(gdWithFillBoth);
Button optionSaveButton = new Button(optionButtonComposite, SWT.NONE);
optionSaveButton.setLayoutData(gdWithFillBoth);
optionSaveButton.setText("Save");
Button optionAddButton = new Button(optionButtonComposite, SWT.NONE);
optionAddButton.setLayoutData(gdWithFillBoth);
optionAddButton.setText("Add");
}
You need to configure ScrolledComposite to resize the content:
scrolledCompositeForOption.setExpandHorizontal(true);
scrolledCompositeForOption.setExpandVertical(true);

ScrolledComposite children not populating content

I have a ScrolledComposite widget that I'm initializing inside a selection listener (in turn attached to another composite). This ScrolledComposite contains in turn another Composite, which in turn holds a Button and a Label. While the internal composite appears, none of its children widgets do. I've used ScrolledComposite plenty of times before, and everything looks right to my eye. Can any of you see anything wrong? Note, the ScrolledComposite is a class variable. Also note that this problem is occurring regardless of if I ever dispose of the composite and its contents in the else condition.
final Button showConsole = new Button(topLeft, SWT.CHECK);
showConsole.setText("Show Debug Console");
showConsole.setFont(new Font(domains.getDisplay(), "Segoe UI", 9, SWT.ITALIC));
showConsole.setSelection(false);
showConsole.addSelectionListener(new SelectionListener() {
#Override
public void widgetSelected(SelectionEvent e) {
//The total widget group is only supposed to appear when the button is selected
if (showConsole.getSelection()) {
scrolledConsoleComp = new ScrolledComposite(leftComposite,
SWT.H_SCROLL | SWT.V_SCROLL | SWT.BORDER);
Composite consoleComposite = new ScrolledComposite(scrolledConsoleComp, SWT.NONE | SWT.BORDER);
consoleComposite.setLayout(new GridLayout());
consoleComposite.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
consoleComposite.setVisible(true);
scrolledConsoleComp.setContent(consoleComposite);
scrolledConsoleComp.setExpandHorizontal(true);
scrolledConsoleComp.setExpandVertical(true);
scrolledConsoleComp.setLayout(new GridLayout());
scrolledConsoleComp.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
Button clear = new Button(consoleComposite, SWT.PUSH);
clear.setText("Clear Console");
final Label consoleText = new Label(consoleComposite, SWT.WRAP);
consoleText.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false));
consoleText.setText("Messages: \n" + consoleData);
clear.addSelectionListener(new SelectionListener() {
#Override
public void widgetSelected(SelectionEvent e) {
consoleData = "";
consoleText.setText("Messages: \n" + consoleData);
}
#Override
public void widgetDefaultSelected(SelectionEvent e) {
}
});
scrolledConsoleComp.setMinSize(leftComposite.computeSize(SWT.DEFAULT, SWT.DEFAULT));
leftComposite.layout(true);
} else {
scrolledConsoleComp.setVisible(false);
scrolledConsoleComp.dispose();
leftComposite.layout(true);
}
}
I appreciate any insight. Let me know if anything in this question is unclear. Thank you!
You're creating your Button and your Label inside a ScrolledComposite. They won't be shown because setContent() is not called.
Usually a ScrolledComposite contains a Composite that holds all the other Widgets.
Your consoleComposite should become a Composite.
No need for a call to setVisible()

Resize SWT Table

I have a wizard with table and button components. When I click to the add button I choose from dialog window what items should be added to the table. I confirm items, and then this ones appears in the table with scrollbar. But if I resize the wizard, the table size is changed. How to fix it?
Table before resize:
Table after wizard resize
Composite compositeArea = new Composite(parent, SWT.NONE);
GridLayout layout = new GridLayout();
layout.numColumns = 3;
compositeArea.setLayout(layout);
Table table = new Table(compositeArea, SWT.BORDER | SWT.V_SCROLL);
new TableColumn(someList, SWT.NULL);
table.setLayoutData(new GridData(HORIZONTAL_ALIGN_FILL | GRAB_HORIZONTAL));
** Please note that the use of HORIZONTAL_ALIGN_FILL and GRAB_HORIZONTAL is discouraged. Instead, you should be using the public GridData(int, int, boolean, boolean) constructor. **
To slighly simplify your code snippet (only one column on the composite, and only one default table column - see full code below):
// ...
final Composite compositeArea = new Composite(parent, SWT.NONE);
compositeArea.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
compositeArea.setLayout(new GridLayout());
final Table table = new Table(compositeArea, SWT.BORDER | SWT.V_SCROLL);
table.setLayoutData(new GridData(GridData.HORIZONTAL_ALIGN_FILL | GridData.GRAB_HORIZONTAL));
// ...
...and we see that the Table isn't fitting in the available space or showing the scrollbar as expected, and the same occurs when the Shell is resized.
In answer to your question, this is because the layout data of the Table doesn't know how to layout vertically - you've only specified two horizontal style attributes.
If we instead use the suggested constructor:
table.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
...the Table takes the available space correct, shows the scrollbar, and updates correctly when the Shell is resized. Using the layout data, we've told the Table to fill the available horizontal space, and the Table will display the scrollbar if necessary.
Full example:
public class TableResizeTest {
private final Display display;
private final Shell shell;
public TableResizeTest() {
display = new Display();
shell = new Shell(display);
shell.setLayout(new FillLayout());
shell.setMaximized(true);
final Composite parent = new Composite(shell, SWT.NONE);
parent.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
parent.setLayout(new GridLayout());
// -- snippet --
final Composite compositeArea = new Composite(parent, SWT.NONE);
compositeArea.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
compositeArea.setLayout(new GridLayout());
final Table table = new Table(compositeArea, SWT.BORDER | SWT.V_SCROLL);
// table.setLayoutData(new GridData(GridData.HORIZONTAL_ALIGN_FILL | GridData.GRAB_HORIZONTAL));
table.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
// -------------
for (int i = 0; i < 20; ++i) {
new TableItem(table, SWT.NONE).setText(String.valueOf(i));
}
}
public void run() {
shell.setSize(300, 300);
shell.open();
while (!shell.isDisposed()) {
if (display.readAndDispatch()) {
display.sleep();
}
}
display.dispose();
}
public static void main(final String... args) {
new TableResizeTest().run();
}
}

SWT GridLayout and GridData alignment of composite blocks

I understand that I have layout but I have problem with setting achivementsChild next to each other. I want to make some alignment or something similar. Now they are standing one below other and I want to set one next to the other.
TabItem tbtmStudent = new TabItem(tabFolder_1, SWT.NONE);
tbtmStudent.setText("Student");
ScrolledComposite scrolledComposite_1 = new ScrolledComposite(tabFolder_1, SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL);
scrolledComposite_1.addMouseWheelListener(new MouseWheelListener() {
public void mouseScrolled(MouseEvent e) {
scrolledComposite.setFocus();
}
});
tbtmStudent.setControl(scrolledComposite_1);
scrolledComposite_1.setExpandHorizontal(true);
scrolledComposite_1.setExpandVertical(true);
List<STUDENT> allSTUDENTNodes = currentData.getStudentNodes();
Composite studentChild = new Composite(scrolledComposite_1, SWT.NONE);
studentChild.setLayout(new GridLayout());
for(STUDENT studentNode: allSTUDENTNodes){
new STUDENTNode(studentChild, SWT.NONE, studentNode);
Composite achivementsChild = new Composite(scrolledComposite_1, SWT.DEFAULT);
achivementsChild.setLayout(new GridLayout());
for(Achivements achivementsNode: studentNode.getAchivements()){
new AchivementsNode(mscbcChild, SWT.NONE, achivementsNode);
}
}
scrolledComposite_1.setContent(studentChild);
scrolledComposite_1.setMinSize(studentChild.computeSize(SWT.DEFAULT, SWT.DEFAULT));
You can specify how many columns you want when you create the GridLayout:
new GridLayout(numberOfColumns, columnsEqual);
numberofColumns is the number of columns you want.
If columnsEqual is true all columns will have the same width, if it is false they will have their preferred size.

SWT set max height of component inside ScrolledComposite

I cannot figure out how to correctly set the height of my row composite. I would like the following code snippet to display only one row of data. Any additional rows would be seen by using the scrollbar. I have tried using rowContainer.setSize() but to no avail. Any help would be appreciated.
Please note that the scrolled composite is not directly linked to the rowContainer composite and contains other composites as well.
private void doStuff(final Composite parentContainer) {
final ScrolledComposite scrolledComposite = new ScrolledComposite(
parentContainer, SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL);
scrolledComposite.setExpandHorizontal(true);
scrolledComposite.setExpandVertical(true);
scrolledComposite.setLayoutData(new GridData(SWT.FILL, SWT.FILL,
true, true));
final Composite borderComposite = new Composite(scrolledComposite,
SWT.BORDER);
borderComposite.setLayout(new GridLayout(1, false));
borderComposite.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true,
true));
scrolledComposite.setContent(borderComposite);
scrolledComposite.setSize(borderComposite.computeSize(SWT.DEFAULT,
SWT.DEFAULT));
// Create a container for a label and button
final Composite labelAndAddButtonContainer = new Composite(
borderComposite, SWT.NONE);
labelAndAddButtonContainer.setLayout(new GridLayout(2, false));
labelAndAddButtonContainer.setLayoutData(new GridData(SWT.LEFT,
SWT.TOP, false, false));
// Create a container to hold all dynamic rows
final Composite rowContainer = new Composite(borderComposite, SWT.NONE);
rowContainer.setLayout(new GridLayout(1, false));
rowContainer.setLayoutData(new GridData(SWT.FILL, SWT.NONE, true, false));
// Create at least one row.
final Collection<String> rowData = getRowData();
if (rowData.isEmpty()) {
createRow(scrolledComposite, rowContainer, "");
} else {
for (final String text : rowData) {
createRow(scrolledComposite, rowContainer, text);
}
// How do I adjust for the height so that only 1 row shows,
// and scrollbars appear if there is more than one row?
}
// Create a button
final Button addButton = new Button(labelAndAddButtonContainer,
SWT.PUSH);
addButton.setImage(someImage);
final Label label = new Label(labelAndAddButtonContainer, SWT.NONE);
label.setText("SOME_LABEL");
}

Categories