negodesign 0.0.29 → 0.0.31

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.
Files changed (131) hide show
  1. package/dist/assets/lonely-404.mp4 +0 -0
  2. package/dist/components/core/banner/AdCardBanner.svelte.d.ts +4 -0
  3. package/dist/components/core/banner/CtaCardBanner.svelte +118 -0
  4. package/dist/components/core/banner/CtaCardBanner.svelte.d.ts +4 -0
  5. package/dist/components/core/banner/{BannerNotification.svelte → NotificationBanner.svelte} +4 -3
  6. package/dist/components/core/banner/NotificationBanner.svelte.d.ts +4 -0
  7. package/dist/components/core/banner/types.d.ts +38 -7
  8. package/dist/components/core/card/highlight/01/CardHighlight01.svelte +15 -26
  9. package/dist/components/core/card/highlight/02/CardHighlight02.svelte +13 -24
  10. package/dist/components/core/card/media/01/CardMedia01.svelte +2 -12
  11. package/dist/components/core/card/media/02/CardMedia02.svelte +2 -12
  12. package/dist/components/core/card/promotion/CardPromotion.svelte +5 -1
  13. package/dist/components/core/card/shared/CardButton.svelte +9 -3
  14. package/dist/components/core/card/shared/CardButton.svelte.d.ts +1 -1
  15. package/dist/components/core/card/shared/CardLogo.svelte +19 -0
  16. package/dist/components/core/card/shared/CardLogo.svelte.d.ts +7 -0
  17. package/dist/components/core/card/shared/CardThumbnailVideo.svelte +3 -0
  18. package/dist/components/core/card/types.d.ts +97 -0
  19. package/dist/components/core/carousel/grid/media/types.d.ts +11 -0
  20. package/dist/components/core/carousel/grid/media/ui/CarouselGridMedia.svelte +2 -1
  21. package/dist/components/core/carousel/grid/profile/types.d.ts +11 -0
  22. package/dist/components/core/carousel/grid/profile/ui/CarouselGridProfile.svelte +3 -5
  23. package/dist/components/core/carousel/grid/shared/ui/CarouselGridSlot.svelte +4 -9
  24. package/dist/components/core/carousel/grid/shared/ui/CarouselGridSlot.svelte.d.ts +1 -0
  25. package/dist/components/core/carousel/highlights/types.d.ts +11 -0
  26. package/dist/components/core/carousel/promotion/types.d.ts +10 -0
  27. package/dist/components/core/carousel/types.d.ts +56 -0
  28. package/dist/components/core/datatable/data/data-table.d.ts +25 -0
  29. package/dist/components/core/footer/types.d.ts +51 -0
  30. package/dist/components/core/footer/types.js +1 -0
  31. package/dist/components/core/footer/ui/01/Footer01.svelte +76 -0
  32. package/dist/components/core/footer/ui/01/Footer01.svelte.d.ts +4 -0
  33. package/dist/components/core/footer/ui/02/Footer02.svelte +53 -0
  34. package/dist/components/core/footer/ui/02/Footer02.svelte.d.ts +4 -0
  35. package/dist/components/core/footer/ui/Footer.svelte +18 -0
  36. package/dist/components/core/footer/ui/Footer.svelte.d.ts +7 -0
  37. package/dist/components/core/footer/ui/shared/FooterColumn.svelte +18 -0
  38. package/dist/components/core/footer/ui/shared/FooterColumn.svelte.d.ts +4 -0
  39. package/dist/components/core/footer/ui/shared/FooterNewsLetter.svelte +57 -0
  40. package/dist/components/core/footer/ui/shared/FooterNewsLetter.svelte.d.ts +9 -0
  41. package/dist/components/core/footer/ui/shared/FooterSocialIcon.svelte +62 -0
  42. package/dist/components/core/footer/ui/shared/FooterSocialIcon.svelte.d.ts +4 -0
  43. package/dist/components/core/nav/data/nav-menu-sidebar.d.ts +29 -0
  44. package/dist/components/core/nav/data/nav-menu.d.ts +43 -0
  45. package/dist/components/core/nav/data/nav-user-sidebar.d.ts +14 -0
  46. package/dist/components/core/nav/ui/menu-links.svelte +1 -1
  47. package/dist/components/core/panel/CarouselSlot.svelte +2 -2
  48. package/dist/components/core/panel/LeftHero.svelte +2 -2
  49. package/dist/components/core/panel/type.d.ts +11 -0
  50. package/dist/components/core/search/types.d.ts +17 -5
  51. package/dist/components/core/sidebar/types.d.ts +19 -0
  52. package/dist/components/core/sidebar/types.js +1 -0
  53. package/dist/components/core/tabs/data/TabModel.d.ts +11 -0
  54. package/dist/components/core/tabs/types.d.ts +11 -0
  55. package/dist/components/core/tabs/types.js +1 -0
  56. package/dist/components/pages/admin/01/ui/types.d.ts +21 -0
  57. package/dist/components/pages/admin/01/ui/types.js +1 -0
  58. package/dist/components/pages/product-details/01/ProductDetails01.svelte +71 -0
  59. package/dist/components/pages/product-details/01/ProductDetails01.svelte.d.ts +11 -0
  60. package/dist/components/pages/product-details/02/ProductDetails02.svelte +88 -0
  61. package/dist/components/pages/product-details/02/ProductDetails02.svelte.d.ts +11 -0
  62. package/dist/components/pages/product-details/03/ProductDetails03.svelte +77 -0
  63. package/dist/components/pages/product-details/03/ProductDetails03.svelte.d.ts +11 -0
  64. package/dist/components/pages/product-details/04/ProductDetails04.svelte +65 -0
  65. package/dist/components/pages/product-details/04/ProductDetails04.svelte.d.ts +11 -0
  66. package/dist/components/pages/product-details/ProductDetails.svelte +38 -0
  67. package/dist/components/pages/product-details/ProductDetails.svelte.d.ts +4 -0
  68. package/dist/components/pages/product-details/shared/ProductDetailActions.svelte +82 -0
  69. package/dist/components/pages/product-details/shared/ProductDetailActions.svelte.d.ts +13 -0
  70. package/dist/components/pages/product-details/shared/ProductDetailBreadcrumb.svelte +46 -0
  71. package/dist/components/pages/product-details/shared/ProductDetailBreadcrumb.svelte.d.ts +8 -0
  72. package/dist/components/pages/product-details/shared/ProductDetailDescription.svelte +38 -0
  73. package/dist/components/pages/product-details/shared/ProductDetailDescription.svelte.d.ts +8 -0
  74. package/dist/components/pages/product-details/shared/ProductDetailFeatures.svelte +40 -0
  75. package/dist/components/pages/product-details/shared/ProductDetailFeatures.svelte.d.ts +7 -0
  76. package/dist/components/pages/product-details/shared/ProductDetailFilesVertical.svelte +72 -0
  77. package/dist/components/pages/product-details/shared/ProductDetailFilesVertical.svelte.d.ts +9 -0
  78. package/dist/components/pages/product-details/shared/ProductDetailHeader.svelte +41 -0
  79. package/dist/components/pages/product-details/shared/ProductDetailHeader.svelte.d.ts +9 -0
  80. package/dist/components/pages/product-details/shared/ProductDetailImage.svelte +70 -0
  81. package/dist/components/pages/product-details/shared/ProductDetailImage.svelte.d.ts +9 -0
  82. package/dist/components/pages/product-details/shared/ProductDetailMap.svelte +57 -0
  83. package/dist/components/pages/product-details/shared/ProductDetailMap.svelte.d.ts +9 -0
  84. package/dist/components/pages/product-details/shared/ProductDetailPrice.svelte +44 -0
  85. package/dist/components/pages/product-details/shared/ProductDetailPrice.svelte.d.ts +9 -0
  86. package/dist/components/pages/product-details/shared/ProductDetailRating.svelte +42 -0
  87. package/dist/components/pages/product-details/shared/ProductDetailRating.svelte.d.ts +8 -0
  88. package/dist/components/pages/product-details/shared/ProductDetailReviews.svelte +70 -0
  89. package/dist/components/pages/product-details/shared/ProductDetailReviews.svelte.d.ts +8 -0
  90. package/dist/components/pages/product-details/shared/ProductDetailTabs.svelte +96 -0
  91. package/dist/components/pages/product-details/shared/ProductDetailTabs.svelte.d.ts +12 -0
  92. package/dist/components/pages/product-details/shared/ProductDetailTags.svelte +35 -0
  93. package/dist/components/pages/product-details/shared/ProductDetailTags.svelte.d.ts +8 -0
  94. package/dist/components/pages/product-details/shared/ProductPurchasePanel.svelte +58 -0
  95. package/dist/components/pages/product-details/shared/ProductPurchasePanel.svelte.d.ts +11 -0
  96. package/dist/components/pages/product-details/types.d.ts +170 -0
  97. package/dist/components/pages/product-details/types.js +1 -0
  98. package/dist/components/pages/profile-user/01/ProfileUser01.svelte +113 -0
  99. package/dist/components/pages/profile-user/01/ProfileUser01.svelte.d.ts +27 -0
  100. package/dist/components/pages/profile-user/02/ProfileUser02.svelte +83 -0
  101. package/dist/components/pages/profile-user/02/ProfileUser02.svelte.d.ts +20 -0
  102. package/dist/components/pages/profile-user/03/ProfileUser03.svelte +85 -0
  103. package/dist/components/pages/profile-user/03/ProfileUser03.svelte.d.ts +20 -0
  104. package/dist/components/pages/profile-user/ProfileUser.svelte +53 -0
  105. package/dist/components/pages/profile-user/ProfileUser.svelte.d.ts +4 -0
  106. package/dist/components/pages/profile-user/shared/ProfileUserAddress.svelte +84 -0
  107. package/dist/components/pages/profile-user/shared/ProfileUserAddress.svelte.d.ts +8 -0
  108. package/dist/components/pages/profile-user/shared/ProfileUserHeader.svelte +104 -0
  109. package/dist/components/pages/profile-user/shared/ProfileUserHeader.svelte.d.ts +9 -0
  110. package/dist/components/pages/profile-user/shared/ProfileUserResetPassword.svelte +116 -0
  111. package/dist/components/pages/profile-user/shared/ProfileUserResetPassword.svelte.d.ts +7 -0
  112. package/dist/components/pages/profile-user/shared/ProfileUserSetting.svelte +176 -0
  113. package/dist/components/pages/profile-user/shared/ProfileUserSetting.svelte.d.ts +14 -0
  114. package/dist/components/pages/profile-user/shared/ProfileUserTabs.svelte +78 -0
  115. package/dist/components/pages/profile-user/shared/ProfileUserTabs.svelte.d.ts +22 -0
  116. package/dist/components/pages/profile-user/types.d.ts +144 -0
  117. package/dist/components/pages/profile-user/types.js +1 -0
  118. package/dist/globals.css +319 -4
  119. package/dist/i18n/langs/en.d.ts +87 -0
  120. package/dist/i18n/langs/en.js +87 -0
  121. package/dist/i18n/langs/pt.d.ts +87 -0
  122. package/dist/i18n/langs/pt.js +93 -6
  123. package/dist/i18n/translations.d.ts +174 -0
  124. package/dist/index.d.ts +194 -27
  125. package/dist/index.js +194 -27
  126. package/dist/styles/globals.css +1 -1
  127. package/dist/types/index.d.ts +196 -5
  128. package/package.json +1 -1
  129. package/dist/components/core/banner/BannerNotification.svelte.d.ts +0 -4
  130. package/dist/components/core/banner/CardAdBanner.svelte.d.ts +0 -4
  131. /package/dist/components/core/banner/{CardAdBanner.svelte → AdCardBanner.svelte} +0 -0
@@ -0,0 +1,58 @@
1
+ <script lang="ts" module>
2
+ /**
3
+ * Painel de compra do produto: avaliação, preço e ações.
4
+ * Compõe ProductDetailRating, ProductDetailPrice e ProductDetailActions.
5
+ * @component
6
+ * @example
7
+ * ```svelte
8
+ * <ProductPurchasePanel {data} isLoading={true} />
9
+ * ```
10
+ */
11
+ </script>
12
+
13
+ <script lang="ts">
14
+ import ProductDetailActions from "./ProductDetailActions.svelte";
15
+ import ProductDetailPrice from "./ProductDetailPrice.svelte";
16
+ import ProductDetailRating from "./ProductDetailRating.svelte";
17
+ import type { ProductDetailsData } from "../types";
18
+
19
+ let {
20
+ data,
21
+ isLoading = false,
22
+ onBuy,
23
+ onFavorite,
24
+ onCart,
25
+ }: {
26
+ data: ProductDetailsData;
27
+ isLoading?: boolean;
28
+ onBuy?: (id: string | number) => void;
29
+ onFavorite?: (id: string | number) => void;
30
+ onCart?: (id: string | number) => void;
31
+ } = $props();
32
+ </script>
33
+
34
+ <div class="flex flex-col gap-4">
35
+ <ProductDetailRating
36
+ rating={data.rating}
37
+ reviewsCount={data.reviewsCount}
38
+ {isLoading}
39
+ />
40
+
41
+ <ProductDetailPrice
42
+ newPrice={data.newPrice}
43
+ oldPrice={data.oldPrice}
44
+ currency={data.currency}
45
+ {isLoading}
46
+ />
47
+
48
+ <ProductDetailActions
49
+ id={data.id}
50
+ buttonBuyText={data.buttonBuyText}
51
+ isFavorite={data.isFavorite}
52
+ isCart={data.isCart}
53
+ {isLoading}
54
+ {onBuy}
55
+ {onFavorite}
56
+ {onCart}
57
+ />
58
+ </div>
@@ -0,0 +1,11 @@
1
+ import type { ProductDetailsData } from "../types";
2
+ type $$ComponentProps = {
3
+ data: ProductDetailsData;
4
+ isLoading?: boolean;
5
+ onBuy?: (id: string | number) => void;
6
+ onFavorite?: (id: string | number) => void;
7
+ onCart?: (id: string | number) => void;
8
+ };
9
+ declare const ProductPurchasePanel: import("svelte").Component<$$ComponentProps, {}, "">;
10
+ type ProductPurchasePanel = ReturnType<typeof ProductPurchasePanel>;
11
+ export default ProductPurchasePanel;
@@ -0,0 +1,170 @@
1
+ import type { IconSvgElement } from "@hugeicons/svelte";
2
+ /**
3
+ * Item individual do breadcrumb de navegação.
4
+ * Representa um nível hierárquico na navegação da página
5
+ * (ex: Home / Turismo / Hotel Baía Azul).
6
+ */
7
+ export interface ProductDetailsBreadcrumbItem {
8
+ /** Texto visível do item no breadcrumb. */
9
+ label: string;
10
+ /** URL de destino quando o item é clicável (último item geralmente não tem href). */
11
+ href?: string;
12
+ }
13
+ /**
14
+ * Tag/badge associada ao produto.
15
+ * Usada para destacar categorias, localização ou características rápidas.
16
+ */
17
+ export interface ProductDetailsTag {
18
+ /** Ícone opcional exibido antes do texto da tag. */
19
+ icon?: IconSvgElement;
20
+ /** Texto principal da tag (ex: "Luanda", "5 Estrelas"). */
21
+ text: string;
22
+ }
23
+ /**
24
+ * Imagem da galeria do produto.
25
+ * Cada imagem pode ter um texto alternativo para acessibilidade.
26
+ */
27
+ export interface ProductDetailsImage {
28
+ /** Caminho ou URL completa da imagem (obrigatório). */
29
+ src: string;
30
+ /** Texto alternativo para acessibilidade (recomendado). */
31
+ alt?: string;
32
+ }
33
+ /**
34
+ * Informações de localização do produto.
35
+ * Usada para exibir o mapa embed e detalhes do endereço.
36
+ */
37
+ export interface ProductDetailsLocation {
38
+ /** Nome/título da localização (ex: "Morro da Luz"). */
39
+ label?: string;
40
+ /** Endereço completo ou parcial para exibição. */
41
+ address?: string;
42
+ /**
43
+ * URL do embed do mapa.
44
+ * Suporta OpenStreetMap, Google Maps e outros serviços de embed.
45
+ * Se não for fornecido, usa um mapa padrão.
46
+ */
47
+ mapUrl?: string;
48
+ }
49
+ /**
50
+ * Avaliação de um cliente sobre o produto.
51
+ * Contém autor, classificação, data e comentário.
52
+ */
53
+ export interface ProductDetailsReview {
54
+ /** Identificador único da avaliação (usado como key nos {#each}). */
55
+ id: string | number;
56
+ /** Nome do autor da avaliação. */
57
+ author: string;
58
+ /**
59
+ * Classificação numérica (ex: 4.5 de 5).
60
+ * Geralmente um valor entre 0 e 5.
61
+ */
62
+ rating: number;
63
+ /** Data da avaliação (formato string, ex: "12/08/2024"). */
64
+ date?: string;
65
+ /** Comentário/texto completo da avaliação. */
66
+ comment: string;
67
+ }
68
+ /**
69
+ * Aba de conteúdo adicional no produto.
70
+ * Usada para organizar descrição, avaliações, detalhes técnicos, etc.
71
+ */
72
+ export interface ProductDetailsTab {
73
+ /** Identificador único da aba (ex: "description", "reviews"). */
74
+ id: string;
75
+ /** Rótulo visível no botão da aba. */
76
+ label: string;
77
+ }
78
+ /**
79
+ * Dados completos apresentados na página de detalhes do produto.
80
+ * Interface principal que agrega todas as informações necessárias
81
+ * para renderizar qualquer variante do componente.
82
+ */
83
+ export interface ProductDetailsData {
84
+ /** Identificador único do produto. */
85
+ id: string | number;
86
+ /** Itens do breadcrumb de navegação. */
87
+ breadcrumb: ProductDetailsBreadcrumbItem[];
88
+ /** Título principal do produto (nome). */
89
+ title: string;
90
+ /** Subtítulo opcional (slogan ou descrição curta). */
91
+ subtitle?: string;
92
+ /** Descrição curta do produto. */
93
+ description: string;
94
+ /** Descrição longa/detalhada (opcional). */
95
+ longDescription?: string;
96
+ /** Lista de tags/categorias associadas ao produto. */
97
+ tags?: ProductDetailsTag[];
98
+ /** Galeria de imagens do produto. */
99
+ gallery: ProductDetailsImage[];
100
+ /** Informações de localização para exibir no mapa. */
101
+ location?: ProductDetailsLocation;
102
+ /**
103
+ * Classificação média do produto.
104
+ * Valor entre 0 e 5 (ex: 4.2).
105
+ */
106
+ rating?: number;
107
+ /** Número total de avaliações recebidas. */
108
+ reviewsCount?: number;
109
+ /** Lista de avaliações individuais dos clientes. */
110
+ reviews?: ProductDetailsReview[];
111
+ /** Preço atual/promocional do produto. */
112
+ newPrice?: string | number;
113
+ /** Preço original (antes do desconto). */
114
+ oldPrice?: string | number;
115
+ /** Símbolo da moeda (ex: "Kz", "€", "$"). */
116
+ currency?: string;
117
+ /** Quantidade disponível em stock. */
118
+ quantityAvailable?: number;
119
+ /** Lista de características/features do produto (strings). */
120
+ features?: string[];
121
+ /**
122
+ * Abas de conteúdo personalizadas.
123
+ * Se não for fornecido, usa padrão: Descrição + Avaliações.
124
+ */
125
+ tabs?: ProductDetailsTab[];
126
+ /** Texto customizado para o botão de compra (padrão: "Comprar"). */
127
+ buttonBuyText?: string;
128
+ /** Estado inicial do produto no carrinho. */
129
+ isCart?: boolean;
130
+ /** Estado inicial do produto nos favoritos. */
131
+ isFavorite?: boolean;
132
+ }
133
+ /**
134
+ * Propriedades do componente principal ProductDetails.
135
+ * Suporta quatro variantes de layout e callbacks de interação.
136
+ */
137
+ export interface ProductDetailsProps {
138
+ /**
139
+ * Variante do layout da página de detalhes.
140
+ * - 1: Duas colunas (galeria à esquerda, info à direita)
141
+ * - 2: Galeria em destaque com conteúdo centralizado
142
+ * - 3: Painel de compra sticky no lado direito
143
+ * - 4: Abas de conteúdo (descrição e avaliações) abaixo da info
144
+ * @default 1
145
+ */
146
+ varient?: 1 | 2 | 3 | 4;
147
+ /** Dados completos do produto a serem exibidos. */
148
+ data: ProductDetailsData;
149
+ /**
150
+ * Estado de carregamento.
151
+ * Quando true, todos os blocos exibem Skeletons no lugar do conteúdo.
152
+ * @default false
153
+ */
154
+ isLoading?: boolean;
155
+ /**
156
+ * Callback executado quando o utilizador clica no botão de compra.
157
+ * Recebe o id do produto como argumento.
158
+ */
159
+ onBuy?: (id: string | number) => void;
160
+ /**
161
+ * Callback executado quando o utilizador clica no botão de favorito.
162
+ * Recebe o id do produto como argumento.
163
+ */
164
+ onFavorite?: (id: string | number) => void;
165
+ /**
166
+ * Callback executado quando o utilizador clica no botão de carrinho.
167
+ * Recebe o id do produto como argumento.
168
+ */
169
+ onCart?: (id: string | number) => void;
170
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,113 @@
1
+ <script lang="ts" module>
2
+ /**
3
+ * Variante 01 da página de perfil. Reutiliza headers partilhados,
4
+ * tabs, moradas, segurança e definições.
5
+ * @component
6
+ */
7
+ </script>
8
+
9
+ <script lang="ts">
10
+ import { t } from "../../../../i18n";
11
+ import type { ProfileUserData } from "../types";
12
+ import ProfileUserHeader from "../shared/ProfileUserHeader.svelte";
13
+ import ProfileUserTabs from "../shared/ProfileUserTabs.svelte";
14
+ import ProfileUserAddress from "../shared/ProfileUserAddress.svelte";
15
+ import ProfileUserResetPassword from "../shared/ProfileUserResetPassword.svelte";
16
+ import ProfileUserSetting from "../shared/ProfileUserSetting.svelte";
17
+
18
+ let {
19
+ data,
20
+ activeTab = $bindable(),
21
+ isLoading = false,
22
+ onLoginAsUser,
23
+ onAddAddress,
24
+ onChangePassword,
25
+ tabs: customTabs,
26
+ // Header V1
27
+ statusDefault = $t("profile-user.variant1.statusActive"),
28
+ roleDefault = $t("profile-user.variant1.roleAdministrator"),
29
+ loginAsUserLabel = $t("profile-user.variant1.loginAsUser"),
30
+ // Address
31
+ addressesTitle = $t("profile-user.variant1.addresses.title"),
32
+ addressesAddLabel = $t("profile-user.variant1.addresses.add"),
33
+ addressesDefaultBadge = $t("profile-user.variant1.addresses.defaultBadge"),
34
+ addressesEmptyText = $t("profile-user.variant1.addresses.empty"),
35
+ }: {
36
+ data: ProfileUserData;
37
+ activeTab?: string;
38
+ isLoading?: boolean;
39
+ onLoginAsUser?: (id: string | number) => void;
40
+ onAddAddress?: () => void;
41
+ onChangePassword?: (payload: {
42
+ currentPassword: string;
43
+ newPassword: string;
44
+ confirmPassword: string;
45
+ }) => void;
46
+ tabs?: { id: string; label: string }[];
47
+ // Header V1
48
+ statusDefault?: string;
49
+ roleDefault?: string;
50
+ loginAsUserLabel?: string;
51
+ // Address
52
+ addressesTitle?: string;
53
+ addressesAddLabel?: string;
54
+ addressesDefaultBadge?: string;
55
+ addressesEmptyText?: string;
56
+ } = $props();
57
+
58
+ const defaultTabs = $derived(
59
+ customTabs?.length
60
+ ? customTabs
61
+ : [
62
+ { id: "addresses", label: $t("profile-user.variant1.tabs.addresses") || "Moradas" },
63
+ { id: "security", label: $t("profile-user.variant2.tabs.security") || "Segurança" },
64
+ { id: "settings", label: $t("profile-user.variant1.tabs.settings") || "Definições" },
65
+ ]
66
+ );
67
+
68
+ const currentTab = $derived(activeTab ?? defaultTabs[0]?.id ?? "addresses");
69
+ const fullName = $derived(data.fullName ?? `${data.firstName} ${data.lastName}`);
70
+ </script>
71
+
72
+ <div class="bg-background">
73
+ <ProfileUserHeader
74
+ {data}
75
+ {isLoading}
76
+ {fullName}
77
+ {onLoginAsUser}
78
+ {statusDefault}
79
+ {roleDefault}
80
+ {loginAsUserLabel}
81
+ />
82
+
83
+ <div class="mx-auto max-w-7xl px-6 py-8">
84
+ <ProfileUserTabs
85
+ tabs={defaultTabs}
86
+ bind:activeTab
87
+ {isLoading}
88
+ />
89
+
90
+ <div class="flex flex-col gap-8">
91
+ {#if currentTab === "addresses"}
92
+ <ProfileUserAddress
93
+ addresses={data.addresses}
94
+ {isLoading}
95
+ {onAddAddress}
96
+ title={addressesTitle}
97
+ addLabel={addressesAddLabel}
98
+ defaultBadge={addressesDefaultBadge}
99
+ emptyText={addressesEmptyText}
100
+ />
101
+ {:else if currentTab === "security"}
102
+ <ProfileUserResetPassword {isLoading} {onChangePassword} />
103
+ {:else if currentTab === "settings"}
104
+ <ProfileUserSetting
105
+ notificationPref={data.notificationPref}
106
+ enableNotification={data.enableNotification}
107
+ marketingPrefs={data.marketingPrefs}
108
+ {isLoading}
109
+ />
110
+ {/if}
111
+ </div>
112
+ </div>
113
+ </div>
@@ -0,0 +1,27 @@
1
+ import type { ProfileUserData } from "../types";
2
+ type $$ComponentProps = {
3
+ data: ProfileUserData;
4
+ activeTab?: string;
5
+ isLoading?: boolean;
6
+ onLoginAsUser?: (id: string | number) => void;
7
+ onAddAddress?: () => void;
8
+ onChangePassword?: (payload: {
9
+ currentPassword: string;
10
+ newPassword: string;
11
+ confirmPassword: string;
12
+ }) => void;
13
+ tabs?: {
14
+ id: string;
15
+ label: string;
16
+ }[];
17
+ statusDefault?: string;
18
+ roleDefault?: string;
19
+ loginAsUserLabel?: string;
20
+ addressesTitle?: string;
21
+ addressesAddLabel?: string;
22
+ addressesDefaultBadge?: string;
23
+ addressesEmptyText?: string;
24
+ };
25
+ declare const ProfileUser01: import("svelte").Component<$$ComponentProps, {}, "activeTab">;
26
+ type ProfileUser01 = ReturnType<typeof ProfileUser01>;
27
+ export default ProfileUser01;
@@ -0,0 +1,83 @@
1
+ <script lang="ts" module>
2
+ /**
3
+ * Variante 02 da página de perfil. Reutiliza header,
4
+ * tabs underline, moradas, segurança e definições.
5
+ * @component
6
+ */
7
+ </script>
8
+
9
+ <script lang="ts">
10
+ import { t } from "../../../../i18n";
11
+ import type { ProfileUserData } from "../types";
12
+ import ProfileUserHeader from "../shared/ProfileUserHeader.svelte";
13
+ import ProfileUserTabs from "../shared/ProfileUserTabs.svelte";
14
+ import ProfileUserAddress from "../shared/ProfileUserAddress.svelte";
15
+ import ProfileUserResetPassword from "../shared/ProfileUserResetPassword.svelte";
16
+ import ProfileUserSetting from "../shared/ProfileUserSetting.svelte";
17
+
18
+ let {
19
+ data,
20
+ activeTab = $bindable(),
21
+ isLoading = false,
22
+ onAddAddress,
23
+ onChangePassword,
24
+ onLoginAsUser,
25
+ tabs: customTabs,
26
+ }: {
27
+ data: ProfileUserData;
28
+ activeTab?: string;
29
+ isLoading?: boolean;
30
+ onAddAddress?: () => void;
31
+ onChangePassword?: (payload: {
32
+ currentPassword: string;
33
+ newPassword: string;
34
+ confirmPassword: string;
35
+ }) => void;
36
+ onLoginAsUser?: (id: string | number) => void;
37
+ tabs?: { id: string; label: string }[];
38
+ } = $props();
39
+
40
+ const defaultTabs = $derived(
41
+ customTabs?.length
42
+ ? customTabs
43
+ : [
44
+ { id: "addresses", label: $t("profile-user.variant1.tabs.addresses") || "Moradas" },
45
+ { id: "security", label: $t("profile-user.variant2.tabs.security") || "Segurança" },
46
+ { id: "settings", label: $t("profile-user.variant1.tabs.settings") || "Definições" },
47
+ ]
48
+ );
49
+
50
+ const currentTab = $derived(activeTab ?? defaultTabs[0]?.id ?? "addresses");
51
+ const fullName = $derived(data.fullName ?? `${data.firstName} ${data.lastName}`);
52
+ </script>
53
+
54
+ <div class="bg-background">
55
+ <ProfileUserHeader {data} {isLoading} {fullName} {onLoginAsUser} />
56
+
57
+ <div class="mx-auto max-w-5xl px-6 pb-12">
58
+ <ProfileUserTabs
59
+ tabs={defaultTabs}
60
+ bind:activeTab
61
+ {isLoading}
62
+ />
63
+
64
+ <div class="flex flex-col gap-6">
65
+ {#if currentTab === "addresses"}
66
+ <ProfileUserAddress
67
+ addresses={data.addresses}
68
+ {isLoading}
69
+ {onAddAddress}
70
+ />
71
+ {:else if currentTab === "security"}
72
+ <ProfileUserResetPassword {isLoading} {onChangePassword} />
73
+ {:else if currentTab === "settings"}
74
+ <ProfileUserSetting
75
+ notificationPref={data.notificationPref}
76
+ enableNotification={data.enableNotification}
77
+ marketingPrefs={data.marketingPrefs}
78
+ {isLoading}
79
+ />
80
+ {/if}
81
+ </div>
82
+ </div>
83
+ </div>
@@ -0,0 +1,20 @@
1
+ import type { ProfileUserData } from "../types";
2
+ type $$ComponentProps = {
3
+ data: ProfileUserData;
4
+ activeTab?: string;
5
+ isLoading?: boolean;
6
+ onAddAddress?: () => void;
7
+ onChangePassword?: (payload: {
8
+ currentPassword: string;
9
+ newPassword: string;
10
+ confirmPassword: string;
11
+ }) => void;
12
+ onLoginAsUser?: (id: string | number) => void;
13
+ tabs?: {
14
+ id: string;
15
+ label: string;
16
+ }[];
17
+ };
18
+ declare const ProfileUser02: import("svelte").Component<$$ComponentProps, {}, "activeTab">;
19
+ type ProfileUser02 = ReturnType<typeof ProfileUser02>;
20
+ export default ProfileUser02;
@@ -0,0 +1,85 @@
1
+ <script lang="ts" module>
2
+ /**
3
+ * Variante 03 da página de perfil. Reutiliza header, tabs pill,
4
+ * moradas, segurança e definições.
5
+ * Todos os textos parametrizáveis com defaults via i18n.
6
+ * @component
7
+ */
8
+ </script>
9
+
10
+ <script lang="ts">
11
+ import { t } from "../../../../i18n";
12
+ import type { ProfileUserData } from "../types";
13
+ import ProfileUserHeader from "../shared/ProfileUserHeader.svelte";
14
+ import ProfileUserTabs from "../shared/ProfileUserTabs.svelte";
15
+ import ProfileUserAddress from "../shared/ProfileUserAddress.svelte";
16
+ import ProfileUserResetPassword from "../shared/ProfileUserResetPassword.svelte";
17
+ import ProfileUserSetting from "../shared/ProfileUserSetting.svelte";
18
+
19
+ let {
20
+ data,
21
+ activeTab = $bindable(),
22
+ isLoading = false,
23
+ onAddAddress,
24
+ onChangePassword,
25
+ onLoginAsUser,
26
+ tabs: customTabs,
27
+ }: {
28
+ data: ProfileUserData;
29
+ activeTab?: string;
30
+ isLoading?: boolean;
31
+ onAddAddress?: () => void;
32
+ onChangePassword?: (payload: {
33
+ currentPassword: string;
34
+ newPassword: string;
35
+ confirmPassword: string;
36
+ }) => void;
37
+ onLoginAsUser?: (id: string | number) => void;
38
+ tabs?: { id: string; label: string }[];
39
+ } = $props();
40
+
41
+ const defaultTabs = $derived(
42
+ customTabs?.length
43
+ ? customTabs
44
+ : [
45
+ { id: "addresses", label: $t("profile-user.variant1.tabs.addresses") || "Moradas" },
46
+ { id: "security", label: $t("profile-user.variant2.tabs.security") || "Segurança" },
47
+ { id: "settings", label: $t("profile-user.variant1.tabs.settings") || "Definições" },
48
+ ]
49
+ );
50
+
51
+ const currentTab = $derived(activeTab ?? defaultTabs[0]?.id ?? "addresses");
52
+ const fullName = $derived(data.fullName ?? `${data.firstName} ${data.lastName}`);
53
+ </script>
54
+
55
+ <div class="bg-background">
56
+ <ProfileUserHeader {data} {isLoading} {fullName} {onLoginAsUser} />
57
+
58
+ <div class="mx-auto max-w-7xl px-6">
59
+ <ProfileUserTabs
60
+ tabs={defaultTabs}
61
+ bind:activeTab
62
+ style="pill"
63
+ {isLoading}
64
+ />
65
+
66
+ <div class="pb-12">
67
+ {#if currentTab === "addresses"}
68
+ <ProfileUserAddress
69
+ addresses={data.addresses}
70
+ {isLoading}
71
+ {onAddAddress}
72
+ />
73
+ {:else if currentTab === "security"}
74
+ <ProfileUserResetPassword {isLoading} {onChangePassword} />
75
+ {:else if currentTab === "settings"}
76
+ <ProfileUserSetting
77
+ notificationPref={data.notificationPref}
78
+ enableNotification={data.enableNotification}
79
+ marketingPrefs={data.marketingPrefs}
80
+ {isLoading}
81
+ />
82
+ {/if}
83
+ </div>
84
+ </div>
85
+ </div>
@@ -0,0 +1,20 @@
1
+ import type { ProfileUserData } from "../types";
2
+ type $$ComponentProps = {
3
+ data: ProfileUserData;
4
+ activeTab?: string;
5
+ isLoading?: boolean;
6
+ onAddAddress?: () => void;
7
+ onChangePassword?: (payload: {
8
+ currentPassword: string;
9
+ newPassword: string;
10
+ confirmPassword: string;
11
+ }) => void;
12
+ onLoginAsUser?: (id: string | number) => void;
13
+ tabs?: {
14
+ id: string;
15
+ label: string;
16
+ }[];
17
+ };
18
+ declare const ProfileUser03: import("svelte").Component<$$ComponentProps, {}, "activeTab">;
19
+ type ProfileUser03 = ReturnType<typeof ProfileUser03>;
20
+ export default ProfileUser03;
@@ -0,0 +1,53 @@
1
+ <script lang="ts" module>
2
+ /**
3
+ * Página de perfil do utilizador com seleção de layout.
4
+ * Permite escolher entre três variantes.
5
+ * - **1**: Header com avatar à esquerda, tabs para moradas e definições.
6
+ * - **2**: Header com avatar à esquerda, tabs para segurança.
7
+ * - **3**: Header com avatar à esquerda, tabs pill para moradas, segurança e definições.
8
+ *
9
+ * @component
10
+ */
11
+ </script>
12
+
13
+ <script lang="ts">
14
+ import type { ProfileUserProps } from "./types";
15
+ import ProfileUser01 from "./01/ProfileUser01.svelte";
16
+ import ProfileUser02 from "./02/ProfileUser02.svelte";
17
+ import ProfileUser03 from "./03/ProfileUser03.svelte";
18
+
19
+ let {
20
+ varient = 1,
21
+ data,
22
+ activeTab,
23
+ isLoading = false,
24
+ tabs,
25
+ ...restProps
26
+ }: ProfileUserProps = $props();
27
+ </script>
28
+
29
+ {#if varient === 2}
30
+ <ProfileUser02
31
+ {data}
32
+ {activeTab}
33
+ {isLoading}
34
+ {tabs}
35
+ {...restProps}
36
+ />
37
+ {:else if varient === 3}
38
+ <ProfileUser03
39
+ {data}
40
+ {activeTab}
41
+ {isLoading}
42
+ {tabs}
43
+ {...restProps}
44
+ />
45
+ {:else}
46
+ <ProfileUser01
47
+ {data}
48
+ {activeTab}
49
+ {isLoading}
50
+ {tabs}
51
+ {...restProps}
52
+ />
53
+ {/if}
@@ -0,0 +1,4 @@
1
+ import type { ProfileUserProps } from "./types";
2
+ declare const ProfileUser: import("svelte").Component<ProfileUserProps, {}, "">;
3
+ type ProfileUser = ReturnType<typeof ProfileUser>;
4
+ export default ProfileUser;