Skip to content

Conditional slots are not rendered correctly in IE11/Edge #2257

@cwaespi

Description

@cwaespi

Stencil version:

 @stencil/core@1.9.0

I'm submitting a:

[x] bug report
[ ] feature request
[ ] support request => Please do not submit support requests here, use one of these channels: https://stencil-worldwide.herokuapp.com/ or https://forum.ionicframework.com/

Current behavior:
When a slot within a component is dynamically added or removed, stencil (es5 builds only) does not render correctly.

Expected behavior:
If a slot within a component is removed dynamically, the corresponding content should also be removed. If the slot is added again, the content should also reappear.

Steps to reproduce:


Issue A (toggle slot directly):

Component

@Component({
  tag: 'dynamic-slot',
  styles: `
    div {
      display: block;
      width: 200px;
      height: 100px;
      background-color: lightcoral;
    }
  `,
  shadow: true
})
export class DynamicSlot implements ComponentInterface {
  @State() toggle: boolean;

  @Listen('click')
  clickHandler() {
    this.toggle = !this.toggle;
  }

  render() {
    return (
      <div>
        <p>{this.toggle ? 'Toggle true' : 'Toggle false'}</p>
        {this.toggle ? <slot /> : null}
      </div>
    );
  }
}

HTML

<dynamic-slot>
  <a>Should be rendered if toggle is true</a>
</dynamic-slot>

Before click
The text should be hidden because toggle is false.
IssueA-before-click

After first click
Correct rendering after the first click.
IssueA-after-first-click

After second click
The text should be removed because toggle is false.
IssueA-after-second-click

After nth click
The text does not toggle. Always same result.
IssueA-after-second-click


Issue B (toggle slot with div wrapper):

Component

import {
  Component,
  ComponentInterface,
  h,
  State,
  Listen,
} from '@stencil/core';

@Component({
  tag: 'dynamic-slot',
  styles: `
    div {
      display: block;
      width: 200px;
      height: 100px;
      background-color: lightcoral;
    }
  `,
  shadow: true
})
export class DynamicSlot implements ComponentInterface {
  @State() toggle: boolean;

  @Listen('click')
  clickHandler() {
    this.toggle = !this.toggle;
  }

  render() {
    return (
      <div>
        <p>{this.toggle ? 'Toggle true' : 'Toggle false'}</p>
        {this.toggle ? <div><slot /></div> : null}
      </div>
    );
  }
}

HTML

<dynamic-slot>
  <a>Should be rendered if toggle is true</a>
</dynamic-slot>

Before click
The text should be hidden because toggle is false.
IssueB-before-click

After first click
Correct rendering after the first click.
IssueB-after-first-click

After second click
Correct rendering after the second click (text was removed).
IssueB-after-second-click

After nth click
The text should be displayed because toggle is true again.
IssueB-after-third-click


Related code:

// insert any relevant code here

Other information:
In the pre-release @stencil/core 1.9.0-14 it still worked.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions