How to override a TextField's label's padding?

I need to compress the display of one of my forms somewhat to fit more data onto the screen.
For this I would like to reduce the space between a text-field’s label and its content field from 7px (which seems to be the default) to - say - 2px.

Trying to visualize this:

Class com.vaadin.flow.component.textfield.TextField

Current layout:

Label:
      > this is the space I want to reduce
+-----------------------------------+
| Text Input Area                   |
+-----------------------------------+

Desired layout: The Label should be closer to the input area:

Label:
+-----------------------------------+
| Text Input Area                   |
+-----------------------------------+

The gap between the label and the input field - as I found out - is controlled by the label’s bottom-margin (which is 7px high).
But no matter what I try in my style sheet - I can’t adjust that value! :frowning:

The labels are all defined as
<label id="vaadin-text-field-label-##" ...>
(## meaning some number). So I first tried to select them using a selector label[id^="vaadin-text-field-label"] , i.e. select all labels with ids beginning with “vaadin-text-field-label” but that did not work. It had no effect whatsoever! And not even selecting ALL labels and setting their bottom-padding to 2px like so:

label {
	padding-bottom: 2px;
}

changed anything. If I “inspect” the widget in the browser’s development tools the label has again a bottom margin of 7px.
So there seems to be some other mechanism that adjusts that padding which by-passes the style sheet.

How/where can I control that gap between label and input area?

This seems to work for me:

@CssImport(value = "./styles/vaadin-text-field-styles.css", themeFor = "vaadin-text-field")
public class MainView extends VerticalLayout {

    public MainView() {
        TextField filenameTextField = new TextField("Yes padding");
        add(filenameTextField);

        TextField smallPadding = new TextField("Only little padding");
        smallPadding.setThemeName("label-padding");
        add(smallPadding);
		// ...
    }		
		

In /frontend/styles/vaadin-text-field-styles.css:

:host([theme~="label-padding"]
) [part="label"]
 {
    padding-bottom: 2px;
}

Maybe look at the docs on theming here: https://vaadin.com/docs/v14/themes/style-scopes.html if you’re not familiar with Style Scopes.

Thanks for the pointer! The described approach worked perfectly for TextFields and TextAreas.
However, Combobox has no “setThemaName(…)”-method. I would need to adjust their label-margin/padding as well.
How can one mark those so that a “theme~=…”-clause can refer to them? Or what other approach can one use for these?

You can apply a theme attribute through the Element API as well:

smallPaddingComboBox.getElement().getThemeList().add("label-padding");
// or: 
smallPaddingComboBox.getElement().setAttribute("theme", "label-padding");

These both will work if you have the same css file and @CssImport as above, because

  1. the padding styles are applied to the vaadin-text-field inside the ComboBox, not the vaadin-combo-box root element.
  2. in Vaadin components, a theme attribute will be propagated to child components