Skip to content
This repository has been archived by the owner on Jun 29, 2023. It is now read-only.

Commit

Permalink
fix(action): Support slotting icon after initialization (#913)
Browse files Browse the repository at this point in the history
* support adding icon slot in action after initialization

* add test

* decrease delay
  • Loading branch information
driskull committed Apr 2, 2020
1 parent 77ff30c commit faddbc3
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 12 deletions.
17 changes: 17 additions & 0 deletions src/components/calcite-action/calcite-action.e2e.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,23 @@ describe("calcite-action", () => {
expect(iconContainer).not.toBeNull();
});

it("should have icon container with calcite-icon: after delay", async () => {
const page = await newE2EPage();
await page.setContent(`<calcite-action></calcite-action>`);

const action = await page.find("calcite-action");

const delay = 1;
await new Promise((resolve) => setTimeout(resolve, delay));

action.innerHTML = `<calcite-icon icon="hamburger" scale="s"></calcite-icon>`;

await page.waitForChanges();

const iconContainer = await page.find(`calcite-action >>> .${CSS.iconContainer}`);
expect(iconContainer).not.toBeNull();
});

it("should have icon container with svg", async () => {
const page = await newE2EPage();
await page.setContent(`<calcite-action><svg></svg></calcite-action>`);
Expand Down
40 changes: 36 additions & 4 deletions src/components/calcite-action/calcite-action.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { CSS } from "./resources";
import { CSS_UTILITY } from "../utils/resources";

import { getElementDir } from "../utils/dom";
import { VNode } from "@stencil/core/internal";
import { VNode, State } from "@stencil/core/internal";

/**
* @slot - A slot for adding a `calcite-icon`.
Expand Down Expand Up @@ -91,7 +91,29 @@ export class CalciteAction {

@Element() el: HTMLCalciteActionElement;

private buttonEl: HTMLButtonElement;
@State() hasChildren = false;

buttonEl: HTMLButtonElement;

observer = new MutationObserver(() => this.setHasChildren());

// --------------------------------------------------------------------------
//
// Lifecycle
//
// --------------------------------------------------------------------------

componentWillLoad(): void {
this.setHasChildren();
}

componentDidLoad(): void {
this.observer.observe(this.el, { childList: true, subtree: true });
}

componentDidUnload(): void {
this.observer.disconnect();
}

// --------------------------------------------------------------------------
//
Expand All @@ -104,6 +126,16 @@ export class CalciteAction {
this.buttonEl.focus();
}

// --------------------------------------------------------------------------
//
// Private Methods
//
// --------------------------------------------------------------------------

setHasChildren = (): void => {
this.hasChildren = !!this.el.children?.length;
};

// --------------------------------------------------------------------------
//
// Render Methods
Expand All @@ -125,12 +157,12 @@ export class CalciteAction {
}

renderIconContainer(): VNode {
const { el, loading, icon, scale } = this;
const { loading, icon, scale, hasChildren } = this;
const iconScale = scale === "l" ? "m" : "s";
const calciteLoaderNode = loading ? <calcite-loader is-active inline /> : null;
const calciteIconNode = icon ? <calcite-icon icon={icon} scale={iconScale} /> : null;
const iconNode = calciteLoaderNode || calciteIconNode;
const hasIconToDisplay = iconNode || el.children?.length;
const hasIconToDisplay = iconNode || hasChildren;

const slotContainerNode = (
<div
Expand Down
15 changes: 7 additions & 8 deletions src/demos/action/add-action-icon-after-init.html
Original file line number Diff line number Diff line change
Expand Up @@ -18,19 +18,18 @@ <h1>calcite-action</h1>
<h2>LTR</h2>
<div class="action-container">
<h3>With text</h3>
<calcite-action id="slot-test" indicator active text="click-me" label="hello world" text-enabled
>
<calcite-action id="slot-test" indicator active text="click-me" label="hello world" text-enabled>
</calcite-action>

<script>
const slotTestNode = document.getElementById("slot-test");
setTimeout(function(){
const div = document.createElement("div");
div.innerHTML = `<calcite-icon scale="s" icon="configure-popup"></calcite-icon>`;
slotTestNode.appendChild(div);
}, 2000)
setTimeout(function () {
const icon = document.createElement("calcite-icon");
icon.icon = "configure-popup";
icon.scale = "s";
slotTestNode.appendChild(icon);
}, 2000);
</script>

</div>
</section>
</main>
Expand Down

0 comments on commit faddbc3

Please sign in to comment.