By default, Vaadin columns have a fixed width. This is pretty wide, and is OK in a Form-style layout.
I want to render fields horizontally in a wrapping div, and if the fields are wider then they have to be I’m wasting space.
I want the field to be just wide enough to fit the (translated) label + a width for the input that we calculate in various ways + vaadin chrome
In our Vaadin 8 app we have a table with the pixel width of all 256 ISO8859-1 characters of our font, and we use that to calculate a pixel width of any string. It works resonably well, but it is janky.
We can do the same in Vaadin20+, but I wondered if there was a better way now.
Grid columns have col.setAutoWidth(true), which calculates width both from data and header. It is a shame there isn’t anything similar for input fields.
Is it possible to use some textField.getElement().executeJs(“…”) to set the pixel width to some expression that uses the actual font info in the browser?
Or, can it be styled with some fit-content?
Attached screendump from our Vaadin8 app shows an example. Note that the date fields are just wide enough to display “dd.mm.yyyy”, except when the label is wider
I found that stackoverflow page too. I had hoped someone else had already used it in a vaadin context
Using “ch” unit doesn’t really work. If I do:
textField.setWidth(textField.getLabel().length(), Unit.CH)
this label
This is a really long label
would make the field as wide as this:
000000000000000000000000000
ch units should give you a pretty good approximation actually, as it’s based on the width of the 0 glyph, which in most fonts is very close to the average char width.
And I think ch units are the closest you can get to that with CSS, because the html element doesn’t let you do that min-content trick like you do with the label. So, for example, combining the above with
width: 30ch;
}```
*Should* give you a field that's *at least* 30ch wide, but possibly wider if the label is wider.
It is the label width that is the biggest issue. Testing out your suggestion on DatePicker gives exactly what I want:
`–vaadin-field-default-width: min-content;
Have now tried with css variable as well. Didn’t work out of the box, but when I moved the unit to the variable it worked like a charm:
`textField.getStyle().set(“–length”, “30ch”);
vaadin-text-field > input {
width: var(–length);
}`
That actually gives me more freedom on the server-side, so I think I prefer that anyway.
Yes, the padding-right on the label container is to make room for the required indicator.
And the label selector is ::part() because it’s inside the component’s shadow DOM, whereas the <input> is > input because it’s not inside the shadow DOM (for accessibility reasons, primarily).
Glad to hear it worked! I’m thinking that we might make this an official feature, one way or another, as it’s a fairly common desire to get this behavior.
Please let me know if you encounter some cases where it doesn’t work, or causes issues!