Search code examples
javascriptweb-componentstenciljs

How to vertically align a Stencil component with an HTML element using flex?


return (
       <a href="javascript:;" class={`dropdown-item ${this.checkboxColor}`}>
          {this.checkable && <input type="checkbox" id="checkbox4" class={`form-check-input`} />}
          <ifx-icon icon={this.icon}></ifx-icon>
          <label htmlFor="checkbox4" class="form-check-label"><slot /></label>
        </a>
    )

I want to vertically-align ifx-icon with the <label> using flex and align-items: center. The container dropdown-item already has flex applied, but it's not being applied to the ifx-icon's element, because as you know, styles are applied to the component wrapper itself, not the element that's inside.

What do you suggest I do in this case?


Solution

  • As you stated:

    styles are applied to the component wrapper itself, not the element that's inside

    which means that you need to make sure the element or elements that are inside the host element are properly laid out and respond to any style applied to the host element that is desired.

    Assuming the render function you shared is for the dropdown-item component, applying style to that component would only affect the <a> element, not its contents, as you already know. You need to add style to your dropdown-item component so that the <a> lays out the icon and label property.

    That would probably look something like:

    dropdown-item.scss

    :host {
        a.dropdown-item {
            display: inline-flex;
            align-items: center;
        }
    }
    

    You might also be able to use CSS parts to apply the style from outside the component:

    return (
        <a part="container" ...>
            {this.checkable && <input type="checkbox" id="checkbox4" class={`form-check-input`} />}
            <ifx-icon icon={this.icon}></ifx-icon>
            <label htmlFor="checkbox4" class="form-check-label"><slot /></label>
        </a>
    )
    
    dropdown-item::part(container) {
        display: inline-flex;
        align-items: center;
    }