@@ -7,28 +7,16 @@ import {
7
7
ComboboxListbox ,
8
8
ComboboxPortal ,
9
9
ComboboxTrigger ,
10
- Tooltip ,
11
- } from '@qwik-ui/headless' ;
12
-
13
- import {
14
10
ComboboxOption ,
15
11
type ResolvedOption ,
16
- } from '../../../../../../../../packages/kit-headless/src/components/combobox ' ;
12
+ } from '@qwik-ui/headless ' ;
17
13
18
- import { PreviewCodeExample } from '../../../_components/preview-code-example/preview-code-example' ;
14
+ // import {
15
+ // ComboboxOption,
16
+ // type ResolvedOption,
17
+ // } from '../../../../../../../../packages/kit-headless/src/components/combobox';
19
18
20
- const stringsExample = [
21
- 'Caleb' ,
22
- 'Olivia' ,
23
- 'James' ,
24
- 'Ava' ,
25
- 'Noah' ,
26
- 'Emma' ,
27
- 'Oliver' ,
28
- 'Amelia' ,
29
- 'Theodore' ,
30
- 'Elizabeth' ,
31
- ] ;
19
+ import { PreviewCodeExample } from '../../../_components/preview-code-example/preview-code-example' ;
32
20
33
21
type Trainer = {
34
22
testValue : string ;
@@ -59,15 +47,15 @@ export const HeroExample = component$(() => {
59
47
optionValueKey = "testValue"
60
48
optionLabelKey = "testLabel"
61
49
optionDisabledKey = "disabled"
62
- renderOption$ = { ( resolved , index : number ) => (
50
+ renderOption$ = { ( option , index : number ) => (
63
51
< ComboboxOption
64
- key = { resolved . key }
65
- resolved = { resolved }
52
+ key = { option . key }
53
+ resolved = { option }
66
54
index = { index }
67
55
class = "aria-disabled:text-slate-600 aria-disabled:hover:bg-slate-700 rounded-sm px-2 hover:bg-slate-500 aria-selected:bg-slate-500 text-white border-2 border-transparent aria-selected:border-slate-200 group"
68
56
>
69
57
< span class = "block group-aria-selected:translate-x-[3px] transition-transform duration-350" >
70
- { resolved . option . testLabel }
58
+ { option . option . testLabel }
71
59
</ span >
72
60
</ ComboboxOption >
73
61
) }
@@ -142,14 +130,14 @@ export const StringCombobox = component$(() => {
142
130
return option . toLowerCase ( ) . startsWith ( value . toLowerCase ( ) ) ;
143
131
} )
144
132
}
145
- renderOption$ = { ( resolved : ResolvedOption , index : number ) => (
133
+ renderOption$ = { ( option : ResolvedOption , index : number ) => (
146
134
< ComboboxOption
147
- key = { resolved . key }
135
+ key = { option . key }
148
136
class = "aria-disabled:text-slate-600 aria-disabled:hover:bg-slate-700 rounded-sm px-2 hover:bg-slate-500 aria-selected:bg-slate-500 text-white border-2 border-transparent aria-selected:border-slate-200 group"
149
137
index = { index }
150
- resolved = { resolved }
138
+ resolved = { option }
151
139
>
152
- { resolved . label }
140
+ { option . label }
153
141
</ ComboboxOption >
154
142
) }
155
143
>
@@ -416,7 +404,7 @@ export const DisabledExample = component$(() => {
416
404
myDisabledKey : boolean ;
417
405
} ;
418
406
419
- const objectExample : Array < DisabledExample > = [
407
+ const disabledExample : Array < DisabledExample > = [
420
408
{ value : '0' , label : 'Enabled' , myDisabledKey : false } ,
421
409
{ value : '1' , label : 'Enabled' , myDisabledKey : false } ,
422
410
{ value : '2' , label : 'Disabled' , myDisabledKey : true } ,
@@ -433,7 +421,7 @@ export const DisabledExample = component$(() => {
433
421
< div >
434
422
< Combobox
435
423
class = "w-fit"
436
- options = { objectExample }
424
+ options = { disabledExample }
437
425
optionDisabledKey = "myDisabledKey"
438
426
renderOption$ = { ( option : ResolvedOption , index : number ) => (
439
427
< ComboboxOption
@@ -489,58 +477,136 @@ export const CustomKeysExample = component$(() => {
489
477
} ;
490
478
491
479
const pokemonExample : Array < Pokemon > = [
492
- { pokedex : '1' , pokemon : 'Bulbasaur' , isPokemonCaught : false } ,
493
- { pokedex : '2' , pokemon : 'Ivysaur' , isPokemonCaught : true } ,
480
+ { pokedex : '1' , pokemon : 'Bulbasaur' , isPokemonCaught : true } ,
481
+ { pokedex : '2' , pokemon : 'Ivysaur' , isPokemonCaught : false } ,
494
482
{ pokedex : '3' , pokemon : 'Venusaur' , isPokemonCaught : false } ,
495
483
{ pokedex : '4' , pokemon : 'Charmander' , isPokemonCaught : true } ,
496
- { pokedex : '5' , pokemon : 'Charmeleon' , isPokemonCaught : false } ,
484
+ { pokedex : '5' , pokemon : 'Charmeleon' , isPokemonCaught : true } ,
497
485
{ pokedex : '6' , pokemon : 'Charizard' , isPokemonCaught : true } ,
498
486
{ pokedex : '7' , pokemon : 'Squirtle' , isPokemonCaught : false } ,
499
- { pokedex : '8' , pokemon : 'Wartortle' , isPokemonCaught : true } ,
487
+ { pokedex : '8' , pokemon : 'Wartortle' , isPokemonCaught : false } ,
500
488
] ;
501
489
502
- const isTooltipVisibleSig = useSignal ( false ) ;
490
+ const isPokemonCaught = useSignal ( false ) ;
503
491
504
492
useVisibleTask$ ( ( { track } ) => {
505
- track ( ( ) => isTooltipVisibleSig . value ) ;
506
-
507
- console . log ( isTooltipVisibleSig . value ) ;
493
+ track ( ( ) => isPokemonCaught . value ) ;
508
494
} ) ;
509
495
510
496
return (
511
497
< PreviewCodeExample >
512
498
< div class = "flex flex-col items-center gap-4 p-4" q :slot = "actualComponent" >
513
- < div >
499
+ < div class = "relative" >
500
+ { isPokemonCaught . value && (
501
+ < p class = "absolute translate-x-[-105%] w-full text-white bg-slate-800 p-4 shadow-dark-medium rounded-md border-2 border-slate-400" >
502
+ You've already caught this pokemon!
503
+ </ p >
504
+ ) }
514
505
< Combobox
515
506
class = "w-fit"
516
507
options = { pokemonExample }
517
508
optionValueKey = "pokedex"
518
509
optionLabelKey = "pokemon"
519
510
optionDisabledKey = "isPokemonCaught"
511
+ renderOption$ = { ( option : ResolvedOption , index : number ) => {
512
+ const pokemonOption = option . option as Pokemon ;
513
+ return (
514
+ < ComboboxOption
515
+ key = { option . key }
516
+ class = "aria-disabled:text-slate-600 aria-disabled:hover:bg-slate-700 rounded-sm px-2 hover:bg-slate-500 aria-selected:bg-slate-500 text-white border-2 border-transparent aria-selected:border-slate-200 group flex justify-between"
517
+ index = { index }
518
+ resolved = { option }
519
+ onMouseEnter$ = { ( ) => {
520
+ if ( option . disabled === true ) {
521
+ isPokemonCaught . value = true ;
522
+ }
523
+ } }
524
+ onMouseLeave$ = { ( ) => {
525
+ isPokemonCaught . value = false ;
526
+ } }
527
+ >
528
+ < span > { pokemonOption . pokemon } </ span >
529
+ < span > { pokemonOption . pokedex } </ span >
530
+ </ ComboboxOption >
531
+ ) ;
532
+ } }
533
+ >
534
+ < ComboboxLabel class = " font-semibold text-white" > Pokemon 🦏</ ComboboxLabel >
535
+ < ComboboxControl class = "bg-[#1f2532] flex items-center rounded-sm border-slate-400 border-[1px] relative" >
536
+ < ComboboxInput class = "px-2 w-44 bg-slate-900 px-d2 pr-6 text-white placeholder:text-slate-500" />
537
+ < ComboboxTrigger class = "w-6 h-6 group absolute right-0" >
538
+ < svg
539
+ xmlns = "http://www.w3.org/2000/svg"
540
+ viewBox = "0 0 24 24"
541
+ fill = "none"
542
+ class = "stroke-white group-aria-expanded:-rotate-180 transition-transform duration-[450ms]"
543
+ stroke-linecap = "round"
544
+ stroke-width = "2"
545
+ stroke-linejoin = "round"
546
+ >
547
+ < polyline points = "6 9 12 15 18 9" > </ polyline >
548
+ </ svg >
549
+ </ ComboboxTrigger >
550
+ </ ComboboxControl >
551
+ < ComboboxPortal >
552
+ < ComboboxListbox
553
+ flip = { true }
554
+ offset = { 8 }
555
+ class = "w-44 bg-slate-900 px-4 py-2 rounded-sm border-slate-400 border-[1px]"
556
+ />
557
+ </ ComboboxPortal >
558
+ </ Combobox >
559
+ </ div >
560
+ </ div >
561
+
562
+ < div q :slot = "codeExample" >
563
+ < Slot />
564
+ </ div >
565
+ </ PreviewCodeExample >
566
+ ) ;
567
+ } ) ;
568
+
569
+ export const FlipExample = component$ ( ( ) => {
570
+ type FlipExample = {
571
+ value : string ;
572
+ label : string ;
573
+ } ;
574
+
575
+ const flipExample : Array < FlipExample > = [
576
+ { value : '0' , label : 'Up! ☝️' } ,
577
+ { value : '1' , label : 'Up! ☝️' } ,
578
+ { value : '2' , label : 'Down! 👇' } ,
579
+ { value : '3' , label : 'Up! ☝️' } ,
580
+ { value : '4' , label : 'Down! 👇' } ,
581
+ { value : '5' , label : 'Down! 👇' } ,
582
+ { value : '6' , label : 'Down! 👇' } ,
583
+ { value : '7' , label : 'Up! ☝️' } ,
584
+ ] ;
585
+
586
+ return (
587
+ < PreviewCodeExample >
588
+ < div class = "flex flex-col items-center gap-4 p-4" q :slot = "actualComponent" >
589
+ < div >
590
+ < Combobox
591
+ class = "w-fit"
592
+ options = { flipExample }
593
+ optionDisabledKey = "myDisabledKey"
520
594
renderOption$ = { ( option : ResolvedOption , index : number ) => (
521
595
< ComboboxOption
522
596
key = { option . key }
523
597
class = "aria-disabled:text-slate-600 aria-disabled:hover:bg-slate-700 rounded-sm px-2 hover:bg-slate-500 aria-selected:bg-slate-500 text-white border-2 border-transparent aria-selected:border-slate-200 group"
524
598
index = { index }
525
599
resolved = { option }
526
- onMouseEnter$ = { ( ) => {
527
- console . log ( 'Mouse entered' ) ;
528
- if ( option . disabled !== undefined && option . disabled === true ) {
529
- isTooltipVisibleSig . value = true ;
530
- }
531
- } }
532
- onMouseLeave$ = { ( ) => {
533
- console . log ( 'Mouse left' ) ;
534
- isTooltipVisibleSig . value = false ;
535
- } }
536
600
>
537
601
{ option . label }
538
602
</ ComboboxOption >
539
603
) }
540
604
>
541
- < ComboboxLabel class = " font-semibold text-white" > Disabled ⛔</ ComboboxLabel >
542
- < ComboboxControl class = "bg-[#1f2532] flex items-center rounded-sm border-slate-400 border-[1px] relative" >
543
- < ComboboxInput class = "px-2 w-44 bg-slate-900 px-d2 pr-6 text-white placeholder:text-slate-500" />
605
+ < ComboboxLabel class = " font-semibold text-white" >
606
+ ☝️ Scroll up and down with me open! 👇
607
+ </ ComboboxLabel >
608
+ < ComboboxControl class = "bg-[#1f2532] flex items-center rounded-sm border-slate-400 border-[1px] relative mt-2" >
609
+ < ComboboxInput class = "px-2 bg-slate-900 px-d2 pr-6 text-white placeholder:text-slate-500" />
544
610
< ComboboxTrigger class = "w-6 h-6 group absolute right-0" >
545
611
< svg
546
612
xmlns = "http://www.w3.org/2000/svg"
@@ -563,13 +629,71 @@ export const CustomKeysExample = component$(() => {
563
629
/>
564
630
</ ComboboxPortal >
565
631
</ Combobox >
566
- { isTooltipVisibleSig . value && (
567
- < Tooltip
568
- class = "w-fit bg-slate-400 text-slate-950 p-4"
569
- content = "This Pokemon has already been caught!"
570
- position = "top"
571
- />
572
- ) }
632
+ </ div >
633
+ </ div >
634
+
635
+ < div q :slot = "codeExample" >
636
+ < Slot />
637
+ </ div >
638
+ </ PreviewCodeExample >
639
+ ) ;
640
+ } ) ;
641
+
642
+ export const ShiftExample = component$ ( ( ) => {
643
+ const shiftExample = [ 'Example1' , 'Example2' , 'Example3' ] ;
644
+ const isListboxOpenSig = useSignal ( true ) ;
645
+
646
+ return (
647
+ < PreviewCodeExample >
648
+ < div
649
+ class = "flex flex-col items-center gap-4 p-4"
650
+ style = { { overflow : 'auto' , width : '100%' } }
651
+ q :slot = "actualComponent"
652
+ >
653
+ < div class = "w-[5000px] flex-shrink-0 flex justify-center" >
654
+ < Combobox
655
+ class = "w-fit"
656
+ options = { shiftExample }
657
+ bind :isListboxOpenSig = { isListboxOpenSig }
658
+ renderOption$ = { ( option : ResolvedOption , index : number ) => (
659
+ < ComboboxOption
660
+ key = { option . key }
661
+ class = "aria-disabled:text-slate-600 aria-disabled:hover:bg-slate-700 rounded-sm px-2 hover:bg-slate-500 aria-selected:bg-slate-500 text-white border-2 border-transparent aria-selected:border-slate-200 group"
662
+ index = { index }
663
+ resolved = { option }
664
+ >
665
+ { option . label }
666
+ </ ComboboxOption >
667
+ ) }
668
+ >
669
+ < ComboboxLabel class = " font-semibold text-white" > Fruits 🍓</ ComboboxLabel >
670
+ < ComboboxControl class = "bg-[#1f2532] flex items-center rounded-sm border-slate-400 border-[1px] relative" >
671
+ < ComboboxInput
672
+ class = "px-2 w-44 bg-slate-900 px-d2 pr-6 text-white placeholder:text-slate-500"
673
+ placeholder = "Papaya"
674
+ />
675
+ < ComboboxTrigger class = "w-6 h-6 group absolute right-0" >
676
+ < svg
677
+ xmlns = "http://www.w3.org/2000/svg"
678
+ viewBox = "0 0 24 24"
679
+ fill = "none"
680
+ class = "stroke-white group-aria-expanded:-rotate-180 transition-transform duration-[450ms]"
681
+ stroke-linecap = "round"
682
+ stroke-width = "2"
683
+ stroke-linejoin = "round"
684
+ >
685
+ < polyline points = "6 9 12 15 18 9" > </ polyline >
686
+ </ svg >
687
+ </ ComboboxTrigger >
688
+ </ ComboboxControl >
689
+ < ComboboxPortal >
690
+ < ComboboxListbox
691
+ offset = { 8 }
692
+ shift = { true }
693
+ class = "w-44 bg-slate-900 px-4 py-2 rounded-sm border-slate-400 border-[1px]"
694
+ />
695
+ </ ComboboxPortal >
696
+ </ Combobox >
573
697
</ div >
574
698
</ div >
575
699
@@ -603,14 +727,14 @@ export const ContextExample = component$(() => {
603
727
< div class = "flex flex-col gap-4" q :slot = "actualComponent" >
604
728
< Combobox
605
729
options = { animals }
606
- renderOption$ = { ( resolved : ResolvedOption , index : number ) => (
730
+ renderOption$ = { ( option : ResolvedOption , index : number ) => (
607
731
< ComboboxOption
608
732
index = { index }
609
- resolved = { resolved }
733
+ resolved = { option }
610
734
class = "aria-disabled:text-slate-600 aria-disabled:hover:bg-slate-700 rounded-sm px-2 hover:bg-slate-500 aria-selected:bg-slate-500 text-white border-2 border-transparent aria-selected:border-slate-200 group"
611
735
>
612
736
< span class = "block group-aria-selected:translate-x-[3px] transition-transform duration-350" >
613
- { resolved . label }
737
+ < span > { option . label } </ span >
614
738
</ span >
615
739
</ ComboboxOption >
616
740
) }
0 commit comments