setColumnWidth() doesn't seem to work - java

I'm developing a webapplication in the Vaadin framework.
I have a table with 14 columns. The last column holds three icons and a problem I'm having is that like half of the time the table is rendered the icon furthest to the right will be "cut in half" vertically. To avoid this problem I tried to set a fixed width to this column that I think would eradicate the problem, however, nothing happens..
I'm using the conventional approach:
simCardTable.setColumnWidth(actionColumn, 135);
However, no matter what value I set to be the column width the column stays the same... Does anyone know why this is? Is it because it's the last column to be added and therefore there's no space to spare..?
Btw, that is the only column I set a specific width to, all of the restoring columns have a the standard width specified by the width of the column header or the cell content.
Any help would be very appreciated!

As i understand from your question ("The last column holds three icons") you use ColumnGenerator to create this last column, with icons. If I right, it mean that you created some sort of custom layout with this icons inside, in this case for you should work this:
final ColumnGenerator generator = new ColumnGenerator() {
private static final long serialVersionUID = 1L;
#Override
public Component generateCell(Table source, final Object itemId, Object columnId) {
final HorizontalLayout layout = new HorizontalLayout();
layout.setSizeFull();
Embedded icon1 = new Embedded();
Embedded icon2 = new Embedded();
Embedded icon3 = new Embedded();
//Add some themeresource to embedded components
//Do some listners to this icons
layout.addComponent(icon1);
layout.addComponent(icon2);
layout.addComponent(icon3);
//Set column with
setColumnWidth(columnId, 100);
return layout;
}
};

Related

Overflowing layout with TableLayout

I need to show three things in a row in a sort of table. The first column should have a fixed width of say 15% of the screen. The third one should be right aligned and take its preferred width. The second one should take all the remaining space (I'll need to add some spacing, but that's another story).
This happens in start:
final Container list = new Container(BoxLayout.y());
list.setScrollableY(true);
final String[][] lines = {
{"19", "Some text", "123,00"},
{"20", "Some very very very very looong text", "1,00"},
};
for(final String[] line : lines) list.add(createContainer(line));
form.add(list);
The container is rather trivial:
private Container createContainer(String[] line) {
final TableLayout tableLayout = new TableLayout(1, 3);
tableLayout.setGrowHorizontally(true);
final Container result = new Container(tableLayout);
{
final Label l = new Label(line[0]);
l.getAllStyles().setFgColor(0x0000FF);
result.add(tableLayout.createConstraint().widthPercentage(15), l);
}
{
final Label l = new Label(emptyToSpace(line[1]));
l.getAllStyles().setFont(Font.createSystemFont(Font.FACE_SYSTEM, Font.STYLE_BOLD, Font.SIZE_MEDIUM));
result.add(tableLayout.createConstraint().widthPercentage(-2), l);
}
{
final Label l = new Label(line[2]);
l.getAllStyles().setFont(Font.createSystemFont(Font.FACE_SYSTEM, Font.STYLE_BOLD, Font.SIZE_LARGE));
l.getAllStyles().setFgColor(0x00FF00);
result.add(tableLayout.createConstraint().widthPercentage(-1).horizontalAlign(Component.RIGHT), l);
}
return result;
}
According to the javadoc, -1 means preferred size and -2 means "remaining space". It sort of works, but there seem to be a miscalculation.
The problem happens in the simulator, no matter what device I choose. I may be doing it all wrong, as I'm new to codenameone layouts.
The -2 flag is mostly optimized for the last column so this looks like a bug but might be hard to workaround. I don't see a need to use table layout here since you don't use one table which would provide alignment between the rows.
A simpler approach would be border layout e.g.:
Container c = BorderLayout.centerEastWest(new Label(emptyToSpace(line[1])),
rightText, leftText);
If you want the left column to align just use Component.setSameWidth() on the entire column.

Vaadin Grid how to wrap long text in columns

I have a Vaadin grid with 7 columns:
Grid grid = new Grid<>();
grid.setSizeFull();
grid.addColumn(User::getUserName).setCaption("Name").setExpandRatio(2);
grid.addColumn(User::getLastName).setCaption("Last Name").setExpandRatio(1);
grid.addColumn(User::getAge).setCaption("Age").setExpandRatio(2);
grid.addColumn(User::getWork).setCaption("Work").setExpandRatio(1);
grid.addColumn(User::getJobTitle).setCaption("Job Title").setExpandRatio(1);
grid.addColumn(User::getSalary).setCaption("Salary").setExpandRatio(1);
grid.addColumn(User::getOther).setCaption("Other").setExpandRatio(1);
What I need is to set columns width in a way - that all 7 will have be shown on a screen.
With my code now it works in a way that if text content of any column cell is very long - the last columns are not shown on the screen and screen must be scrolled horizontally.
I tried to use method setWidth() and as it takes value in pixels the grid view may differ on various browsers and screens.
What I need is to be sure that my grid looks the same way on different screens and with different cell values.
Recently I had the same situation, this was my solution:
Grid configuration
Grid<Item> gridItem = new Grid<>();
gridItem.setRowHeight(50.0);
Column configuration
gridItem.addComponentColumn(item -> {
Label label = new Label();
label.setValue(item.getText());
label.setWidthUndefined();
label.setStyleName(ValoTheme.LAYOUT_HORIZONTAL_WRAPPING);
return label;
})
.setCaption("Item")
.setWidth(380.0);
Result:

Cell width not respected when using colspan

I'm trying to set a cell width in my LibGDX's table and it's ignoring the value I pass. I suspect it is because it's under rows that are fill and has colspan but I can't explain exactly why It is happenning.
Here's a screen:
I would like the cell of my play button to be smaller in width, so I wrote that code:
setDebug(true, true); //just mentionning, this is in the constructor of a class that extends Table, to prevent having table creation code on my screen
setWidth(400f);
setHeight(80f);
padLeft(30f);
padRight(30f);
Image image = new Image(assets.getTexture("gfx/menu/level-online.png")); //TODO icon depends on state
image.setScaling(Scaling.fill);
Button playButton = new TextButton(level.getType() == LevelType.RACE ? "Play" : "Visit", skin);
Button editButton = new TextButton("Edit", skin);
add(level.getName()).bottom().left().colspan(2).expand();
add(image).width(30f).height(30f);
row();
add(level.getOwner()).top().left().colspan(3).expand();
row();
add(playButton).width(40f).center(); //HERE
add(editButton).left().colspan(2);
As you can see, the width of the cell of the play button is supposed to be 40 but it's way more. (For reference, the cloud is 30 x 30) How can I fix this ?
Fixed it using a table in my last row to separate elements. Thanks to Xoppa and Tenfour04 for their help.
add(level.getName()).bottom().left().colspan(2).expand();
add(image).width(30f).height(30f);
row();
add(level.getOwner()).top().left().colspan(3).expand();
row();
Table buttons = new Table();
buttons.add(playButton).padRight(10f);
buttons.add(editButton);
add(buttons).expand().colspan(3).left();

Libgdx Label multiline text height

i have done a small test on LibGdx, on Multi-line Label, it seems that i cant get the wrapped line's height. Following is the code. Theoretically, height for aLebel should be > bLabel. But the result appear the same.
code:
aLabel.setText("this is a super long long long text that need wrapping."); // line wrapped into 3 lines
aLabel.setWrap(true);
aLabel.setWidth(470);
doLog("aLabel.getHeight(): " + aLabel.getHeight());
bLabel.setText("this is short."); // unwrapped line
bLabel.setWrap(true);
bLabel.setWidth(470);
doLog("bLabel.getHeight(): " + bLabel.getHeight());
result:
aLabel.getHeight(): 45.0
bLabel.getHeight(): 45.0
Do anyone have any idea how to get the actual multi-line height in LibGdx? Thanks in advance.
I had this issue for years and accidentally solved it by setting the width and packing the label twice. Note that multiline labels were never intended to figure out their own width, so you have to set them externally, preferably from it's parent.
public Label createLabel() {
// Create label and set wrap
Label label = new Label("Some long string here...", skin);
label.setWrap(true);
// Pack label
label.pack(); // This might not be necessary, unless you're changing other attributes such as font scale.
// Manual sizing
label.setWidth(textWidth); // Set the width directly
label.pack(); // Label calculates it's height here, but resets width to 0 (bug?)
label.setWidth(textWidth); // Set width again
return label;
}
LibGDX version used: 1.6.4
Pack sizes the widget to its pref size, nothing more. Pref width of a label with wrapping is 0.
Label label = new Label(...);
label.setWrap(true);
label.setWidth(123);
label.setHeight(label.getPrefHeight());
I had the same issue and it seems there doesn't exist a method in Label class to solve this. Also, I agree with you, the getHeight() method should return the real height of the Actor, so I don't know if that's a bug or there is a reasoning behind that behaviour.
Anyways, how I solved the issue is by using BitmapFont's getWrappedBounds method. It's not short, but for your example it would be the following:
doLog("aLabel.getHeight(): " + aLabel.getStyle().font.getWrappedBounds(aLabel.getText(), aLabel.getWidth()).height);
This could be done by adding a restriction to the cell that contains the Label in the Table:
Label label = new Label("Example", new Label.LabelStyle(font, Color.WHITE));
label.setWrap(true);
Table table = new Table();
table.add(label).width(WITH);
For more information about how to use Table go to: https://github.com/libgdx/libgdx/wiki/Table

Java Swing; Problems with Horizontal Scroll for a JTable embedded in a JScrolledPane

I followed some tips in this guide: JTable with horizontal scrollbar but still having problems.
I have two column headers: Name and Description (for our purposes in this ex.)
I want to be able to scroll horizontally whenever an entry is added (ie: Name/Description is just 1 line). However, Swing doesn't seem to default to that behavior!
I have a JTable embedded in a ScrollPane. JScrollPane has the following parameters: JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED and JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED
If I disable with: myTable.AutoResizeMode(AUTO_RESIZE_OFF) the column headers don't fill up the whole table (maybe just 1/2 of the table). I have to manually resize the "Description" Column to see the whole thing.
How can I have autoresizing, but the horizontal scrolling still works?
You can extend JTable as follows:
public class JHorizontalFriendlyTable extends JTable {
#Override
public Dimension getPreferredSize() {
if (getParent () instanceof JViewport) {
if (
((JViewport) getParent()).getWidth() > super.getPreferredSize().width)
) {
return getMinimumSize();
}
}
return super.getPreferredSize();
}
#Override
public boolean getScrollableTracksViewportWidth () {
if (autoResizeMode != AUTO_RESIZE_OFF) {
if (getParent() instanceof JViewport) {
return (((JViewport) getParent()).getWidth() > getPreferredSize().width);
}
return true;
}
return false;
}
}
sample usage:
jScrollPane1 = new JScrollPane();
TableModel jTable1Model = new DefaultTableModel(...);
JTable jTable1 = new JHorizontalFriendlyTable();
jScrollPane1.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_ALWAYS);
jScrollPane1.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
jScrollPane1.setViewPortView(jTable1);
jTable1.setModel(jTable1Model);
jTable1.setPreferredSize(new java.awt.Dimension(1051,518));
jTable1.setPreferredScrollableViewPortSize(new java.awt.Dimension(1000,528));
jTable1.getSize(new java.awt.Dimension(1051, 528));
if (jTable1.getPreferredScrollableViewPortSize().getWidth() >
((JViewPort) jTable1.getParent()).getPreferredSize().getWidth())
{
jTable1.setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
jTable1.doLayout();
}
jTable1.setDragEnabled(false);
jTable1.setColumnSelectionAllowed(false);
jTable1.getTableHeader().setReorderingAllowed(false);
Auto resize means automatically resizing to avoid scrolling.
So the answer is no with standard JTable.
Check out JXTable and see if it does what you want (I haven't used it myself).
One approach might be to use setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS) when you create the table and then use setPreferredScrollableViewportSize() to specify your desired size. After you pack() the window, use setAutoResizeMode(JTable.AUTO_RESIZE_OFF) to allow horizontal scrolling.
If I disable with:
myTable.AutoResizeMode(AUTO_RESIZE_OFF)
the column headers don't fill up the
whole table (maybe just 1/2 of the
table).
By default each column is only 75 pixels wide. You can change the width of the description column to be whatever you want. Read the JTable API and you will find a link to the Swing tutorial on "How to Use Tables" which explains how to do this.
However, even using this approach the column size will not change if the user resizes the frame. It you want to handle this situation then you need to add a ComponentListener to the table (or maybe the scroll pane). Then whenever the componentResized() method is fired you can total the widths of the two columns and then adjust the width of the description column as required to make sure the column total width is not less than the width of the table.
I have to manually resize the
"Description" Column to see the whole
thing.
If you know that your description column will always be large enough to fill the viewport of the scrollpane then you can use the Table Column Adjuster to automatically calculate the maximum width of the description column

Categories

Resources