adidas / choicesjs-stencil

Select Web Component which wraps ChoicesJS library using StencilJS
MIT License
65 stars 10 forks source link

Is there a way to use choicesjs-stencil within Stencil web component ? #15

Closed sadamia closed 4 years ago

sadamia commented 4 years ago

Node/npm version(s): v13.11.0

Package(s) version(s): The app component is created with Stencil CLI, npm init stencil and has only two dependencies

    "choices.js": "^9.0.1",
    "choicesjs-stencil": "^1.5.1"

Description of the issue/feature: I'm trying to use choicesjs-stencil within StencilJS web component, when I initialize the component with option single, the dropdown doesn't show up, the problem is in click handler

var target = _ref10.target;
    var clickWasWithinContainer = this.containerOuter.element.contains(target);

https://github.com/jshjohnson/Choices/blob/master/src/scripts/choices.ts#L1735

The target variable is my-component instead of being div.choices__item element, as I understand it happens because, the original target is hidden as "internal implementation", and instead the event is re-targeted to the host element.

Some example to reproduce the issue: Here is the repo https://github.com/sadamia/choicesjs-stencil-example

Use cases:

git clone https://github.com/sadamia/choicesjs-stencil-example.git
cd choicesjs-stencil-example
npm install
npm run start

Inspect the component from dev tools, find the click handler attach breakpoint.

Screen
moelders commented 4 years ago

Hello @sadamia, Thank you for the explanation, we did not have that issue before. The ChoicesJS Web Component is just a wrapper for the real implementation of ChoicesJS, which you have linked. It is not managing any event by itself. So, it seems that the issue is on the core of ChoicesJS, have you tried to rework that snippet of code?

sadamia commented 4 years ago

Hello @moelders, Thank you for reaching out, I found this solution, you could open a dropdown by calling showDropdown() API method on the dropdown and adding it as a click handler on the stencil component.

export class MyComponent {
  private choicesRef;

  openDropDown() {
    this.choicesRef.showDropdown(false);
  }

  render() {
    return (
      <choicesjs-stencil
        placeholderValue="Select project"
        choices={projects}
        name="projects"
        type="single"
        searchFields={["label", "value"]}
        key={"label"}
        itemScope={true}
        searchEnabled={true}
        searchChoices={true}
        renderChoiceLimit={-1}
        searchFloor={1}
        position={"auto"}
        renderSelectedChoices={"auto"}
        silent={false}
        searchResultLimit={4}
        ref={(el) => this.choicesRef = el}
        onClick={() => this.openDropDown()}
      ></choicesjs-stencil>
    );
  }
}

Closing this issue.

moelders commented 4 years ago

Hello @sadamia, thank you for giving us the solution. Yes, the good part of the Web Component is that it provides all the available methods as its API. Have a good one!