svelte-multiselect 8.2.2 โ†’ 8.2.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -14,6 +14,7 @@ export let defaultDisabledTitle = `This option is disabled`;
14
14
  export let disabled = false;
15
15
  export let disabledInputTitle = `This input is disabled`;
16
16
  // case-insensitive equality comparison after string coercion (looking only at the `label` key of object options)
17
+ // prettier-ignore
17
18
  export let duplicateFunc = (op1, op2) => `${get_label(op1)}`.toLowerCase() === `${get_label(op2)}`.toLowerCase();
18
19
  export let duplicateOptionMsg = `This option is already selected`;
19
20
  export let duplicates = false; // whether to allow duplicate options
@@ -53,7 +54,7 @@ export let required = false;
53
54
  export let resetFilterOnAdd = true;
54
55
  export let searchText = ``;
55
56
  export let selected = options
56
- ?.filter((op) => op?.preselected)
57
+ ?.filter((op) => op instanceof Object && op?.preselected)
57
58
  .slice(0, maxSelect ?? undefined) ?? [];
58
59
  export let sortSelected = false;
59
60
  export let selectedOptionsDraggable = !sortSelected;
@@ -123,7 +124,7 @@ function add(label, event) {
123
124
  // a new option from the user-entered text
124
125
  if (typeof options[0] === `object`) {
125
126
  // if 1st option is an object, we create new option as object to keep type homogeneity
126
- option = { label: searchText, value: searchText };
127
+ option = { label: searchText };
127
128
  }
128
129
  else {
129
130
  if ([`number`, `undefined`].includes(typeof options[0]) &&
@@ -147,7 +148,7 @@ function add(label, event) {
147
148
  return;
148
149
  }
149
150
  if (maxSelect === 1) {
150
- // for maxselect = 1 we always replace current option with new one
151
+ // for maxSelect = 1 we always replace current option with new one
151
152
  selected = [option];
152
153
  }
153
154
  else {
@@ -183,7 +184,7 @@ function remove(label) {
183
184
  selected = selected; // Svelte rerender after in-place splice
184
185
  const option = options.find((option) => get_label(option) === label) ??
185
186
  // if option with label could not be found but allowUserOptions is truthy,
186
- // assume it was created by user and create correspondidng option object
187
+ // assume it was created by user and create corresponding option object
187
188
  // on the fly for use as event payload
188
189
  (allowUserOptions && { label, value: label });
189
190
  if (!option) {
@@ -212,7 +213,7 @@ function close_dropdown(event) {
212
213
  }
213
214
  // handle all keyboard events this component receives
214
215
  async function handle_keydown(event) {
215
- // on escape or tab out of input: dismiss options dropdown and reset search text
216
+ // on escape or tab out of input: close options dropdown and reset search text
216
217
  if (event.key === `Escape` || event.key === `Tab`) {
217
218
  close_dropdown(event);
218
219
  searchText = ``;
@@ -375,9 +376,10 @@ const dragstart = (idx) => (event) => {
375
376
  on:dragstart={dragstart(idx)}
376
377
  on:drop|preventDefault={drop(idx)}
377
378
  on:dragenter={() => (drag_idx = idx)}
379
+ on:dragover|preventDefault
378
380
  class:active={drag_idx === idx}
379
- ondragover="return false"
380
381
  >
382
+ <!-- on:dragover|preventDefault needed for the drop to succeed https://stackoverflow.com/a/31085796 -->
381
383
  <slot name="selected" {option} {idx}>
382
384
  {#if parseLabelsAsHtml}
383
385
  {@html get_label(option)}
@@ -399,36 +401,39 @@ const dragstart = (idx) => (event) => {
399
401
  {/if}
400
402
  </li>
401
403
  {/each}
404
+ <li style="display: contents;">
405
+ <input
406
+ class={inputClass}
407
+ bind:this={input}
408
+ {autocomplete}
409
+ bind:value={searchText}
410
+ on:mouseup|self|stopPropagation={open_dropdown}
411
+ on:keydown|stopPropagation={handle_keydown}
412
+ on:focus
413
+ on:focus={open_dropdown}
414
+ {id}
415
+ {disabled}
416
+ {inputmode}
417
+ {pattern}
418
+ placeholder={selected.length == 0 ? placeholder : null}
419
+ aria-invalid={invalid ? `true` : null}
420
+ ondrop="return false"
421
+ on:blur
422
+ on:change
423
+ on:click
424
+ on:keydown
425
+ on:keyup
426
+ on:mousedown
427
+ on:mouseenter
428
+ on:mouseleave
429
+ on:touchcancel
430
+ on:touchend
431
+ on:touchmove
432
+ on:touchstart
433
+ />
434
+ <!-- the above on:* lines forward potentially useful DOM events -->
435
+ </li>
402
436
  </ul>
403
- <input
404
- class={inputClass}
405
- bind:this={input}
406
- {autocomplete}
407
- bind:value={searchText}
408
- on:mouseup|self|stopPropagation={open_dropdown}
409
- on:keydown|stopPropagation={handle_keydown}
410
- on:focus
411
- on:focus={open_dropdown}
412
- {id}
413
- {disabled}
414
- {inputmode}
415
- {pattern}
416
- placeholder={selected.length == 0 ? placeholder : null}
417
- aria-invalid={invalid ? `true` : null}
418
- on:blur
419
- on:change
420
- on:click
421
- on:keydown
422
- on:keyup
423
- on:mousedown
424
- on:mouseenter
425
- on:mouseleave
426
- on:touchcancel
427
- on:touchend
428
- on:touchmove
429
- on:touchstart
430
- />
431
- <!-- the above on:* lines forward potentially useful DOM events -->
432
437
  {#if loading}
433
438
  <slot name="spinner">
434
439
  <CircleSpinner />
@@ -538,8 +543,8 @@ const dragstart = (idx) => (event) => {
538
543
  border: var(--sms-border, 1pt solid lightgray);
539
544
  border-radius: var(--sms-border-radius, 3pt);
540
545
  background: var(--sms-bg);
541
- width: var(--sms-width, 100%);
542
- max-width: var(--sms-max-width, 800px);
546
+ width: var(--sms-width);
547
+ max-width: var(--sms-max-width);
543
548
  padding: var(--sms-padding, 0 3pt);
544
549
  color: var(--sms-text-color);
545
550
  font-size: var(--sms-font-size, inherit);
@@ -608,23 +613,19 @@ const dragstart = (idx) => (event) => {
608
613
  margin: auto 0; /* CSS reset */
609
614
  padding: 0; /* CSS reset */
610
615
  }
611
- :where(div.multiselect > ul.selected + input) {
616
+ :where(div.multiselect > ul.selected > li > input) {
612
617
  border: none;
613
618
  outline: none;
614
619
  background: none;
620
+ flex: 1; /* this + next line fix issue #12 https://git.io/JiDe3 */
621
+ min-width: 2em;
615
622
  /* ensure input uses text color and not --sms-selected-text-color */
616
623
  color: var(--sms-text-color);
617
624
  font-size: inherit;
618
625
  cursor: inherit; /* needed for disabled state */
619
626
  border-radius: 0; /* reset ul.selected > li */
620
- width: 0;
621
- visibility: hidden;
622
- }
623
- :where(div.multiselect:focus-within > ul.selected + input) {
624
- visibility: visible;
625
- width: 3em;
626
627
  }
627
- :where(div.multiselect > ul.selected + input::placeholder) {
628
+ :where(div.multiselect > ul.selected > li > input::placeholder) {
628
629
  padding-left: 5pt;
629
630
  color: var(--sms-placeholder-color);
630
631
  opacity: var(--sms-placeholder-opacity);
@@ -1,7 +1,7 @@
1
1
  import { SvelteComponentTyped } from "svelte";
2
- import type { MultiSelectEvents, Option } from './';
3
- declare const __propDef: {
4
- props: {
2
+ import type { MultiSelectEvents, Option as GenericOption } from './';
3
+ declare class __sveltets_Render<Option extends GenericOption> {
4
+ props(): {
5
5
  activeIndex?: number | null | undefined;
6
6
  activeOption?: Option | null | undefined;
7
7
  addOptionMsg?: string | undefined;
@@ -12,7 +12,7 @@ declare const __propDef: {
12
12
  defaultDisabledTitle?: string | undefined;
13
13
  disabled?: boolean | undefined;
14
14
  disabledInputTitle?: string | undefined;
15
- duplicateFunc?: ((op1: Option, op2: Option) => boolean) | undefined;
15
+ duplicateFunc?: ((op1: GenericOption, op2: GenericOption) => boolean) | undefined;
16
16
  duplicateOptionMsg?: string | undefined;
17
17
  duplicates?: boolean | undefined;
18
18
  filterFunc?: ((op: Option, searchText: string) => boolean) | undefined;
@@ -53,7 +53,8 @@ declare const __propDef: {
53
53
  ulSelectedClass?: string | undefined;
54
54
  value?: Option | Option[] | null | undefined;
55
55
  };
56
- slots: {
56
+ events(): MultiSelectEvents;
57
+ slots(): {
57
58
  'expand-icon': {
58
59
  open: boolean;
59
60
  };
@@ -69,11 +70,10 @@ declare const __propDef: {
69
70
  idx: any;
70
71
  };
71
72
  };
72
- events: MultiSelectEvents;
73
- };
74
- export type MultiSelectProps = typeof __propDef.props;
75
- export type MultiSelectEvents = typeof __propDef.events;
76
- export type MultiSelectSlots = typeof __propDef.slots;
77
- export default class MultiSelect extends SvelteComponentTyped<MultiSelectProps, MultiSelectEvents, MultiSelectSlots> {
73
+ }
74
+ export type MultiSelectProps<Option extends GenericOption> = ReturnType<__sveltets_Render<Option>['props']>;
75
+ export type MultiSelectEvents<Option extends GenericOption> = ReturnType<__sveltets_Render<Option>['events']>;
76
+ export type MultiSelectSlots<Option extends GenericOption> = ReturnType<__sveltets_Render<Option>['slots']>;
77
+ export default class MultiSelect<Option extends GenericOption> extends SvelteComponentTyped<MultiSelectProps<Option>, MultiSelectEvents<Option>, MultiSelectSlots<Option>> {
78
78
  }
79
79
  export {};
package/changelog.md CHANGED
@@ -2,8 +2,30 @@
2
2
 
3
3
  All notable changes to this project will be documented in this file. Dates are displayed in UTC.
4
4
 
5
+ #### [v8.2.4](https://github.com/janosh/svelte-multiselect/compare/v8.2.3...v8.2.4)
6
+
7
+ > 8 January 2023
8
+
9
+ - Coverage badges [`#190`](https://github.com/janosh/svelte-multiselect/pull/190)
10
+ - feat: add type inference for the `options` prop [`#189`](https://github.com/janosh/svelte-multiselect/pull/189)
11
+ - feat: add type inference for the `options` prop (#189) [`#78`](https://github.com/janosh/svelte-multiselect/issues/78)
12
+ - merge ExampleCode.svelte with CollapsibleCode.svelte [`56ff99b`](https://github.com/janosh/svelte-multiselect/commit/56ff99bcc378c5582b303aa1c03302cdbceb3076)
13
+ - pnpm add -D svelte-zoo to outsource some site components and icons [`6ee64f3`](https://github.com/janosh/svelte-multiselect/commit/6ee64f376dfe166b993c94a36d376d1dce5f44f5)
14
+ - restore reactive searchText block in loading example [`846da66`](https://github.com/janosh/svelte-multiselect/commit/846da66af058ac1f448c8aaa513d12fb4c2ac4cc)
15
+ - fix bunch of TS errors, add playwright test for dragging selected options to reorder [`a483217`](https://github.com/janosh/svelte-multiselect/commit/a4832176f6fceb5346af2d4cd8ecc01a5626ab43)
16
+ - add update-coverage package.json script [`1094f08`](https://github.com/janosh/svelte-multiselect/commit/1094f08cec9d6fd2f54b058af05022ab35ec4ac9)
17
+ - add vite alias $root to clean up package.json, readme|contributing|changelog.md imports [`c19cbe4`](https://github.com/janosh/svelte-multiselect/commit/c19cbe4e38413bbcd04d4e35eddcd4cd88c67662)
18
+ - mv src/components src/site [`3683ed7`](https://github.com/janosh/svelte-multiselect/commit/3683ed70f19498070ffe9e95c0261c688fb2f7c7)
19
+
5
20
  <!-- auto-changelog-above -->
6
21
 
22
+ #### [v8.2.3](https://github.com/janosh/svelte-multiselect/compare/v8.2.2...v8.2.3)
23
+
24
+ > 28 December 2022
25
+
26
+ - add 'Open in StackBlitz' links to example code fences [`ac07557`](https://github.com/janosh/svelte-multiselect/commit/ac075576c261892807faa0071b5f3e0b5b4fcd2c)
27
+ - v8.2.2 contains unintended breaking changes and was deprecated on NPM (see [#188](https://github.com/janosh/svelte-multiselect/issues/188)). Use this fixed release instead. [`ef4d669`](https://github.com/janosh/svelte-multiselect/commit/ef4d669)
28
+
7
29
  #### [v8.2.2](https://github.com/janosh/svelte-multiselect/compare/v8.2.1...v8.2.2)
8
30
 
9
31
  > 18 December 2022
@@ -109,7 +131,7 @@ All notable changes to this project will be documented in this file. Dates are d
109
131
 
110
132
  - Fix single select with arrow and enter keys [`#128`](https://github.com/janosh/svelte-multiselect/pull/128)
111
133
  - Add SCSS preprocessing [`#126`](https://github.com/janosh/svelte-multiselect/pull/126)
112
- - [pre-commit.ci] pre-commit autoupdate [`#124`](https://github.com/janosh/svelte-multiselect/pull/124)
134
+ - pre-commit autoupdate [`#124`](https://github.com/janosh/svelte-multiselect/pull/124)
113
135
  - more unit tests [`1adbc99`](https://github.com/janosh/svelte-multiselect/commit/1adbc994b746b39c4ad081dc2573bf37f27c96c0)
114
136
  - test required but empty MultiSelect fails form validity check (i.e. causes unsubmittable form) and filled one passes it [`fd8b377`](https://github.com/janosh/svelte-multiselect/commit/fd8b37782cd508aacfc8125c6647cefe56144b80)
115
137
 
@@ -179,7 +201,7 @@ All notable changes to this project will be documented in this file. Dates are d
179
201
  - Convert E2E tests from`vitest` to `@playwright/test` [`#95`](https://github.com/janosh/svelte-multiselect/pull/95)
180
202
  - Allow empty Multiselect [`#94`](https://github.com/janosh/svelte-multiselect/pull/94)
181
203
  - Add new slot `'remove-icon'` [`#93`](https://github.com/janosh/svelte-multiselect/pull/93)
182
- - [pre-commit.ci] pre-commit autoupdate [`#92`](https://github.com/janosh/svelte-multiselect/pull/92)
204
+ - pre-commit autoupdate [`#92`](https://github.com/janosh/svelte-multiselect/pull/92)
183
205
 
184
206
  #### [v5.0.3](https://github.com/janosh/svelte-multiselect/compare/v5.0.2...v5.0.3)
185
207
 
@@ -217,7 +239,7 @@ All notable changes to this project will be documented in this file. Dates are d
217
239
 
218
240
  - Fix backspace deleting multiple selected options if identical labels [`#72`](https://github.com/janosh/svelte-multiselect/pull/72)
219
241
  - Several fixes for `allowUserOptions` [`#69`](https://github.com/janosh/svelte-multiselect/pull/69)
220
- - [pre-commit.ci] pre-commit autoupdate [`#70`](https://github.com/janosh/svelte-multiselect/pull/70)
242
+ - pre-commit autoupdate [`#70`](https://github.com/janosh/svelte-multiselect/pull/70)
221
243
 
222
244
  #### [v4.0.5](https://github.com/janosh/svelte-multiselect/compare/v4.0.4...v4.0.5)
223
245
 
@@ -340,7 +362,7 @@ All notable changes to this project will be documented in this file. Dates are d
340
362
  - favorite web framework show Confetti.svelte on:add Svelte [`8d109ee`](https://github.com/janosh/svelte-multiselect/commit/8d109ee5c7755e447fcb72419f3b7ecc19cac0b2)
341
363
  - bump svelte@3.45.0 to silence warning: MultiSelect has unused export property 'defaultDisabledTitle' (sveltejs/svelte#6964) [`f80a7a6`](https://github.com/janosh/svelte-multiselect/commit/f80a7a622310005407585298f2611597c0941990)
342
364
  - update readme + svelte-toc@0.2.0 [`40013ba`](https://github.com/janosh/svelte-multiselect/commit/40013badd61dd0fcade7ab295dabd26693e3cc51)
343
- - [pre-commit.ci] pre-commit autoupdate [`0d05864`](https://github.com/janosh/svelte-multiselect/commit/0d05864d19987460dd30d667eb22deb91a520668)
365
+ - pre-commit autoupdate [`0d05864`](https://github.com/janosh/svelte-multiselect/commit/0d05864d19987460dd30d667eb22deb91a520668)
344
366
  - iOS Safari prevent zoom into page on focus MultiSelect input [`44f17be`](https://github.com/janosh/svelte-multiselect/commit/44f17be53378e38f4a8748b815737d25cdebc85f)
345
367
 
346
368
  ### [v3.0.0](https://github.com/janosh/svelte-multiselect/compare/v2.0.0...v3.0.0)
@@ -391,7 +413,7 @@ All notable changes to this project will be documented in this file. Dates are d
391
413
 
392
414
  - Add new prop disabledOptions [`#9`](https://github.com/janosh/svelte-multiselect/pull/9)
393
415
  - add pre-commit hooks [`dfb6399`](https://github.com/janosh/svelte-multiselect/commit/dfb6399a77b705f8e5979eb887d345a5f52ff929)
394
- - [pre-commit.ci] pre-commit autoupdate [`b69425d`](https://github.com/janosh/svelte-multiselect/commit/b69425d18473122f1af889d2f48c60d02e43b99f)
416
+ - pre-commit autoupdate [`b69425d`](https://github.com/janosh/svelte-multiselect/commit/b69425d18473122f1af889d2f48c60d02e43b99f)
395
417
 
396
418
  #### [v1.1.11](https://github.com/janosh/svelte-multiselect/compare/v1.1.10...v1.1.11)
397
419
 
@@ -483,7 +505,7 @@ All notable changes to this project will be documented in this file. Dates are d
483
505
 
484
506
  - remove hidden input for storing currently selected options as JSON [`802a219`](https://github.com/janosh/svelte-multiselect/commit/802a2195a28986c219298d7d9e7ca47f2aaf7db6)
485
507
 
486
- #### v1.0.0
508
+ ### v1.0.0
487
509
 
488
510
  > 7 May 2021
489
511
 
@@ -2,7 +2,7 @@
2
2
  /** @typedef {typeof __propDef.events} ChevronExpandEvents */
3
3
  /** @typedef {typeof __propDef.slots} ChevronExpandSlots */
4
4
  export default class ChevronExpand extends SvelteComponentTyped<{
5
- [x: string]: never;
5
+ [x: string]: any;
6
6
  }, {
7
7
  [evt: string]: CustomEvent<any>;
8
8
  }, {}> {
@@ -13,7 +13,7 @@ export type ChevronExpandSlots = typeof __propDef.slots;
13
13
  import { SvelteComponentTyped } from "svelte";
14
14
  declare const __propDef: {
15
15
  props: {
16
- [x: string]: never;
16
+ [x: string]: any;
17
17
  };
18
18
  events: {
19
19
  [evt: string]: CustomEvent<any>;
@@ -2,7 +2,7 @@
2
2
  /** @typedef {typeof __propDef.events} CrossEvents */
3
3
  /** @typedef {typeof __propDef.slots} CrossSlots */
4
4
  export default class Cross extends SvelteComponentTyped<{
5
- [x: string]: never;
5
+ [x: string]: any;
6
6
  }, {
7
7
  [evt: string]: CustomEvent<any>;
8
8
  }, {}> {
@@ -13,7 +13,7 @@ export type CrossSlots = typeof __propDef.slots;
13
13
  import { SvelteComponentTyped } from "svelte";
14
14
  declare const __propDef: {
15
15
  props: {
16
- [x: string]: never;
16
+ [x: string]: any;
17
17
  };
18
18
  events: {
19
19
  [evt: string]: CustomEvent<any>;
@@ -2,7 +2,7 @@
2
2
  /** @typedef {typeof __propDef.events} DisabledEvents */
3
3
  /** @typedef {typeof __propDef.slots} DisabledSlots */
4
4
  export default class Disabled extends SvelteComponentTyped<{
5
- [x: string]: never;
5
+ [x: string]: any;
6
6
  }, {
7
7
  [evt: string]: CustomEvent<any>;
8
8
  }, {}> {
@@ -13,7 +13,7 @@ export type DisabledSlots = typeof __propDef.slots;
13
13
  import { SvelteComponentTyped } from "svelte";
14
14
  declare const __propDef: {
15
15
  props: {
16
- [x: string]: never;
16
+ [x: string]: any;
17
17
  };
18
18
  events: {
19
19
  [evt: string]: CustomEvent<any>;
@@ -2,7 +2,7 @@
2
2
  /** @typedef {typeof __propDef.events} OctocatEvents */
3
3
  /** @typedef {typeof __propDef.slots} OctocatSlots */
4
4
  export default class Octocat extends SvelteComponentTyped<{
5
- [x: string]: never;
5
+ [x: string]: any;
6
6
  }, {
7
7
  [evt: string]: CustomEvent<any>;
8
8
  }, {}> {
@@ -13,7 +13,7 @@ export type OctocatSlots = typeof __propDef.slots;
13
13
  import { SvelteComponentTyped } from "svelte";
14
14
  declare const __propDef: {
15
15
  props: {
16
- [x: string]: never;
16
+ [x: string]: any;
17
17
  };
18
18
  events: {
19
19
  [evt: string]: CustomEvent<any>;
package/index.d.ts CHANGED
@@ -47,3 +47,4 @@ export type MultiSelectEvents = {
47
47
  touchmove: TouchEvent;
48
48
  touchstart: TouchEvent;
49
49
  };
50
+ export declare function scroll_into_view_if_needed_polyfill(centerIfNeeded?: boolean): IntersectionObserver;
package/index.js CHANGED
@@ -3,21 +3,25 @@ export { default } from './MultiSelect.svelte';
3
3
  // https://github.com/janosh/svelte-multiselect/issues/87
4
4
  // this polyfill was copied from
5
5
  // https://github.com/nuxodin/lazyfill/blob/a8e63/polyfills/Element/prototype/scrollIntoViewIfNeeded.js
6
+ // exported for testing
7
+ export function scroll_into_view_if_needed_polyfill(centerIfNeeded = true) {
8
+ const el = this;
9
+ const observer = new IntersectionObserver(function ([entry]) {
10
+ const ratio = entry.intersectionRatio;
11
+ if (ratio < 1) {
12
+ const place = ratio <= 0 && centerIfNeeded ? `center` : `nearest`;
13
+ el.scrollIntoView({
14
+ block: place,
15
+ inline: place,
16
+ });
17
+ }
18
+ this.disconnect();
19
+ });
20
+ observer.observe(this);
21
+ return observer; // return for testing
22
+ }
6
23
  if (typeof Element !== `undefined` &&
7
24
  !Element.prototype?.scrollIntoViewIfNeeded &&
8
25
  typeof IntersectionObserver !== `undefined`) {
9
- Element.prototype.scrollIntoViewIfNeeded = function (centerIfNeeded = true) {
10
- const el = this;
11
- new IntersectionObserver(function ([entry]) {
12
- const ratio = entry.intersectionRatio;
13
- if (ratio < 1) {
14
- const place = ratio <= 0 && centerIfNeeded ? `center` : `nearest`;
15
- el.scrollIntoView({
16
- block: place,
17
- inline: place,
18
- });
19
- }
20
- this.disconnect();
21
- }).observe(this);
22
- };
26
+ Element.prototype.scrollIntoViewIfNeeded = scroll_into_view_if_needed_polyfill;
23
27
  }
package/package.json CHANGED
@@ -5,42 +5,42 @@
5
5
  "homepage": "https://janosh.github.io/svelte-multiselect",
6
6
  "repository": "https://github.com/janosh/svelte-multiselect",
7
7
  "license": "MIT",
8
- "version": "8.2.2",
8
+ "version": "8.2.4",
9
9
  "type": "module",
10
10
  "svelte": "index.js",
11
- "main": "index.js",
12
11
  "bugs": "https://github.com/janosh/svelte-multiselect/issues",
13
12
  "devDependencies": {
14
13
  "@iconify/svelte": "^3.0.1",
15
- "@playwright/test": "^1.29.0",
16
- "@sveltejs/adapter-static": "1.0.0",
17
- "@sveltejs/kit": "1.0.1",
18
- "@sveltejs/package": "1.0.1",
14
+ "@playwright/test": "^1.29.2",
15
+ "@sveltejs/adapter-static": "1.0.1",
16
+ "@sveltejs/kit": "1.0.7",
17
+ "@sveltejs/package": "1.0.2",
19
18
  "@sveltejs/vite-plugin-svelte": "^2.0.2",
20
- "@typescript-eslint/eslint-plugin": "^5.46.1",
21
- "@typescript-eslint/parser": "^5.46.1",
22
- "@vitest/coverage-c8": "^0.25.8",
23
- "eslint": "^8.30.0",
19
+ "@typescript-eslint/eslint-plugin": "^5.48.0",
20
+ "@typescript-eslint/parser": "^5.48.0",
21
+ "@vitest/coverage-c8": "^0.26.3",
22
+ "eslint": "^8.31.0",
24
23
  "eslint-plugin-svelte3": "^4.0.0",
25
- "hastscript": "^7.1.0",
24
+ "hastscript": "^7.2.0",
26
25
  "highlight.js": "^11.7.0",
27
- "jsdom": "^20.0.3",
26
+ "jsdom": "^21.0.0",
28
27
  "mdsvex": "^0.10.6",
29
28
  "mdsvexamples": "^0.3.3",
30
- "prettier": "^2.8.1",
29
+ "prettier": "^2.8.2",
31
30
  "prettier-plugin-svelte": "^2.9.0",
32
31
  "rehype-autolink-headings": "^6.1.1",
33
32
  "rehype-slug": "^5.1.0",
34
33
  "svelte": "^3.55.0",
35
- "svelte-check": "^2.10.2",
36
- "svelte-github-corner": "^0.1.0",
34
+ "svelte-check": "^3.0.1",
35
+ "svelte-github-corner": "^0.2.0",
37
36
  "svelte-preprocess": "^5.0.0",
38
- "svelte-toc": "^0.5.0",
39
- "svelte2tsx": "^0.5.22",
37
+ "svelte-toc": "^0.5.1",
38
+ "svelte-zoo": "^0.1.4",
39
+ "svelte2tsx": "^0.6.0",
40
40
  "tslib": "^2.4.1",
41
41
  "typescript": "^4.9.4",
42
- "vite": "^4.0.1",
43
- "vitest": "^0.25.8"
42
+ "vite": "^4.0.4",
43
+ "vitest": "^0.26.3"
44
44
  },
45
45
  "keywords": [
46
46
  "svelte",
package/readme.md CHANGED
@@ -21,7 +21,7 @@
21
21
 
22
22
  <slot name="examples" />
23
23
 
24
- ## ๐Ÿ’ก &nbsp; Features
24
+ ## ๐Ÿ’ก &thinsp; Features
25
25
 
26
26
  - **Bindable:** `bind:selected` gives you an array of the currently selected options. Thanks to Svelte's 2-way binding, it can also control the component state externally through assignment `selected = ['foo', 42]`.
27
27
  - **Keyboard friendly** for mouse-less form completion
@@ -34,7 +34,13 @@
34
34
 
35
35
  <slot name="nav" />
36
36
 
37
- ## ๐Ÿ“œ &nbsp; Breaking changes
37
+ ## ๐Ÿงช &thinsp; Coverage
38
+
39
+ | Statements | Branches | Lines |
40
+ | ------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------ | -------------------------------------------------------------------------------- |
41
+ | ![Statements](https://img.shields.io/badge/statements-92.95%25-brightgreen.svg?style=flat) | ![Branches](https://img.shields.io/badge/branches-100%25-brightgreen.svg?style=flat) | ![Lines](https://img.shields.io/badge/lines-92.95%25-brightgreen.svg?style=flat) |
42
+
43
+ ## ๐Ÿ“œ &thinsp; Breaking changes
38
44
 
39
45
  - **6.1.0**&nbsp; The `dispatch` events `focus` and `blur` were renamed to `open` and `close`, respectively. These actions refer to the dropdown list, i.e. `<MultiSelect on:open={(event) => console.log(event)}>` will trigger when the dropdown list opens. The focus and blur events are now regular DOM (not Svelte `dispatch`) events emitted by the `<input>` node. [PR 120](https://github.com/janosh/svelte-multiselect/pull/120).
40
46
  - **v7.0.0**&nbsp; `selected` (as well `selectedLabels` and `selectedValues`) used to be arrays always. Now, if `maxSelect=1`, they will no longer be a length-1 array but simply a single a option (label/value respectively) or `null` if no option is selected. [PR 123](https://github.com/janosh/svelte-multiselect/pull/123).
@@ -42,15 +48,15 @@
42
48
  - Props `selectedLabels` and `selectedValues` were removed. If you were using them, they were equivalent to assigning `bind:selected` to a local variable and then running `selectedLabels = selected.map(option => option.label)` and `selectedValues = selected.map(option => option.value)` if your options were objects with `label` and `value` keys. If they were simple strings/numbers, there was no point in using `selected{Labels,Values}` anyway. [PR 138](https://github.com/janosh/svelte-multiselect/pull/138)
43
49
  - Prop `noOptionsMsg` was renamed to `noMatchingOptionsMsg`. [PR 133](https://github.com/janosh/svelte-multiselect/pull/133).
44
50
 
45
- ## ๐Ÿ”จ &nbsp; Installation
51
+ ## ๐Ÿ”จ &thinsp; Installation
46
52
 
47
53
  ```sh
48
- npm install -D svelte-multiselect
49
- pnpm add -D svelte-multiselect
50
- yarn add -D svelte-multiselect
54
+ npm install --dev svelte-multiselect
55
+ pnpm add --dev svelte-multiselect
56
+ yarn add --dev svelte-multiselect
51
57
  ```
52
58
 
53
- ## ๐Ÿ“™ &nbsp; Usage
59
+ ## ๐Ÿ“™ &thinsp; Usage
54
60
 
55
61
  ```svelte
56
62
  <script>
@@ -68,7 +74,7 @@ Favorite Frontend Tools?
68
74
  <MultiSelect bind:selected options={ui_libs} />
69
75
  ```
70
76
 
71
- ## ๐Ÿ”ฃ &nbsp; Props
77
+ ## ๐Ÿ”ฃ &thinsp; Props
72
78
 
73
79
  Full list of props/bindable variables for this component. The `Option` type you see below is defined in [`src/lib/index.ts`](https://github.com/janosh/svelte-multiselect/blob/main/src/lib/index.ts) and can be imported as `import { type Option } from 'svelte-multiselect'`.
74
80
 
@@ -135,7 +141,7 @@ Full list of props/bindable variables for this component. The `Option` type you
135
141
 
136
142
  <!-- prettier-ignore -->
137
143
  1. ```ts
138
- duplicateFunc: (op1: Option, op2: Option) => boolean = (op1, op2) =>
144
+ duplicateFunc: (op1: GenericOption, op2: GenericOption) => boolean = (op1, op2) =>
139
145
  `${get_label(op1)}`.toLowerCase() === `${get_label(op2)}`.toLowerCase()
140
146
  ```
141
147
 
@@ -344,7 +350,7 @@ Full list of props/bindable variables for this component. The `Option` type you
344
350
 
345
351
  If `maxSelect={1}`, `value` will be the single item in `selected` (or `null` if `selected` is empty). If `maxSelect != 1`, `maxSelect` and `selected` are equal. Warning: `value` supports 1-way binding only, meaning `bind:value` will update `value` when internal component state changes but changing `value` externally will not update internal component state. This is because `value` is already reactive to `selected` and making `selected` reactive to `value` would be cyclic. Suggestions for better solutions that solve both [#86](https://github.com/janosh/svelte-multiselect/issues/86) and [#136](https://github.com/janosh/svelte-multiselect/issues/136) welcome!
346
352
 
347
- ## ๐ŸŽฐ &nbsp; Slots
353
+ ## ๐ŸŽฐ &thinsp; Slots
348
354
 
349
355
  `MultiSelect.svelte` accepts the following named slots:
350
356
 
@@ -376,7 +382,7 @@ Example:
376
382
  </MultiSelect>
377
383
  ```
378
384
 
379
- ## ๐ŸŽฌ &nbsp; Events
385
+ ## ๐ŸŽฌ &thinsp; Events
380
386
 
381
387
  `MultiSelect.svelte` dispatches the following events:
382
388
 
@@ -439,25 +445,36 @@ The above list of events are [Svelte `dispatch` events](https://svelte.dev/tutor
439
445
  />
440
446
  ```
441
447
 
442
- ## ๐Ÿฆบ &nbsp; TypeScript
448
+ ## ๐Ÿฆบ &thinsp; TypeScript
443
449
 
444
- TypeScript users can import the types used for internal type safety:
450
+ The type of `options` is inferred automatically from the data you pass. E.g.
445
451
 
446
- ```svelte
447
- <script lang="ts">
448
- import MultiSelect from 'svelte-multiselect'
449
- import type { Option, ObjectOption } from 'svelte-multiselect'
450
-
451
- const myOptions: ObjectOption[] = [
452
- { label: 'foo', value: 42 },
453
- { label: 'bar', value: 69 },
454
- ]
455
- // an Option can be string | number | ObjectOption
456
- const myNumbers: Option[] = [42, 69]
457
- </script>
452
+ ```ts
453
+ const options = [
454
+ { label: `foo`, value: 42 }
455
+ { label: `bar`, value: 69 }
456
+ ]
457
+ // type Option = { label: string, value: number }
458
+ const options = [`foo`, `bar`]
459
+ // type Option = string
460
+ const options = [42, 69]
461
+ // type Option = number
462
+ ```
463
+
464
+ The inferred type of `Option` is used to enforce type-safety on derived props like `selected` as well as slot components. E.g. you'll get an error when trying to use a slot component that expects a string if your options are objects (see [this comment](https://github.com/janosh/svelte-multiselect/pull/189/files#r1058853697) for example screenshots).
465
+
466
+ You can also import [the types this component uses](https://github.com/janosh/svelte-multiselect/blob/main/src/lib/index.ts) for downstream applications:
467
+
468
+ ```ts
469
+ import {
470
+ Option,
471
+ ObjectOption,
472
+ DispatchEvents,
473
+ MultiSelectEvents,
474
+ } from 'svelte-multiselect'
458
475
  ```
459
476
 
460
- ## โœจ &nbsp; Styling
477
+ ## โœจ &thinsp; Styling
461
478
 
462
479
  There are 3 ways to style this component. To understand which options do what, it helps to keep in mind this simplified DOM structure of the component:
463
480
 
@@ -485,8 +502,8 @@ If you only want to make small adjustments, you can pass the following CSS varia
485
502
  - `background: var(--sms-bg)`
486
503
  - `color: var(--sms-text-color)`
487
504
  - `min-height: var(--sms-min-height, 22pt)`
488
- - `width: var(--sms-width, 100%)`
489
- - `max-width: var(--sms-max-width, 800px)`
505
+ - `width: var(--sms-width)`
506
+ - `max-width: var(--sms-max-width)`
490
507
  - `margin: var(--sms-margin)`
491
508
  - `font-size: var(--sms-font-size, inherit)`
492
509
  - `div.multiselect.open`
@@ -608,10 +625,10 @@ Odd as it may seem, you get the most fine-grained control over the styling of ev
608
625
  }
609
626
  ```
610
627
 
611
- ## ๐Ÿ†• &nbsp; Changelog
628
+ ## ๐Ÿ†• &thinsp; Changelog
612
629
 
613
630
  [View the changelog](changelog.md).
614
631
 
615
- ## ๐Ÿ™ &nbsp; Contributing
632
+ ## ๐Ÿ™ &thinsp; Contributing
616
633
 
617
634
  Here are some steps to [get you started](contributing.md) if you'd like to contribute to this project!