@sapudex/web-components 2.36.0 → 2.38.0
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.
- package/cypress/specs/List.cy.tsx +38 -0
- package/cypress/specs/Pagination.cy.tsx +52 -0
- package/cypress/specs/PasswordField.cy.tsx +36 -0
- package/cypress/specs/Search.cy.tsx +265 -0
- package/cypress/specs/SelectBox.cy.tsx +19 -1
- package/cypress/specs/TabNavigation.cy.tsx +314 -0
- package/cypress/specs/Table.cy.tsx +170 -0
- package/cypress/support/component-imports.instrumented.ts +2 -0
- package/cypress/support/component-imports.src.ts +2 -0
- package/dist/CountrySelector.d.ts +2 -0
- package/dist/CountrySelector.js +12 -3
- package/dist/CountrySelector.js.map +1 -1
- package/dist/CountrySelectorTemplate.d.ts +2 -0
- package/dist/CountrySelectorTemplate.js +8 -0
- package/dist/CountrySelectorTemplate.js.map +1 -0
- package/dist/FilterMenu.d.ts +3 -3
- package/dist/FilterMenu.js +8 -9
- package/dist/FilterMenu.js.map +1 -1
- package/dist/FilterMenuTemplate.d.ts +2 -0
- package/dist/FilterMenuTemplate.js +27 -0
- package/dist/FilterMenuTemplate.js.map +1 -0
- package/dist/List.d.ts +1 -0
- package/dist/List.js +4 -0
- package/dist/List.js.map +1 -1
- package/dist/Pagination.js +1 -0
- package/dist/Pagination.js.map +1 -1
- package/dist/PasswordField.d.ts +16 -0
- package/dist/PasswordField.js +40 -0
- package/dist/PasswordField.js.map +1 -1
- package/dist/PasswordFieldTemplate.js +1 -1
- package/dist/PasswordFieldTemplate.js.map +1 -1
- package/dist/Search.d.ts +1 -0
- package/dist/Search.js +6 -0
- package/dist/Search.js.map +1 -1
- package/dist/SearchableListBaseTemplate.d.ts +2 -0
- package/dist/SearchableListBaseTemplate.js +32 -0
- package/dist/SearchableListBaseTemplate.js.map +1 -0
- package/dist/SecondaryNavigation.d.ts +2 -0
- package/dist/SecondaryNavigation.js +20 -0
- package/dist/SecondaryNavigation.js.map +1 -1
- package/dist/SelectBase.d.ts +7 -6
- package/dist/SelectBase.js +2 -2
- package/dist/SelectBase.js.map +1 -1
- package/dist/SelectBox.d.ts +2 -0
- package/dist/SelectBox.js +12 -3
- package/dist/SelectBox.js.map +1 -1
- package/dist/SelectBoxTemplate.d.ts +2 -0
- package/dist/SelectBoxTemplate.js +27 -0
- package/dist/SelectBoxTemplate.js.map +1 -0
- package/dist/Tab.d.ts +9 -0
- package/dist/Tab.js +6 -0
- package/dist/Tab.js.map +1 -1
- package/dist/TabNavigation.js +32 -12
- package/dist/TabNavigation.js.map +1 -1
- package/dist/TableGroupRowTemplate.js +1 -1
- package/dist/TableGroupRowTemplate.js.map +1 -1
- package/dist/TableTemplate.js +1 -1
- package/dist/TableTemplate.js.map +1 -1
- package/dist/TagTemplate.js +2 -4
- package/dist/TagTemplate.js.map +1 -1
- package/dist/TextField.js +1 -0
- package/dist/TextField.js.map +1 -1
- package/dist/Wizard.d.ts +2 -2
- package/dist/Wizard.js +7 -7
- package/dist/Wizard.js.map +1 -1
- package/dist/assets/{InputSuggestions-BIR_sdOv.js → InputSuggestions-BQp20KJM.js} +1 -1
- package/dist/assets/{ListItemStandardExpandableTextTemplate-5xOuY0en.js → ListItemStandardExpandableTextTemplate-D0w0u6f7.js} +1 -1
- package/dist/assets/{bundle.esm-C8GwJvJr.js → bundle.esm-DIFG6k5I.js} +240 -240
- package/dist/assets/messagebundle_bg-4ainC3nj.js +1 -0
- package/dist/assets/messagebundle_cs-CFtmLavu.js +1 -0
- package/dist/assets/messagebundle_en-BxjFAY2S.js +1 -0
- package/dist/css/themes/MastheadMenu.css +1 -1
- package/dist/css/themes/MastheadMobileMenu.css +1 -1
- package/dist/css/themes/MediaPlayer.css +1 -1
- package/dist/css/themes/RatingBar.css +1 -1
- package/dist/css/themes/RatingIndicator.css +1 -1
- package/dist/css/themes/SecondaryNavigationSubItem.css +1 -1
- package/dist/css/themes/Slider.css +1 -1
- package/dist/css/themes/TabNavigation.css +1 -1
- package/dist/css/themes/TableGroupRow.css +1 -1
- package/dist/css/themes/Wizard.css +1 -1
- package/dist/css/themes/WizardTab.css +1 -1
- package/dist/custom-elements-internal.json +65 -0
- package/dist/custom-elements.json +49 -0
- package/dist/features/SearchSuggestionsPopover.d.ts +4 -0
- package/dist/features/SearchSuggestionsPopover.js +56 -3
- package/dist/features/SearchSuggestionsPopover.js.map +1 -1
- package/dist/generated/assets/i18n/messagebundle_bg.json +1 -1
- package/dist/generated/assets/i18n/messagebundle_cs.json +1 -1
- package/dist/generated/assets/i18n/messagebundle_en.json +1 -1
- package/dist/generated/i18n/i18n-defaults.d.ts +2 -3
- package/dist/generated/i18n/i18n-defaults.js +2 -3
- package/dist/generated/i18n/i18n-defaults.js.map +1 -1
- package/dist/generated/templates/ListTemplate.lit.js +1 -1
- package/dist/generated/templates/ListTemplate.lit.js.map +1 -1
- package/dist/generated/templates/TabHeaderTemplate.lit.js +4 -4
- package/dist/generated/templates/TabHeaderTemplate.lit.js.map +1 -1
- package/dist/generated/templates/TabInOverflowTemplate.lit.js +2 -2
- package/dist/generated/templates/TabInOverflowTemplate.lit.js.map +1 -1
- package/dist/generated/themes/MastheadMenu.css.d.ts +1 -1
- package/dist/generated/themes/MastheadMenu.css.js +1 -1
- package/dist/generated/themes/MastheadMenu.css.js.map +1 -1
- package/dist/generated/themes/MastheadMobileMenu.css.d.ts +1 -1
- package/dist/generated/themes/MastheadMobileMenu.css.js +1 -1
- package/dist/generated/themes/MastheadMobileMenu.css.js.map +1 -1
- package/dist/generated/themes/MediaPlayer.css.d.ts +1 -1
- package/dist/generated/themes/MediaPlayer.css.js +1 -1
- package/dist/generated/themes/MediaPlayer.css.js.map +1 -1
- package/dist/generated/themes/RatingBar.css.d.ts +1 -1
- package/dist/generated/themes/RatingBar.css.js +1 -1
- package/dist/generated/themes/RatingBar.css.js.map +1 -1
- package/dist/generated/themes/RatingIndicator.css.d.ts +1 -1
- package/dist/generated/themes/RatingIndicator.css.js +1 -1
- package/dist/generated/themes/RatingIndicator.css.js.map +1 -1
- package/dist/generated/themes/SecondaryNavigationSubItem.css.d.ts +1 -1
- package/dist/generated/themes/SecondaryNavigationSubItem.css.js +1 -1
- package/dist/generated/themes/SecondaryNavigationSubItem.css.js.map +1 -1
- package/dist/generated/themes/Slider.css.d.ts +1 -1
- package/dist/generated/themes/Slider.css.js +1 -1
- package/dist/generated/themes/Slider.css.js.map +1 -1
- package/dist/generated/themes/TabNavigation.css.d.ts +1 -1
- package/dist/generated/themes/TabNavigation.css.js +1 -1
- package/dist/generated/themes/TabNavigation.css.js.map +1 -1
- package/dist/generated/themes/TableGroupRow.css.d.ts +1 -1
- package/dist/generated/themes/TableGroupRow.css.js +1 -1
- package/dist/generated/themes/TableGroupRow.css.js.map +1 -1
- package/dist/generated/themes/Wizard.css.d.ts +1 -1
- package/dist/generated/themes/Wizard.css.js +1 -1
- package/dist/generated/themes/Wizard.css.js.map +1 -1
- package/dist/generated/themes/WizardTab.css.d.ts +1 -1
- package/dist/generated/themes/WizardTab.css.js +1 -1
- package/dist/generated/themes/WizardTab.css.js.map +1 -1
- package/dist/messagebundle.properties +1 -6
- package/dist/messagebundle_bg.properties +129 -2
- package/dist/messagebundle_cs.properties +126 -0
- package/dist/messagebundle_en.properties +3 -1
- package/dist/vscode.html-custom-data.json +6 -1
- package/dist/web-types.json +42 -4
- package/package.json +1 -1
- package/src/CountrySelector.ts +14 -3
- package/src/CountrySelectorTemplate.tsx +12 -0
- package/src/FilterMenu.ts +9 -10
- package/src/FilterMenuTemplate.tsx +104 -0
- package/src/List.hbs +1 -1
- package/src/List.ts +5 -0
- package/src/Pagination.ts +1 -0
- package/src/PasswordField.ts +55 -0
- package/src/PasswordFieldTemplate.tsx +3 -0
- package/src/Search.ts +7 -0
- package/src/SearchableListBaseTemplate.tsx +157 -0
- package/src/SecondaryNavigation.ts +20 -0
- package/src/SelectBase.ts +7 -6
- package/src/SelectBox.ts +14 -3
- package/src/SelectBoxTemplate.tsx +165 -0
- package/src/Tab.ts +14 -0
- package/src/TabHeader.hbs +6 -2
- package/src/TabInOverflow.hbs +2 -0
- package/src/TabNavigation.ts +34 -12
- package/src/TableGroupRowTemplate.tsx +26 -17
- package/src/TableTemplate.tsx +1 -1
- package/src/TagTemplate.tsx +2 -4
- package/src/TextField.ts +1 -0
- package/src/Wizard.ts +15 -14
- package/src/features/SearchSuggestionsPopover.ts +59 -3
- package/src/generated/i18n/i18n-defaults.ts +2 -2
- package/src/generated/templates/ListTemplate.lit.ts +1 -1
- package/src/generated/templates/TabHeaderTemplate.lit.ts +4 -4
- package/src/generated/templates/TabInOverflowTemplate.lit.ts +2 -2
- package/src/generated/themes/MastheadMenu.css.ts +1 -1
- package/src/generated/themes/MastheadMobileMenu.css.ts +1 -1
- package/src/generated/themes/MediaPlayer.css.ts +1 -1
- package/src/generated/themes/RatingBar.css.ts +1 -1
- package/src/generated/themes/RatingIndicator.css.ts +1 -1
- package/src/generated/themes/SecondaryNavigationSubItem.css.ts +1 -1
- package/src/generated/themes/Slider.css.ts +1 -1
- package/src/generated/themes/TabNavigation.css.ts +1 -1
- package/src/generated/themes/TableGroupRow.css.ts +1 -1
- package/src/generated/themes/Wizard.css.ts +1 -1
- package/src/generated/themes/WizardTab.css.ts +1 -1
- package/src/i18n/messagebundle.properties +1 -6
- package/src/i18n/messagebundle_bg.properties +129 -2
- package/src/i18n/messagebundle_cs.properties +126 -0
- package/src/i18n/messagebundle_en.properties +3 -1
- package/src/themes/MastheadMenu.css +4 -2
- package/src/themes/MastheadMobileMenu.css +4 -2
- package/src/themes/MediaPlayer.css +12 -0
- package/src/themes/RatingBar.css +14 -5
- package/src/themes/SecondaryNavigationSubItem.css +1 -0
- package/src/themes/TabNavigation.css +6 -0
- package/src/themes/TableGroupRow.css +5 -0
- package/src/themes/Wizard.css +19 -15
- package/src/themes/WizardTab.css +43 -28
- package/dist/assets/messagebundle_bg-4X593TQq.js +0 -1
- package/dist/assets/messagebundle_cs-Bt8XtMib.js +0 -1
- package/dist/assets/messagebundle_en-iNqRB1VZ.js +0 -1
- package/dist/generated/templates/CountrySelectorTemplate.lit.d.ts +0 -3
- package/dist/generated/templates/CountrySelectorTemplate.lit.js +0 -8
- package/dist/generated/templates/CountrySelectorTemplate.lit.js.map +0 -1
- package/dist/generated/templates/FilterMenuTemplate.lit.d.ts +0 -3
- package/dist/generated/templates/FilterMenuTemplate.lit.js +0 -13
- package/dist/generated/templates/FilterMenuTemplate.lit.js.map +0 -1
- package/dist/generated/templates/SearchableListBaseTemplate.lit.d.ts +0 -3
- package/dist/generated/templates/SearchableListBaseTemplate.lit.js +0 -19
- package/dist/generated/templates/SearchableListBaseTemplate.lit.js.map +0 -1
- package/dist/generated/templates/SelectBoxTemplate.lit.d.ts +0 -3
- package/dist/generated/templates/SelectBoxTemplate.lit.js +0 -20
- package/dist/generated/templates/SelectBoxTemplate.lit.js.map +0 -1
- package/src/CountrySelector.hbs +0 -6
- package/src/FilterMenu.hbs +0 -88
- package/src/SearchableListBase.hbs +0 -148
- package/src/SelectBox.hbs +0 -138
- package/src/generated/templates/CountrySelectorTemplate.lit.ts +0 -12
- package/src/generated/templates/FilterMenuTemplate.lit.ts +0 -17
- package/src/generated/templates/SearchableListBaseTemplate.lit.ts +0 -23
- package/src/generated/templates/SelectBoxTemplate.lit.ts +0 -24
|
@@ -1613,6 +1613,320 @@ describe("Tab Navigation component", () => {
|
|
|
1613
1613
|
});
|
|
1614
1614
|
});
|
|
1615
1615
|
|
|
1616
|
+
// ── Disabled tab behaviour ──────────────────────────────────────────────────
|
|
1617
|
+
|
|
1618
|
+
describe("Disabled tab", () => {
|
|
1619
|
+
describe("Rendering", () => {
|
|
1620
|
+
it("renders aria-disabled='true' on a disabled tab button", () => {
|
|
1621
|
+
cy.mount(
|
|
1622
|
+
<UDExTabNavigation>
|
|
1623
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1624
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1625
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1626
|
+
</UDExTabNavigation>
|
|
1627
|
+
);
|
|
1628
|
+
|
|
1629
|
+
cy.get("[udex-tab-navigation]")
|
|
1630
|
+
.shadow()
|
|
1631
|
+
.find("button[role='tab']")
|
|
1632
|
+
.eq(1)
|
|
1633
|
+
.should("have.attr", "aria-disabled", "true");
|
|
1634
|
+
});
|
|
1635
|
+
|
|
1636
|
+
it("does not set native disabled attribute — tab remains in DOM for assistive technology", () => {
|
|
1637
|
+
cy.mount(
|
|
1638
|
+
<UDExTabNavigation>
|
|
1639
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1640
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1641
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1642
|
+
</UDExTabNavigation>
|
|
1643
|
+
);
|
|
1644
|
+
|
|
1645
|
+
cy.get("[udex-tab-navigation]")
|
|
1646
|
+
.shadow()
|
|
1647
|
+
.find("button[role='tab']")
|
|
1648
|
+
.eq(1)
|
|
1649
|
+
.should("not.have.attr", "disabled");
|
|
1650
|
+
});
|
|
1651
|
+
|
|
1652
|
+
it("applies disabled opacity style to the disabled tab button", () => {
|
|
1653
|
+
cy.mount(
|
|
1654
|
+
<UDExTabNavigation>
|
|
1655
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1656
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1657
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1658
|
+
</UDExTabNavigation>
|
|
1659
|
+
);
|
|
1660
|
+
|
|
1661
|
+
cy.get("[udex-tab-navigation]")
|
|
1662
|
+
.shadow()
|
|
1663
|
+
.find("button[role='tab'][aria-disabled='true']")
|
|
1664
|
+
.should("have.css", "opacity", "0.4");
|
|
1665
|
+
});
|
|
1666
|
+
|
|
1667
|
+
it("does not apply aria-disabled on enabled tabs", () => {
|
|
1668
|
+
cy.mount(
|
|
1669
|
+
<UDExTabNavigation>
|
|
1670
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1671
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1672
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1673
|
+
</UDExTabNavigation>
|
|
1674
|
+
);
|
|
1675
|
+
|
|
1676
|
+
cy.get("[udex-tab-navigation]")
|
|
1677
|
+
.shadow()
|
|
1678
|
+
.find("button[role='tab']")
|
|
1679
|
+
.eq(0)
|
|
1680
|
+
.should("not.have.attr", "aria-disabled");
|
|
1681
|
+
|
|
1682
|
+
cy.get("[udex-tab-navigation]")
|
|
1683
|
+
.shadow()
|
|
1684
|
+
.find("button[role='tab']")
|
|
1685
|
+
.eq(2)
|
|
1686
|
+
.should("not.have.attr", "aria-disabled");
|
|
1687
|
+
});
|
|
1688
|
+
});
|
|
1689
|
+
|
|
1690
|
+
describe("Interaction", () => {
|
|
1691
|
+
it("does not change the selected tab when a disabled tab is clicked", () => {
|
|
1692
|
+
cy.mount(
|
|
1693
|
+
<UDExTabNavigation>
|
|
1694
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1695
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1696
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1697
|
+
</UDExTabNavigation>
|
|
1698
|
+
);
|
|
1699
|
+
|
|
1700
|
+
// Force click because pointer-events: none prevents normal click
|
|
1701
|
+
cy.get("[udex-tab-navigation]")
|
|
1702
|
+
.shadow()
|
|
1703
|
+
.find("button[role='tab']")
|
|
1704
|
+
.eq(1)
|
|
1705
|
+
.click({ force: true });
|
|
1706
|
+
|
|
1707
|
+
// Tab 1 should remain selected
|
|
1708
|
+
cy.get("[udex-tab-navigation]")
|
|
1709
|
+
.shadow()
|
|
1710
|
+
.find("button[role='tab'][aria-selected='true']")
|
|
1711
|
+
.should("contain.text", "Tab 1");
|
|
1712
|
+
|
|
1713
|
+
// Tab 2 should NOT be selected
|
|
1714
|
+
cy.get("[udex-tab-navigation]")
|
|
1715
|
+
.shadow()
|
|
1716
|
+
.find("button[role='tab']")
|
|
1717
|
+
.eq(1)
|
|
1718
|
+
.should("have.attr", "aria-selected", "false");
|
|
1719
|
+
});
|
|
1720
|
+
|
|
1721
|
+
it("does not fire tab-select event when a disabled tab is clicked", () => {
|
|
1722
|
+
const tabSelectHandler = cy.stub().as("tabSelect");
|
|
1723
|
+
|
|
1724
|
+
cy.mount(
|
|
1725
|
+
<UDExTabNavigation onTabSelect={tabSelectHandler}>
|
|
1726
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1727
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1728
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1729
|
+
</UDExTabNavigation>
|
|
1730
|
+
);
|
|
1731
|
+
|
|
1732
|
+
cy.get("[udex-tab-navigation]")
|
|
1733
|
+
.shadow()
|
|
1734
|
+
.find("button[role='tab']")
|
|
1735
|
+
.eq(1)
|
|
1736
|
+
.click({ force: true });
|
|
1737
|
+
|
|
1738
|
+
cy.get("@tabSelect").should("not.have.been.called");
|
|
1739
|
+
});
|
|
1740
|
+
});
|
|
1741
|
+
|
|
1742
|
+
describe("Keyboard navigation", () => {
|
|
1743
|
+
it("disabled tab has tabindex='-1' even when it would otherwise be the roving-tabindex target", () => {
|
|
1744
|
+
cy.mount(
|
|
1745
|
+
<UDExTabNavigation>
|
|
1746
|
+
<UDExTab text="Tab 1" disabled selected><div>Content 1</div></UDExTab>
|
|
1747
|
+
<UDExTab text="Tab 2"><div>Content 2</div></UDExTab>
|
|
1748
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1749
|
+
</UDExTabNavigation>
|
|
1750
|
+
);
|
|
1751
|
+
|
|
1752
|
+
// The disabled tab should always have tabindex -1
|
|
1753
|
+
cy.get("[udex-tab-navigation]")
|
|
1754
|
+
.shadow()
|
|
1755
|
+
.find("button[role='tab'][aria-disabled='true']")
|
|
1756
|
+
.should("have.attr", "tabindex", "-1");
|
|
1757
|
+
});
|
|
1758
|
+
|
|
1759
|
+
it("arrow-key navigation skips disabled tab (ArrowRight)", () => {
|
|
1760
|
+
cy.mount(
|
|
1761
|
+
<UDExTabNavigation>
|
|
1762
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1763
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1764
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1765
|
+
</UDExTabNavigation>
|
|
1766
|
+
);
|
|
1767
|
+
|
|
1768
|
+
// Focus Tab 1 and press ArrowRight — should skip Tab 2 (disabled) and land on Tab 3
|
|
1769
|
+
cy.get("[udex-tab-navigation]")
|
|
1770
|
+
.shadow()
|
|
1771
|
+
.find("button[role='tab']")
|
|
1772
|
+
.eq(0)
|
|
1773
|
+
.focus()
|
|
1774
|
+
.realPress("ArrowRight");
|
|
1775
|
+
|
|
1776
|
+
cy.get("[udex-tab-navigation]")
|
|
1777
|
+
.shadow()
|
|
1778
|
+
.find("button[role='tab']")
|
|
1779
|
+
.eq(2)
|
|
1780
|
+
.should("be.focused");
|
|
1781
|
+
});
|
|
1782
|
+
|
|
1783
|
+
it("arrow-key navigation skips disabled tab (ArrowLeft)", () => {
|
|
1784
|
+
cy.mount(
|
|
1785
|
+
<UDExTabNavigation>
|
|
1786
|
+
<UDExTab text="Tab 1"><div>Content 1</div></UDExTab>
|
|
1787
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1788
|
+
<UDExTab text="Tab 3" selected><div>Content 3</div></UDExTab>
|
|
1789
|
+
</UDExTabNavigation>
|
|
1790
|
+
);
|
|
1791
|
+
|
|
1792
|
+
// Focus Tab 3 and press ArrowLeft — should skip Tab 2 (disabled) and land on Tab 1
|
|
1793
|
+
cy.get("[udex-tab-navigation]")
|
|
1794
|
+
.shadow()
|
|
1795
|
+
.find("button[role='tab']")
|
|
1796
|
+
.eq(2)
|
|
1797
|
+
.focus()
|
|
1798
|
+
.realPress("ArrowLeft");
|
|
1799
|
+
|
|
1800
|
+
cy.get("[udex-tab-navigation]")
|
|
1801
|
+
.shadow()
|
|
1802
|
+
.find("button[role='tab']")
|
|
1803
|
+
.eq(0)
|
|
1804
|
+
.should("be.focused");
|
|
1805
|
+
});
|
|
1806
|
+
|
|
1807
|
+
it("arrow-key navigation skips multiple consecutive disabled tabs", () => {
|
|
1808
|
+
cy.mount(
|
|
1809
|
+
<UDExTabNavigation>
|
|
1810
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1811
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1812
|
+
<UDExTab text="Tab 3" disabled><div>Content 3</div></UDExTab>
|
|
1813
|
+
<UDExTab text="Tab 4"><div>Content 4</div></UDExTab>
|
|
1814
|
+
</UDExTabNavigation>
|
|
1815
|
+
);
|
|
1816
|
+
|
|
1817
|
+
cy.get("[udex-tab-navigation]")
|
|
1818
|
+
.shadow()
|
|
1819
|
+
.find("button[role='tab']")
|
|
1820
|
+
.eq(0)
|
|
1821
|
+
.focus()
|
|
1822
|
+
.realPress("ArrowRight");
|
|
1823
|
+
|
|
1824
|
+
cy.get("[udex-tab-navigation]")
|
|
1825
|
+
.shadow()
|
|
1826
|
+
.find("button[role='tab']")
|
|
1827
|
+
.eq(3)
|
|
1828
|
+
.should("be.focused");
|
|
1829
|
+
});
|
|
1830
|
+
|
|
1831
|
+
it("arrow-key navigation skips disabled tabs in vertical mode (ArrowDown)", () => {
|
|
1832
|
+
cy.mount(
|
|
1833
|
+
<UDExTabNavigation orientation="Vertical">
|
|
1834
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1835
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1836
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1837
|
+
</UDExTabNavigation>
|
|
1838
|
+
);
|
|
1839
|
+
|
|
1840
|
+
cy.get("[udex-tab-navigation]")
|
|
1841
|
+
.shadow()
|
|
1842
|
+
.find("button[role='tab']")
|
|
1843
|
+
.eq(0)
|
|
1844
|
+
.focus()
|
|
1845
|
+
.realPress("ArrowDown");
|
|
1846
|
+
|
|
1847
|
+
cy.get("[udex-tab-navigation]")
|
|
1848
|
+
.shadow()
|
|
1849
|
+
.find("button[role='tab']")
|
|
1850
|
+
.eq(2)
|
|
1851
|
+
.should("be.focused");
|
|
1852
|
+
});
|
|
1853
|
+
});
|
|
1854
|
+
|
|
1855
|
+
describe("Default selection", () => {
|
|
1856
|
+
it("selects the first non-disabled tab when the first tab is disabled and none are explicitly selected", () => {
|
|
1857
|
+
cy.mount(
|
|
1858
|
+
<UDExTabNavigation>
|
|
1859
|
+
<UDExTab text="Tab 1" disabled><div>Content 1</div></UDExTab>
|
|
1860
|
+
<UDExTab text="Tab 2"><div>Content 2</div></UDExTab>
|
|
1861
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1862
|
+
</UDExTabNavigation>
|
|
1863
|
+
);
|
|
1864
|
+
|
|
1865
|
+
cy.get("[udex-tab-navigation]")
|
|
1866
|
+
.shadow()
|
|
1867
|
+
.find("button[role='tab'][aria-selected='true']")
|
|
1868
|
+
.should("contain.text", "Tab 2");
|
|
1869
|
+
});
|
|
1870
|
+
|
|
1871
|
+
it("selects the first non-disabled tab when multiple leading tabs are disabled", () => {
|
|
1872
|
+
cy.mount(
|
|
1873
|
+
<UDExTabNavigation>
|
|
1874
|
+
<UDExTab text="Tab 1" disabled><div>Content 1</div></UDExTab>
|
|
1875
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1876
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1877
|
+
<UDExTab text="Tab 4"><div>Content 4</div></UDExTab>
|
|
1878
|
+
</UDExTabNavigation>
|
|
1879
|
+
);
|
|
1880
|
+
|
|
1881
|
+
cy.get("[udex-tab-navigation]")
|
|
1882
|
+
.shadow()
|
|
1883
|
+
.find("button[role='tab'][aria-selected='true']")
|
|
1884
|
+
.should("contain.text", "Tab 3");
|
|
1885
|
+
});
|
|
1886
|
+
|
|
1887
|
+
it("ignores selected attribute on a disabled tab and falls back to first enabled tab", () => {
|
|
1888
|
+
cy.mount(
|
|
1889
|
+
<UDExTabNavigation>
|
|
1890
|
+
<UDExTab text="Tab 1" disabled selected><div>Content 1</div></UDExTab>
|
|
1891
|
+
<UDExTab text="Tab 2"><div>Content 2</div></UDExTab>
|
|
1892
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1893
|
+
</UDExTabNavigation>
|
|
1894
|
+
);
|
|
1895
|
+
|
|
1896
|
+
// The disabled tab cannot be selected, so the first enabled tab is chosen
|
|
1897
|
+
cy.get("[udex-tab-navigation]")
|
|
1898
|
+
.shadow()
|
|
1899
|
+
.find("button[role='tab'][aria-selected='true']")
|
|
1900
|
+
.should("contain.text", "Tab 2");
|
|
1901
|
+
});
|
|
1902
|
+
});
|
|
1903
|
+
|
|
1904
|
+
describe("Auto-play skips disabled tabs", () => {
|
|
1905
|
+
it("auto-play advances past disabled tabs", () => {
|
|
1906
|
+
cy.clock(0, ["setInterval", "clearInterval"]);
|
|
1907
|
+
cy.mount(
|
|
1908
|
+
<UDExTabNavigation
|
|
1909
|
+
orientation="Vertical"
|
|
1910
|
+
autoPlay
|
|
1911
|
+
autoPlayInterval={1000}
|
|
1912
|
+
>
|
|
1913
|
+
<UDExTab text="Tab 1" selected><div>Content 1</div></UDExTab>
|
|
1914
|
+
<UDExTab text="Tab 2" disabled><div>Content 2</div></UDExTab>
|
|
1915
|
+
<UDExTab text="Tab 3"><div>Content 3</div></UDExTab>
|
|
1916
|
+
</UDExTabNavigation>
|
|
1917
|
+
);
|
|
1918
|
+
|
|
1919
|
+
// After 1 tick, auto-play should skip disabled Tab 2 and select Tab 3
|
|
1920
|
+
cy.tick(1000);
|
|
1921
|
+
|
|
1922
|
+
cy.get("[udex-tab-navigation]")
|
|
1923
|
+
.shadow()
|
|
1924
|
+
.find("button[role='tab'][aria-selected='true']")
|
|
1925
|
+
.should("contain.text", "Tab 3");
|
|
1926
|
+
});
|
|
1927
|
+
});
|
|
1928
|
+
});
|
|
1929
|
+
|
|
1616
1930
|
// ── Process Tab variant ──────────────────────────────────────────────────────
|
|
1617
1931
|
|
|
1618
1932
|
describe("TabNavigation - Process Tab variant", () => {
|
|
@@ -269,6 +269,10 @@ describe("Table", () => {
|
|
|
269
269
|
cy.get("#table").shadow().find(".udex-table").should("have.attr", "aria-label", "table devices")
|
|
270
270
|
});
|
|
271
271
|
|
|
272
|
+
it("header holder has role presentation to be transparent in the ARIA tree", () => {
|
|
273
|
+
cy.get("#table").shadow().find(".udex-table__header-holder").should("have.attr", "role", "presentation");
|
|
274
|
+
});
|
|
275
|
+
|
|
272
276
|
it("renders the right amount of header rows", () => {
|
|
273
277
|
cy.get("#table").find("udex-table-header-row").should("have.length", 1)
|
|
274
278
|
});
|
|
@@ -357,3 +361,169 @@ describe("Table", () => {
|
|
|
357
361
|
})
|
|
358
362
|
});
|
|
359
363
|
});
|
|
364
|
+
|
|
365
|
+
const multipleGroupRowsTable = <UDExTable id="table-multi-group">
|
|
366
|
+
<UDExTableHeaderRow slot="headerRow">
|
|
367
|
+
<UDExTableHeaderCell>Product</UDExTableHeaderCell>
|
|
368
|
+
<UDExTableHeaderCell>Price</UDExTableHeaderCell>
|
|
369
|
+
</UDExTableHeaderRow>
|
|
370
|
+
<UDExTableGroupRow id="group-row-1" group-title="Group A" collapsible>
|
|
371
|
+
<UDExTableRow>
|
|
372
|
+
<UDExTableCell>Item A1</UDExTableCell>
|
|
373
|
+
<UDExTableCell>$100</UDExTableCell>
|
|
374
|
+
</UDExTableRow>
|
|
375
|
+
</UDExTableGroupRow>
|
|
376
|
+
<UDExTableGroupRow id="group-row-2" group-title="Group B" collapsible>
|
|
377
|
+
<UDExTableRow>
|
|
378
|
+
<UDExTableCell>Item B1</UDExTableCell>
|
|
379
|
+
<UDExTableCell>$200</UDExTableCell>
|
|
380
|
+
</UDExTableRow>
|
|
381
|
+
</UDExTableGroupRow>
|
|
382
|
+
<UDExTableGroupRow id="group-row-3" group-title="Group C" collapsible>
|
|
383
|
+
<UDExTableRow>
|
|
384
|
+
<UDExTableCell>Item C1</UDExTableCell>
|
|
385
|
+
<UDExTableCell>$300</UDExTableCell>
|
|
386
|
+
</UDExTableRow>
|
|
387
|
+
</UDExTableGroupRow>
|
|
388
|
+
</UDExTable>;
|
|
389
|
+
|
|
390
|
+
describe("TableGroupRow Accessibility", () => {
|
|
391
|
+
beforeEach(() => {
|
|
392
|
+
cy.mount(multipleGroupRowsTable);
|
|
393
|
+
});
|
|
394
|
+
|
|
395
|
+
it("generates unique button IDs for each collapsible group row", () => {
|
|
396
|
+
const ids: string[] = [];
|
|
397
|
+
|
|
398
|
+
cy.get("[udex-table-group-row]").each($groupRow => {
|
|
399
|
+
cy.wrap($groupRow).shadow().find(".udex-table-grow-btn").invoke("attr", "id").then(id => {
|
|
400
|
+
expect(id).to.match(/^udex-table-group-opener-/);
|
|
401
|
+
ids.push(id as string);
|
|
402
|
+
});
|
|
403
|
+
}).then(() => {
|
|
404
|
+
const uniqueIds = new Set(ids);
|
|
405
|
+
expect(uniqueIds.size).to.equal(ids.length, "All group row button IDs must be unique");
|
|
406
|
+
});
|
|
407
|
+
});
|
|
408
|
+
|
|
409
|
+
it("button aria-controls references an existing element in the shadow DOM", () => {
|
|
410
|
+
cy.get("#group-row-1").shadow().find(".udex-table-grow-btn").then($btn => {
|
|
411
|
+
const controlsId = $btn.attr("aria-controls");
|
|
412
|
+
expect(controlsId).to.match(/^udex-table-group-rows-/);
|
|
413
|
+
cy.get("#group-row-1").shadow().find(`#${controlsId}`).should("exist").and("have.class", "udex-table-grow-rows");
|
|
414
|
+
});
|
|
415
|
+
});
|
|
416
|
+
|
|
417
|
+
it("button aria-controls value matches the rows container ID on the same instance", () => {
|
|
418
|
+
cy.get("[udex-table-group-row]").each($groupRow => {
|
|
419
|
+
cy.wrap($groupRow).shadow().find(".udex-table-grow-btn").invoke("attr", "aria-controls").then(controlsValue => {
|
|
420
|
+
cy.wrap($groupRow).shadow().find(".udex-table-grow-rows").invoke("attr", "id").should("equal", controlsValue);
|
|
421
|
+
});
|
|
422
|
+
});
|
|
423
|
+
});
|
|
424
|
+
|
|
425
|
+
it("each rows container has a unique ID matching its group row instance", () => {
|
|
426
|
+
const containerIds: string[] = [];
|
|
427
|
+
|
|
428
|
+
cy.get("[udex-table-group-row]").each($groupRow => {
|
|
429
|
+
cy.wrap($groupRow).shadow().find(".udex-table-grow-rows").invoke("attr", "id").then(id => {
|
|
430
|
+
expect(id).to.match(/^udex-table-group-rows-/);
|
|
431
|
+
containerIds.push(id as string);
|
|
432
|
+
});
|
|
433
|
+
}).then(() => {
|
|
434
|
+
const uniqueIds = new Set(containerIds);
|
|
435
|
+
expect(uniqueIds.size).to.equal(containerIds.length, "All rows container IDs must be unique");
|
|
436
|
+
});
|
|
437
|
+
});
|
|
438
|
+
});
|
|
439
|
+
|
|
440
|
+
const nonCollapsibleGroupRowTable = <UDExTable id="table-non-collapsible-group">
|
|
441
|
+
<UDExTableHeaderRow slot="headerRow">
|
|
442
|
+
<UDExTableHeaderCell>Product</UDExTableHeaderCell>
|
|
443
|
+
<UDExTableHeaderCell>Price</UDExTableHeaderCell>
|
|
444
|
+
</UDExTableHeaderRow>
|
|
445
|
+
<UDExTableGroupRow id="non-collapsible-group" group-title="Static Group">
|
|
446
|
+
<UDExTableRow>
|
|
447
|
+
<UDExTableCell>Item 1</UDExTableCell>
|
|
448
|
+
<UDExTableCell>$50</UDExTableCell>
|
|
449
|
+
</UDExTableRow>
|
|
450
|
+
</UDExTableGroupRow>
|
|
451
|
+
</UDExTable>;
|
|
452
|
+
|
|
453
|
+
describe("TableGroupRow ARIA Structure", () => {
|
|
454
|
+
describe("Collapsible group row", () => {
|
|
455
|
+
beforeEach(() => {
|
|
456
|
+
cy.mount(multipleGroupRowsTable);
|
|
457
|
+
});
|
|
458
|
+
|
|
459
|
+
it("contains a div with role='row' and class 'udex-table-group-header-row'", () => {
|
|
460
|
+
cy.get("#group-row-1").shadow().find("div[role='row']")
|
|
461
|
+
.should("exist")
|
|
462
|
+
.and("have.class", "udex-table-group-header-row");
|
|
463
|
+
});
|
|
464
|
+
|
|
465
|
+
it("the row wrapper contains a div with role='rowheader'", () => {
|
|
466
|
+
cy.get("#group-row-1").shadow().find("div[role='row'] > div[role='rowheader']")
|
|
467
|
+
.should("exist")
|
|
468
|
+
.and("have.class", "udex-table-group-header-cell");
|
|
469
|
+
});
|
|
470
|
+
|
|
471
|
+
it("the rowheader contains the button with class 'udex-table-grow-btn'", () => {
|
|
472
|
+
cy.get("#group-row-1").shadow().find("div[role='rowheader'] > button.udex-table-grow-btn")
|
|
473
|
+
.should("exist");
|
|
474
|
+
});
|
|
475
|
+
|
|
476
|
+
it("the row and rowheader wrappers have display:contents", () => {
|
|
477
|
+
cy.get("#group-row-1").shadow().find(".udex-table-group-header-row").then($row => {
|
|
478
|
+
expect(window.getComputedStyle($row[0]).display).to.equal("contents");
|
|
479
|
+
});
|
|
480
|
+
cy.get("#group-row-1").shadow().find(".udex-table-group-header-cell").then($cell => {
|
|
481
|
+
expect(window.getComputedStyle($cell[0]).display).to.equal("contents");
|
|
482
|
+
});
|
|
483
|
+
});
|
|
484
|
+
|
|
485
|
+
it("all collapsible group rows have the row > rowheader > button structure", () => {
|
|
486
|
+
cy.get("[udex-table-group-row]").each($groupRow => {
|
|
487
|
+
cy.wrap($groupRow).shadow().find("div[role='row'] > div[role='rowheader'] > button.udex-table-grow-btn")
|
|
488
|
+
.should("exist");
|
|
489
|
+
});
|
|
490
|
+
});
|
|
491
|
+
});
|
|
492
|
+
|
|
493
|
+
describe("Non-collapsible group row", () => {
|
|
494
|
+
beforeEach(() => {
|
|
495
|
+
cy.mount(nonCollapsibleGroupRowTable);
|
|
496
|
+
});
|
|
497
|
+
|
|
498
|
+
it("contains a div with role='row' and class 'udex-table-group-header-row'", () => {
|
|
499
|
+
cy.get("#non-collapsible-group").shadow().find("div[role='row']")
|
|
500
|
+
.should("exist")
|
|
501
|
+
.and("have.class", "udex-table-group-header-row");
|
|
502
|
+
});
|
|
503
|
+
|
|
504
|
+
it("the row wrapper contains a div with role='rowheader'", () => {
|
|
505
|
+
cy.get("#non-collapsible-group").shadow().find("div[role='row'] > div[role='rowheader']")
|
|
506
|
+
.should("exist")
|
|
507
|
+
.and("have.class", "udex-table-group-header-cell");
|
|
508
|
+
});
|
|
509
|
+
|
|
510
|
+
it("the rowheader contains a div (not button) with class 'udex-table-grow-btn'", () => {
|
|
511
|
+
cy.get("#non-collapsible-group").shadow().find("div[role='rowheader'] > div.udex-table-grow-btn")
|
|
512
|
+
.should("exist");
|
|
513
|
+
});
|
|
514
|
+
|
|
515
|
+
it("the non-collapsible title div displays the group title", () => {
|
|
516
|
+
cy.get("#non-collapsible-group").shadow().find("div[role='rowheader'] .udex-table-grow-btn")
|
|
517
|
+
.should("have.text", "Static Group");
|
|
518
|
+
});
|
|
519
|
+
|
|
520
|
+
it("the row and rowheader wrappers have display:contents", () => {
|
|
521
|
+
cy.get("#non-collapsible-group").shadow().find(".udex-table-group-header-row").then($row => {
|
|
522
|
+
expect(window.getComputedStyle($row[0]).display).to.equal("contents");
|
|
523
|
+
});
|
|
524
|
+
cy.get("#non-collapsible-group").shadow().find(".udex-table-group-header-cell").then($cell => {
|
|
525
|
+
expect(window.getComputedStyle($cell[0]).display).to.equal("contents");
|
|
526
|
+
});
|
|
527
|
+
});
|
|
528
|
+
});
|
|
529
|
+
});
|
|
@@ -43,6 +43,7 @@ import UDExMessageStrip from "../../instrumented/MessageStrip.js";
|
|
|
43
43
|
import UDExModal from "../../instrumented/Modal.js";
|
|
44
44
|
import UDExSearch from "../../instrumented/Search.js";
|
|
45
45
|
import UDExMediaPlayer from "../../instrumented/MediaPlayer.js";
|
|
46
|
+
import UDExPagination from "../../instrumented/Pagination.js";
|
|
46
47
|
import UDExPasswordField from "../../instrumented/PasswordField.js";
|
|
47
48
|
import UDExPhoneNumberField from "../../instrumented/PhoneNumberField.js";
|
|
48
49
|
import UDExPromoTile from "../../instrumented/PromoTile.js";
|
|
@@ -128,6 +129,7 @@ export {
|
|
|
128
129
|
UDExModal,
|
|
129
130
|
UDExMediaPlayer,
|
|
130
131
|
UDExSearch,
|
|
132
|
+
UDExPagination,
|
|
131
133
|
UDExPasswordField,
|
|
132
134
|
UDExPhoneNumberField,
|
|
133
135
|
UDExPromoTile,
|
|
@@ -43,6 +43,7 @@ import UDExMessageStrip from "../../src/MessageStrip.js";
|
|
|
43
43
|
import UDExModal from "../../src/Modal.js";
|
|
44
44
|
import UDExSearch from "../../src/Search.js";
|
|
45
45
|
import UDExMediaPlayer from "../../src/MediaPlayer.js";
|
|
46
|
+
import UDExPagination from "../../src/Pagination.js";
|
|
46
47
|
import UDExPasswordField from "../../src/PasswordField.js";
|
|
47
48
|
import UDExPhoneNumberField from "../../src/PhoneNumberField.js";
|
|
48
49
|
import UDExPromoTile from "../../src/PromoTile.js";
|
|
@@ -128,6 +129,7 @@ export {
|
|
|
128
129
|
UDExModal,
|
|
129
130
|
UDExMediaPlayer,
|
|
130
131
|
UDExSearch,
|
|
132
|
+
UDExPagination,
|
|
131
133
|
UDExPasswordField,
|
|
132
134
|
UDExPhoneNumberField,
|
|
133
135
|
UDExPromoTile,
|
|
@@ -71,6 +71,8 @@ declare class UDExCountrySelector extends UDExSelectBase {
|
|
|
71
71
|
prepareCountrySelectorItems(): void;
|
|
72
72
|
getItemTemplate(country: Country): string | undefined;
|
|
73
73
|
getCountryLabel(countryName?: string, localName?: string): string | null;
|
|
74
|
+
get countryFlag(): object;
|
|
75
|
+
get searchableList(): import("@ui5/webcomponents-base").JSX.Element;
|
|
74
76
|
get selectedCountryName(): string | null;
|
|
75
77
|
get flagAriaLabel(): string;
|
|
76
78
|
get selectedCountryFlagX(): string | undefined;
|
package/dist/CountrySelector.js
CHANGED
|
@@ -5,7 +5,7 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
|
|
|
5
5
|
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
6
|
};
|
|
7
7
|
import customElement from "@ui5/webcomponents-base/dist/decorators/customElement.js";
|
|
8
|
-
import
|
|
8
|
+
import jsxRenderer from "@ui5/webcomponents-base/dist/renderer/JsxRenderer.js";
|
|
9
9
|
import property from "@ui5/webcomponents-base/dist/decorators/property.js";
|
|
10
10
|
import UI5Button from "@ui5/webcomponents/dist/Button.js";
|
|
11
11
|
import "@ui5/webcomponents-icons/dist/navigation-down-arrow.js";
|
|
@@ -20,7 +20,9 @@ import UDExSelectBase from "./SelectBase.js";
|
|
|
20
20
|
import UDExListItem from "./ListItem.js";
|
|
21
21
|
import UDExTextField from "./TextField.js";
|
|
22
22
|
import UDExStatusMessage from "./StatusMessage.js";
|
|
23
|
-
import SelectBoxTemplate from "./
|
|
23
|
+
import SelectBoxTemplate from "./SelectBoxTemplate.js";
|
|
24
|
+
import CountrySelectorTemplate from "./CountrySelectorTemplate.js";
|
|
25
|
+
import SearchableListBaseTemplate from "./SearchableListBaseTemplate.js";
|
|
24
26
|
// Styles
|
|
25
27
|
import CountrySelectorCss from "./generated/themes/CountrySelector.css.js";
|
|
26
28
|
import TextFieldCss from "./generated/themes/TextField.css.js";
|
|
@@ -143,6 +145,13 @@ let UDExCountrySelector = class UDExCountrySelector extends UDExSelectBase {
|
|
|
143
145
|
getCountryLabel(countryName, localName) {
|
|
144
146
|
return localName ? `${countryName} (${localName})` : countryName || null;
|
|
145
147
|
}
|
|
148
|
+
get countryFlag() {
|
|
149
|
+
return CountrySelectorTemplate.call(this);
|
|
150
|
+
}
|
|
151
|
+
get searchableList() {
|
|
152
|
+
this.defaultAccessibleRole = this._listBoxRole;
|
|
153
|
+
return SearchableListBaseTemplate.call(this);
|
|
154
|
+
}
|
|
146
155
|
get selectedCountryName() {
|
|
147
156
|
return this._selectedCountry ? this.getCountryLabel(this._selectedCountry.countryName, this._selectedCountry.localName) : "";
|
|
148
157
|
}
|
|
@@ -174,7 +183,7 @@ __decorate([
|
|
|
174
183
|
UDExCountrySelector = __decorate([
|
|
175
184
|
customElement({
|
|
176
185
|
tag: "udex-country-selector",
|
|
177
|
-
renderer:
|
|
186
|
+
renderer: jsxRenderer,
|
|
178
187
|
styles: [
|
|
179
188
|
TextFieldCss,
|
|
180
189
|
SelectBaseCss,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CountrySelector.js","sourceRoot":"","sources":["../src/CountrySelector.ts"],"names":[],"mappings":"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","sourcesContent":["import customElement from \"@ui5/webcomponents-base/dist/decorators/customElement.js\";\nimport litRender from \"@ui5/webcomponents-base/dist/renderer/LitRenderer.js\";\nimport property from \"@ui5/webcomponents-base/dist/decorators/property.js\";\nimport UI5Button from \"@ui5/webcomponents/dist/Button.js\";\nimport \"@ui5/webcomponents-icons/dist/navigation-down-arrow.js\";\nimport \"@ui5/webcomponents-icons/dist/navigation-up-arrow.js\";\nimport type { Country } from \"./data/CountryListISO3166.js\";\nimport { CountryListDB } from \"./data/CountryListISO3166.js\";\nimport IllustratedMessage from \"@ui5/webcomponents-fiori/dist/IllustratedMessage.js\";\nimport \"@ui5/webcomponents-fiori/dist/illustrations/NoSearchResults.js\";\nimport UDExSearch from \"./Search.js\";\nimport UDExDropdown from \"./Dropdown.js\";\nimport UDExList from \"./List.js\";\nimport UDExSelectBase from \"./SelectBase.js\";\nimport UDExListItem from \"./ListItem.js\";\nimport UDExTextField from \"./TextField.js\";\nimport UDExStatusMessage from \"./StatusMessage.js\";\nimport SelectBoxTemplate from \"./generated/templates/SelectBoxTemplate.lit.js\";\n\n// Styles\nimport CountrySelectorCss from \"./generated/themes/CountrySelector.css.js\";\nimport TextFieldCss from \"./generated/themes/TextField.css.js\";\nimport SelectBaseCss from \"./generated/themes/SelectBase.css.js\";\nimport SearchableListCss from \"./generated/themes/SearchableList.css.js\";\nimport getEffectiveScrollbarStyle from \"./utils/getEffectiveScrollbarStyle.js\";\n\ntype UDExCountrySelectorChangeSearchEventDetail = {\n value: string,\n}\n\n/**\n * @class\n *\n * <h3 class=\"comment-api-title\">Overview</h3>\n *\n *\n * <h3>Usage</h3>\n *\n * For the <code>udex-country-selector</code>\n * <h3>ES6 Module Import</h3>\n *\n * <code>import \"@sapudex/web-components/dist/CountrySelector.js\";</code>\n *\n * @constructor\n * @extends UDExSelectBase\n * @tagname udex-country-selector\n * @public\n */\n@customElement({\n tag: \"udex-country-selector\",\n renderer: litRender,\n styles: [\n TextFieldCss,\n SelectBaseCss,\n CountrySelectorCss,\n SearchableListCss,\n getEffectiveScrollbarStyle(),\n ],\n template: SelectBoxTemplate,\n dependencies: [\n UI5Button,\n UDExList,\n UDExSearch,\n UDExListItem,\n UDExDropdown,\n UDExTextField,\n UDExStatusMessage,\n IllustratedMessage,\n ],\n})\n\nclass UDExCountrySelector extends UDExSelectBase {\n /**\n * Allows to define the initially preselected country.\n *\n * @default \"\"\n * @public\n */\n @property({ type: String })\n preselectedCountry!: string;\n\n /**\n * Allows to define the list of blocked country.\n *\n * @default \"\"\n * @public\n */\n @property({ type: String })\n blockedCountryCodes?: string;\n\n /**\n * Allows to hide the flag images in the country selector.\n *\n * @default false\n * @public\n */\n @property({ type: Boolean })\n hideFlagImages?: boolean;\n\n /**\n * Indicates whether the country selector is enabled.\n *\n * @default true\n * @private\n */\n @property({ type: Boolean })\n _countrySelector: boolean = true;\n\n _countryList: Country[] = CountryListDB;\n _selectedCountry!: Country | undefined;\n\n onAfterRendering(): void {\n super.onAfterRendering();\n this.handleOutsideClick();\n }\n\n onBeforeRendering(): void {\n super.onBeforeRendering();\n this.filterBlockedCountries();\n this.setPreselectedCountry();\n this.prepareCountrySelectorItems();\n }\n\n handleItemPress(e: CustomEvent): void {\n this.handleItemSelection(e);\n this.selectCountryByElement(e.target as HTMLElement);\n }\n\n handleInputFocusIn(): void {\n this.inputFocusIn();\n }\n\n handleInputFocusOut(e: FocusEvent): void {\n const relatedTarget = e.relatedTarget as HTMLElement;\n const isInsideComponent = relatedTarget?.closest(`.${this._rootClass}`);\n\n if (!isInsideComponent) {\n this.closeDropdown();\n this.resetSearchState();\n this.updateImagePosition();\n }\n\n this._focused = false;\n }\n\n handleKeyDownSearch(e: KeyboardEvent): void {\n this.onKeyDownSearch(e);\n }\n\n handleDropdownBeforeOpen(): void {\n this.dropdownBeforeOpen();\n }\n\n handleDropdownClose(): void {\n this._open = false;\n this.fireEventDropdownClose();\n }\n\n handleOutsideClick(): void {\n document.addEventListener(\"click\", (e: Event) => {\n if (e.target !== this) {\n this._open = this._popover.open;\n }\n });\n }\n\n updateImagePosition(): void {\n const imagePlaceholder = this.shadowRoot!.querySelector<HTMLElement>(\".udex-text-field__input > .udex-text-field__image\");\n if (imagePlaceholder) {\n imagePlaceholder.style.backgroundPosition = this.selectedCountryFlagX || \"\";\n }\n }\n\n filterBlockedCountries(): void {\n if (this.blockedCountryCodes?.length) {\n const blockedCountryCodesArray = this.blockedCountryCodes.split(\",\").map(code => code.trim().toUpperCase());\n this._countryList = this._countryList.filter(country => !blockedCountryCodesArray.includes(country.iso.toUpperCase()));\n }\n }\n\n setPreselectedCountry(): void {\n if (!this._selectedCountry && this.preselectedCountry) {\n const preselectedISO = this.preselectedCountry.toUpperCase();\n this._selectedCountry = this._countryList.find(({ iso }) => iso.toUpperCase() === preselectedISO);\n }\n }\n\n selectCountryByElement(el: HTMLElement): void {\n const tokenId = el?.getAttribute(\"data-token-id\") || \"\";\n const itemObj = this.getItemFromList(tokenId);\n this._selectedCountry = this._countryList.find(country => country.iso === itemObj?._id);\n this._selectedOption = this.selectedCountryName || \"\";\n }\n\n prepareCountrySelectorItems(): void {\n this.items.length = 0;\n this._countryList.forEach(country => {\n const selected = country.iso.toUpperCase() === this._selectedCountry?.iso.toUpperCase();\n this.items.push({\n label: this.getCountryLabel(country.countryName, country.localName),\n innerHTML: this.getItemTemplate(country),\n selected,\n _id: country.iso.toUpperCase(),\n } as UDExListItem);\n });\n }\n\n getItemTemplate(country: Country) :string | undefined {\n return this.hideFlagImages ? undefined : `<span class=\"udex-text-field__image\" style=\"background-position:${country.flagX}\">`;\n }\n\n getCountryLabel(countryName?: string, localName?: string): string | null {\n return localName ? `${countryName} (${localName})` : countryName || null;\n }\n\n get selectedCountryName(): string | null {\n return this._selectedCountry ? this.getCountryLabel(this._selectedCountry.countryName, this._selectedCountry.localName) : \"\";\n }\n\n get flagAriaLabel(): string {\n return this.getCountryLabel(this._selectedCountry?.countryName, this._selectedCountry?.localName) || \"None\";\n }\n\n get selectedCountryFlagX(): string | undefined {\n return this._selectedCountry?.flagX;\n }\n\n get selectedCountryFlagY(): string | undefined {\n return this._selectedCountry?.flagY;\n }\n\n get showImageFlags(): boolean {\n return true;\n }\n}\n\nUDExCountrySelector.define();\n\nexport default UDExCountrySelector;\nexport type { UDExCountrySelectorChangeSearchEventDetail };\n"]}
|
|
1
|
+
{"version":3,"file":"CountrySelector.js","sourceRoot":"","sources":["../src/CountrySelector.ts"],"names":[],"mappings":";;;;;;AAAA,OAAO,aAAa,MAAM,0DAA0D,CAAC;AACrF,OAAO,WAAW,MAAM,sDAAsD,CAAC;AAC/E,OAAO,QAAQ,MAAM,qDAAqD,CAAC;AAC3E,OAAO,SAAS,MAAM,mCAAmC,CAAC;AAC1D,OAAO,wDAAwD,CAAC;AAChE,OAAO,sDAAsD,CAAC;AAE9D,OAAO,EAAE,aAAa,EAAE,MAAM,8BAA8B,CAAC;AAC7D,OAAO,kBAAkB,MAAM,qDAAqD,CAAC;AACrF,OAAO,gEAAgE,CAAC;AACxE,OAAO,UAAU,MAAM,aAAa,CAAC;AACrC,OAAO,YAAY,MAAM,eAAe,CAAC;AACzC,OAAO,QAAQ,MAAM,WAAW,CAAC;AACjC,OAAO,cAAc,MAAM,iBAAiB,CAAC;AAC7C,OAAO,YAAY,MAAM,eAAe,CAAC;AACzC,OAAO,aAAa,MAAM,gBAAgB,CAAC;AAC3C,OAAO,iBAAiB,MAAM,oBAAoB,CAAC;AACnD,OAAO,iBAAiB,MAAM,wBAAwB,CAAC;AACvD,OAAO,uBAAuB,MAAM,8BAA8B,CAAC;AACnE,OAAO,0BAA0B,MAAM,iCAAiC,CAAC;AAEzE,SAAS;AACT,OAAO,kBAAkB,MAAM,2CAA2C,CAAC;AAC3E,OAAO,YAAY,MAAM,qCAAqC,CAAC;AAC/D,OAAO,aAAa,MAAM,sCAAsC,CAAC;AACjE,OAAO,iBAAiB,MAAM,0CAA0C,CAAC;AACzE,OAAO,0BAA0B,MAAM,uCAAuC,CAAC;AAM/E;;;;;;;;;;;;;;;;;GAiBG;AAwBH,IAAM,mBAAmB,GAAzB,MAAM,mBAAoB,SAAQ,cAAc;IAAhD;;QA4BE;;;;;WAKG;QAED,qBAAgB,GAAY,IAAI,CAAC;QAEnC,iBAAY,GAAc,aAAa,CAAC;IAuI1C,CAAC;IApIC,gBAAgB;QACd,KAAK,CAAC,gBAAgB,EAAE,CAAC;QACzB,IAAI,CAAC,kBAAkB,EAAE,CAAC;IAC5B,CAAC;IAED,iBAAiB;QACf,KAAK,CAAC,iBAAiB,EAAE,CAAC;QAC1B,IAAI,CAAC,sBAAsB,EAAE,CAAC;QAC9B,IAAI,CAAC,qBAAqB,EAAE,CAAC;QAC7B,IAAI,CAAC,2BAA2B,EAAE,CAAC;IACrC,CAAC;IAED,eAAe,CAAC,CAAc;QAC5B,IAAI,CAAC,mBAAmB,CAAC,CAAC,CAAC,CAAC;QAC5B,IAAI,CAAC,sBAAsB,CAAC,CAAC,CAAC,MAAqB,CAAC,CAAC;IACvD,CAAC;IAED,kBAAkB;QAChB,IAAI,CAAC,YAAY,EAAE,CAAC;IACtB,CAAC;IAED,mBAAmB,CAAC,CAAa;QAC/B,MAAM,aAAa,GAAG,CAAC,CAAC,aAA4B,CAAC;QACrD,MAAM,iBAAiB,GAAG,aAAa,EAAE,OAAO,CAAC,IAAI,IAAI,CAAC,UAAU,EAAE,CAAC,CAAC;QAExE,IAAI,CAAC,iBAAiB,EAAE,CAAC;YACvB,IAAI,CAAC,aAAa,EAAE,CAAC;YACrB,IAAI,CAAC,gBAAgB,EAAE,CAAC;YACxB,IAAI,CAAC,mBAAmB,EAAE,CAAC;QAC7B,CAAC;QAED,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;IACxB,CAAC;IAED,mBAAmB,CAAC,CAAgB;QAClC,IAAI,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC;IAC1B,CAAC;IAED,wBAAwB;QACtB,IAAI,CAAC,kBAAkB,EAAE,CAAC;IAC5B,CAAC;IAED,mBAAmB;QACjB,IAAI,CAAC,KAAK,GAAG,KAAK,CAAC;QACnB,IAAI,CAAC,sBAAsB,EAAE,CAAC;IAChC,CAAC;IAED,kBAAkB;QAChB,QAAQ,CAAC,gBAAgB,CAAC,OAAO,EAAE,CAAC,CAAQ,EAAE,EAAE;YAC9C,IAAI,CAAC,CAAC,MAAM,KAAK,IAAI,EAAE,CAAC;gBACtB,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC;YAClC,CAAC;QACH,CAAC,CAAC,CAAC;IACL,CAAC;IAED,mBAAmB;QACjB,MAAM,gBAAgB,GAAG,IAAI,CAAC,UAAW,CAAC,aAAa,CAAc,mDAAmD,CAAC,CAAC;QAC1H,IAAI,gBAAgB,EAAE,CAAC;YACrB,gBAAgB,CAAC,KAAK,CAAC,kBAAkB,GAAG,IAAI,CAAC,oBAAoB,IAAI,EAAE,CAAC;QAC9E,CAAC;IACH,CAAC;IAED,sBAAsB;QACpB,IAAI,IAAI,CAAC,mBAAmB,EAAE,MAAM,EAAE,CAAC;YACrC,MAAM,wBAAwB,GAAG,IAAI,CAAC,mBAAmB,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC,CAAC;YAC5G,IAAI,CAAC,YAAY,GAAG,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC,wBAAwB,CAAC,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC;QACzH,CAAC;IACH,CAAC;IAED,qBAAqB;QACnB,IAAI,CAAC,IAAI,CAAC,gBAAgB,IAAI,IAAI,CAAC,kBAAkB,EAAE,CAAC;YACtD,MAAM,cAAc,GAAG,IAAI,CAAC,kBAAkB,CAAC,WAAW,EAAE,CAAC;YAC7D,IAAI,CAAC,gBAAgB,GAAG,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,EAAE,GAAG,EAAE,EAAE,EAAE,CAAC,GAAG,CAAC,WAAW,EAAE,KAAK,cAAc,CAAC,CAAC;QACpG,CAAC;IACH,CAAC;IAED,sBAAsB,CAAC,EAAe;QACpC,MAAM,OAAO,GAAG,EAAE,EAAE,YAAY,CAAC,eAAe,CAAC,IAAI,EAAE,CAAC;QACxD,MAAM,OAAO,GAAG,IAAI,CAAC,eAAe,CAAC,OAAO,CAAC,CAAC;QAC9C,IAAI,CAAC,gBAAgB,GAAG,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,CAAC,GAAG,KAAK,OAAO,EAAE,GAAG,CAAC,CAAC;QACxF,IAAI,CAAC,eAAe,GAAG,IAAI,CAAC,mBAAmB,IAAI,EAAE,CAAC;IACxD,CAAC;IAED,2BAA2B;QACzB,IAAI,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC;QACtB,IAAI,CAAC,YAAY,CAAC,OAAO,CAAC,OAAO,CAAC,EAAE;YAClC,MAAM,QAAQ,GAAG,OAAO,CAAC,GAAG,CAAC,WAAW,EAAE,KAAK,IAAI,CAAC,gBAAgB,EAAE,GAAG,CAAC,WAAW,EAAE,CAAC;YACxF,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC;gBACd,KAAK,EAAE,IAAI,CAAC,eAAe,CAAC,OAAO,CAAC,WAAW,EAAE,OAAO,CAAC,SAAS,CAAC;gBACnE,SAAS,EAAE,IAAI,CAAC,eAAe,CAAC,OAAO,CAAC;gBACxC,QAAQ;gBACR,GAAG,EAAE,OAAO,CAAC,GAAG,CAAC,WAAW,EAAE;aACf,CAAC,CAAC;QACrB,CAAC,CAAC,CAAC;IACL,CAAC;IAED,eAAe,CAAC,OAAgB;QAC9B,OAAO,IAAI,CAAC,cAAc,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,mEAAmE,OAAO,CAAC,KAAK,IAAI,CAAC;IAChI,CAAC;IAED,eAAe,CAAC,WAAoB,EAAE,SAAkB;QACtD,OAAO,SAAS,CAAC,CAAC,CAAC,GAAG,WAAW,KAAK,SAAS,GAAG,CAAC,CAAC,CAAC,WAAW,IAAI,IAAI,CAAC;IAC3E,CAAC;IAED,IAAa,WAAW;QACtB,OAAO,uBAAuB,CAAC,IAAI,CAAC,IAAI,CAAW,CAAC;IACtD,CAAC;IAED,IAAa,cAAc;QACzB,IAAI,CAAC,qBAAqB,GAAG,IAAI,CAAC,YAAY,CAAC;QAC/C,OAAO,0BAA0B,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC/C,CAAC;IAED,IAAI,mBAAmB;QACrB,OAAO,IAAI,CAAC,gBAAgB,CAAC,CAAC,CAAC,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC,gBAAgB,CAAC,WAAW,EAAE,IAAI,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;IAC/H,CAAC;IAED,IAAI,aAAa;QACf,OAAO,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC,gBAAgB,EAAE,WAAW,EAAE,IAAI,CAAC,gBAAgB,EAAE,SAAS,CAAC,IAAI,MAAM,CAAC;IAC9G,CAAC;IAED,IAAI,oBAAoB;QACtB,OAAO,IAAI,CAAC,gBAAgB,EAAE,KAAK,CAAC;IACtC,CAAC;IAED,IAAI,oBAAoB;QACtB,OAAO,IAAI,CAAC,gBAAgB,EAAE,KAAK,CAAC;IACtC,CAAC;IAED,IAAI,cAAc;QAChB,OAAO,IAAI,CAAC;IACd,CAAC;CACF,CAAA;AApKG;IADD,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;+DACG;AAS5B;IADD,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC;gEACI;AAS7B;IADD,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;2DACD;AASzB;IADD,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,CAAC;6DACO;AAnC/B,mBAAmB;IAvBxB,aAAa,CAAC;QACb,GAAG,EAAE,uBAAuB;QAC5B,QAAQ,EAAE,WAAW;QACrB,MAAM,EAAE;YACN,YAAY;YACZ,aAAa;YACb,kBAAkB;YAClB,iBAAiB;YACjB,0BAA0B,EAAE;SAC7B;QACD,QAAQ,EAAE,iBAAiB;QAC3B,YAAY,EAAE;YACZ,SAAS;YACT,QAAQ;YACR,UAAU;YACV,YAAY;YACZ,YAAY;YACZ,aAAa;YACb,iBAAiB;YACjB,kBAAkB;SACnB;KACF,CAAC;GAEI,mBAAmB,CA4KxB;AAED,mBAAmB,CAAC,MAAM,EAAE,CAAC;AAE7B,eAAe,mBAAmB,CAAC","sourcesContent":["import customElement from \"@ui5/webcomponents-base/dist/decorators/customElement.js\";\nimport jsxRenderer from \"@ui5/webcomponents-base/dist/renderer/JsxRenderer.js\";\nimport property from \"@ui5/webcomponents-base/dist/decorators/property.js\";\nimport UI5Button from \"@ui5/webcomponents/dist/Button.js\";\nimport \"@ui5/webcomponents-icons/dist/navigation-down-arrow.js\";\nimport \"@ui5/webcomponents-icons/dist/navigation-up-arrow.js\";\nimport type { Country } from \"./data/CountryListISO3166.js\";\nimport { CountryListDB } from \"./data/CountryListISO3166.js\";\nimport IllustratedMessage from \"@ui5/webcomponents-fiori/dist/IllustratedMessage.js\";\nimport \"@ui5/webcomponents-fiori/dist/illustrations/NoSearchResults.js\";\nimport UDExSearch from \"./Search.js\";\nimport UDExDropdown from \"./Dropdown.js\";\nimport UDExList from \"./List.js\";\nimport UDExSelectBase from \"./SelectBase.js\";\nimport UDExListItem from \"./ListItem.js\";\nimport UDExTextField from \"./TextField.js\";\nimport UDExStatusMessage from \"./StatusMessage.js\";\nimport SelectBoxTemplate from \"./SelectBoxTemplate.js\";\nimport CountrySelectorTemplate from \"./CountrySelectorTemplate.js\";\nimport SearchableListBaseTemplate from \"./SearchableListBaseTemplate.js\";\n\n// Styles\nimport CountrySelectorCss from \"./generated/themes/CountrySelector.css.js\";\nimport TextFieldCss from \"./generated/themes/TextField.css.js\";\nimport SelectBaseCss from \"./generated/themes/SelectBase.css.js\";\nimport SearchableListCss from \"./generated/themes/SearchableList.css.js\";\nimport getEffectiveScrollbarStyle from \"./utils/getEffectiveScrollbarStyle.js\";\n\ntype UDExCountrySelectorChangeSearchEventDetail = {\n value: string,\n}\n\n/**\n * @class\n *\n * <h3 class=\"comment-api-title\">Overview</h3>\n *\n *\n * <h3>Usage</h3>\n *\n * For the <code>udex-country-selector</code>\n * <h3>ES6 Module Import</h3>\n *\n * <code>import \"@sapudex/web-components/dist/CountrySelector.js\";</code>\n *\n * @constructor\n * @extends UDExSelectBase\n * @tagname udex-country-selector\n * @public\n */\n@customElement({\n tag: \"udex-country-selector\",\n renderer: jsxRenderer,\n styles: [\n TextFieldCss,\n SelectBaseCss,\n CountrySelectorCss,\n SearchableListCss,\n getEffectiveScrollbarStyle(),\n ],\n template: SelectBoxTemplate,\n dependencies: [\n UI5Button,\n UDExList,\n UDExSearch,\n UDExListItem,\n UDExDropdown,\n UDExTextField,\n UDExStatusMessage,\n IllustratedMessage,\n ],\n})\n\nclass UDExCountrySelector extends UDExSelectBase {\n /**\n * Allows to define the initially preselected country.\n *\n * @default \"\"\n * @public\n */\n @property({ type: String })\n preselectedCountry!: string;\n\n /**\n * Allows to define the list of blocked country.\n *\n * @default \"\"\n * @public\n */\n @property({ type: String })\n blockedCountryCodes?: string;\n\n /**\n * Allows to hide the flag images in the country selector.\n *\n * @default false\n * @public\n */\n @property({ type: Boolean })\n hideFlagImages?: boolean;\n\n /**\n * Indicates whether the country selector is enabled.\n *\n * @default true\n * @private\n */\n @property({ type: Boolean })\n _countrySelector: boolean = true;\n\n _countryList: Country[] = CountryListDB;\n _selectedCountry!: Country | undefined;\n\n onAfterRendering(): void {\n super.onAfterRendering();\n this.handleOutsideClick();\n }\n\n onBeforeRendering(): void {\n super.onBeforeRendering();\n this.filterBlockedCountries();\n this.setPreselectedCountry();\n this.prepareCountrySelectorItems();\n }\n\n handleItemPress(e: CustomEvent): void {\n this.handleItemSelection(e);\n this.selectCountryByElement(e.target as HTMLElement);\n }\n\n handleInputFocusIn(): void {\n this.inputFocusIn();\n }\n\n handleInputFocusOut(e: FocusEvent): void {\n const relatedTarget = e.relatedTarget as HTMLElement;\n const isInsideComponent = relatedTarget?.closest(`.${this._rootClass}`);\n\n if (!isInsideComponent) {\n this.closeDropdown();\n this.resetSearchState();\n this.updateImagePosition();\n }\n\n this._focused = false;\n }\n\n handleKeyDownSearch(e: KeyboardEvent): void {\n this.onKeyDownSearch(e);\n }\n\n handleDropdownBeforeOpen(): void {\n this.dropdownBeforeOpen();\n }\n\n handleDropdownClose(): void {\n this._open = false;\n this.fireEventDropdownClose();\n }\n\n handleOutsideClick(): void {\n document.addEventListener(\"click\", (e: Event) => {\n if (e.target !== this) {\n this._open = this._popover.open;\n }\n });\n }\n\n updateImagePosition(): void {\n const imagePlaceholder = this.shadowRoot!.querySelector<HTMLElement>(\".udex-text-field__input > .udex-text-field__image\");\n if (imagePlaceholder) {\n imagePlaceholder.style.backgroundPosition = this.selectedCountryFlagX || \"\";\n }\n }\n\n filterBlockedCountries(): void {\n if (this.blockedCountryCodes?.length) {\n const blockedCountryCodesArray = this.blockedCountryCodes.split(\",\").map(code => code.trim().toUpperCase());\n this._countryList = this._countryList.filter(country => !blockedCountryCodesArray.includes(country.iso.toUpperCase()));\n }\n }\n\n setPreselectedCountry(): void {\n if (!this._selectedCountry && this.preselectedCountry) {\n const preselectedISO = this.preselectedCountry.toUpperCase();\n this._selectedCountry = this._countryList.find(({ iso }) => iso.toUpperCase() === preselectedISO);\n }\n }\n\n selectCountryByElement(el: HTMLElement): void {\n const tokenId = el?.getAttribute(\"data-token-id\") || \"\";\n const itemObj = this.getItemFromList(tokenId);\n this._selectedCountry = this._countryList.find(country => country.iso === itemObj?._id);\n this._selectedOption = this.selectedCountryName || \"\";\n }\n\n prepareCountrySelectorItems(): void {\n this.items.length = 0;\n this._countryList.forEach(country => {\n const selected = country.iso.toUpperCase() === this._selectedCountry?.iso.toUpperCase();\n this.items.push({\n label: this.getCountryLabel(country.countryName, country.localName),\n innerHTML: this.getItemTemplate(country),\n selected,\n _id: country.iso.toUpperCase(),\n } as UDExListItem);\n });\n }\n\n getItemTemplate(country: Country) :string | undefined {\n return this.hideFlagImages ? undefined : `<span class=\"udex-text-field__image\" style=\"background-position:${country.flagX}\">`;\n }\n\n getCountryLabel(countryName?: string, localName?: string): string | null {\n return localName ? `${countryName} (${localName})` : countryName || null;\n }\n\n override get countryFlag(): object {\n return CountrySelectorTemplate.call(this) as object;\n }\n\n override get searchableList() {\n this.defaultAccessibleRole = this._listBoxRole;\n return SearchableListBaseTemplate.call(this);\n }\n\n get selectedCountryName(): string | null {\n return this._selectedCountry ? this.getCountryLabel(this._selectedCountry.countryName, this._selectedCountry.localName) : \"\";\n }\n\n get flagAriaLabel(): string {\n return this.getCountryLabel(this._selectedCountry?.countryName, this._selectedCountry?.localName) || \"None\";\n }\n\n get selectedCountryFlagX(): string | undefined {\n return this._selectedCountry?.flagX;\n }\n\n get selectedCountryFlagY(): string | undefined {\n return this._selectedCountry?.flagY;\n }\n\n get showImageFlags(): boolean {\n return true;\n }\n}\n\nUDExCountrySelector.define();\n\nexport default UDExCountrySelector;\nexport type { UDExCountrySelectorChangeSearchEventDetail };\n"]}
|