@propbinder/mobile-design 0.2.50 → 0.2.53

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 (221) hide show
  1. package/fesm2022/propbinder-mobile-design.mjs +26206 -0
  2. package/fesm2022/propbinder-mobile-design.mjs.map +1 -0
  3. package/index.d.ts +8193 -0
  4. package/package.json +39 -3
  5. package/ng-package.json +0 -24
  6. package/src/animations/page-transitions.ts +0 -165
  7. package/src/components/action-list-item/ds-mobile-action-list-item.ts +0 -102
  8. package/src/components/action-list-item/index.ts +0 -2
  9. package/src/components/app-icon/ds-app-icon.ts +0 -133
  10. package/src/components/app-icon/index.ts +0 -2
  11. package/src/components/attachment-preview/ds-mobile-attachment-preview.css +0 -139
  12. package/src/components/attachment-preview/ds-mobile-attachment-preview.ts +0 -164
  13. package/src/components/attachment-preview/index.ts +0 -1
  14. package/src/components/avatar-with-badge/ds-avatar-with-badge.ts +0 -142
  15. package/src/components/avatar-with-badge/index.ts +0 -2
  16. package/src/components/booking-modal/ds-mobile-booking-confirmation-wrapper.ts +0 -71
  17. package/src/components/booking-modal/ds-mobile-booking-modal.service.ts +0 -121
  18. package/src/components/booking-modal/ds-mobile-booking-modal.ts +0 -598
  19. package/src/components/booking-modal/ds-mobile-booking-summary.ts +0 -161
  20. package/src/components/booking-modal/index.ts +0 -4
  21. package/src/components/bottom-sheet/ds-mobile-actions-bottom-sheet.ts +0 -266
  22. package/src/components/bottom-sheet/ds-mobile-bottom-sheet-header.ts +0 -146
  23. package/src/components/bottom-sheet/ds-mobile-bottom-sheet-wrapper.ts +0 -156
  24. package/src/components/bottom-sheet/ds-mobile-bottom-sheet.css +0 -101
  25. package/src/components/bottom-sheet/ds-mobile-bottom-sheet.service.ts +0 -169
  26. package/src/components/bottom-sheet/ds-mobile-confirmation-sheet.ts +0 -211
  27. package/src/components/bottom-sheet/ds-mobile-post-create-bottom-sheet.ts +0 -578
  28. package/src/components/bottom-sheet/ds-mobile-profile-actions-sheet.ts +0 -614
  29. package/src/components/bottom-sheet/index.ts +0 -8
  30. package/src/components/bottom-sheet/modal-shadow-fix.ts +0 -42
  31. package/src/components/card-inline/ds-mobile-card-inline.ts +0 -301
  32. package/src/components/card-inline/index.ts +0 -2
  33. package/src/components/card-inline-banner/ds-mobile-card-inline-banner.ts +0 -118
  34. package/src/components/card-inline-banner/index.ts +0 -1
  35. package/src/components/card-inline-contact/ds-mobile-card-inline-contact.ts +0 -120
  36. package/src/components/card-inline-contact/index.ts +0 -1
  37. package/src/components/card-inline-file/ds-mobile-card-inline-file.ts +0 -141
  38. package/src/components/card-inline-file/index.ts +0 -1
  39. package/src/components/chat-modal/ds-mobile-chat-modal.css +0 -159
  40. package/src/components/chat-modal/ds-mobile-chat-modal.service.ts +0 -105
  41. package/src/components/chat-modal/ds-mobile-chat-modal.ts +0 -918
  42. package/src/components/chat-modal/index.ts +0 -8
  43. package/src/components/comment/ds-mobile-comment.ts +0 -568
  44. package/src/components/comment/index.ts +0 -2
  45. package/src/components/contact-list-item/ds-mobile-contact-list-item.ts +0 -182
  46. package/src/components/contact-list-item/index.ts +0 -2
  47. package/src/components/content/ds-mobile-content.ts +0 -139
  48. package/src/components/content/index.ts +0 -2
  49. package/src/components/dropdown/ds-mobile-dropdown.css +0 -199
  50. package/src/components/dropdown/ds-mobile-dropdown.ts +0 -340
  51. package/src/components/dropdown/index.ts +0 -2
  52. package/src/components/ds-mobile-tabs.css +0 -407
  53. package/src/components/ds-mobile-tabs.ts +0 -216
  54. package/src/components/empty-state/ds-mobile-empty-state.ts +0 -120
  55. package/src/components/empty-state/index.ts +0 -2
  56. package/src/components/fab/ds-mobile-fab.ts +0 -315
  57. package/src/components/fab/index.ts +0 -1
  58. package/src/components/facility-creation-modal/ds-mobile-facility-creation-confirmation-wrapper.ts +0 -121
  59. package/src/components/facility-creation-modal/ds-mobile-facility-creation-modal.css +0 -189
  60. package/src/components/facility-creation-modal/ds-mobile-facility-creation-modal.service.ts +0 -135
  61. package/src/components/facility-creation-modal/ds-mobile-facility-creation-modal.ts +0 -656
  62. package/src/components/facility-creation-modal/index.ts +0 -9
  63. package/src/components/facility-creation-modal/sheets/ds-mobile-access-sheet.ts +0 -105
  64. package/src/components/facility-creation-modal/sheets/ds-mobile-price-sheet.ts +0 -188
  65. package/src/components/facility-creation-modal/sheets/ds-mobile-when-can-book-sheet.ts +0 -460
  66. package/src/components/facility-creation-modal/sheets/ds-mobile-who-can-book-sheet.ts +0 -134
  67. package/src/components/facility-detail-modal/ds-mobile-facility-detail-modal.service.ts +0 -69
  68. package/src/components/facility-detail-modal/ds-mobile-facility-detail-modal.ts +0 -379
  69. package/src/components/facility-detail-modal/index.ts +0 -2
  70. package/src/components/file-attachment/ds-mobile-file-attachment.ts +0 -164
  71. package/src/components/file-attachment/index.ts +0 -2
  72. package/src/components/handbook-detail-modal/ds-mobile-handbook-detail-modal.css +0 -214
  73. package/src/components/handbook-detail-modal/ds-mobile-handbook-detail-modal.service.ts +0 -84
  74. package/src/components/handbook-detail-modal/ds-mobile-handbook-detail-modal.ts +0 -424
  75. package/src/components/handbook-detail-modal/index.ts +0 -3
  76. package/src/components/handbook-folder/ds-mobile-handbook-folder-mini.ts +0 -175
  77. package/src/components/handbook-folder/ds-mobile-handbook-folder.ts +0 -533
  78. package/src/components/handbook-folder/index.ts +0 -4
  79. package/src/components/header-content/ds-mobile-header-content.ts +0 -222
  80. package/src/components/header-content/index.ts +0 -2
  81. package/src/components/illustration/ds-mobile-illustration.ts +0 -124
  82. package/src/components/illustration/index.ts +0 -2
  83. package/src/components/index.ts +0 -124
  84. package/src/components/inline-photo/ds-mobile-inline-photo.ts +0 -361
  85. package/src/components/inline-photo/index.ts +0 -1
  86. package/src/components/inline-tabs/ds-mobile-inline-tabs.ts +0 -132
  87. package/src/components/inline-tabs/index.ts +0 -2
  88. package/src/components/interactive-list-item-booking/ds-mobile-interactive-list-item-booking.ts +0 -350
  89. package/src/components/interactive-list-item-booking/index.ts +0 -1
  90. package/src/components/interactive-list-item-inquiry/ds-mobile-interactive-list-item-inquiry.ts +0 -321
  91. package/src/components/interactive-list-item-inquiry/index.ts +0 -2
  92. package/src/components/interactive-list-item-message/ds-mobile-interactive-list-item-message.ts +0 -237
  93. package/src/components/interactive-list-item-message/index.ts +0 -2
  94. package/src/components/interactive-list-item-post/ds-mobile-interactive-list-item-post.ts +0 -549
  95. package/src/components/interactive-list-item-post/ds-mobile-post-pdf-attachment.ts +0 -124
  96. package/src/components/interactive-list-item-post/index.ts +0 -13
  97. package/src/components/lightbox/ds-mobile-lightbox-footer.ts +0 -315
  98. package/src/components/lightbox/ds-mobile-lightbox-header.ts +0 -202
  99. package/src/components/lightbox/ds-mobile-lightbox-image.ts +0 -484
  100. package/src/components/lightbox/ds-mobile-lightbox-pdf.css +0 -377
  101. package/src/components/lightbox/ds-mobile-lightbox-pdf.ts +0 -374
  102. package/src/components/lightbox/ds-mobile-lightbox.css +0 -587
  103. package/src/components/lightbox/ds-mobile-lightbox.service.ts +0 -296
  104. package/src/components/lightbox/ds-mobile-lightbox.ts +0 -529
  105. package/src/components/lightbox/index.ts +0 -22
  106. package/src/components/list-item/ds-mobile-list-item.ts +0 -603
  107. package/src/components/list-item/index.ts +0 -2
  108. package/src/components/list-item-static/ds-mobile-list-item-static.ts +0 -133
  109. package/src/components/list-item-static/index.ts +0 -2
  110. package/src/components/loader-overlay/ds-mobile-loader-overlay.css +0 -49
  111. package/src/components/loader-overlay/ds-mobile-loader-overlay.ts +0 -77
  112. package/src/components/loader-overlay/index.ts +0 -1
  113. package/src/components/logo/ds-logo.ts +0 -95
  114. package/src/components/logo/index.ts +0 -2
  115. package/src/components/message-bubble/ds-mobile-message-bubble.ts +0 -633
  116. package/src/components/message-bubble/index.ts +0 -7
  117. package/src/components/message-composer/ds-mobile-message-composer.ts +0 -1146
  118. package/src/components/message-composer/index.ts +0 -7
  119. package/src/components/modal/ds-mobile-modal.css +0 -163
  120. package/src/components/modal/ds-mobile-modal.service.ts +0 -329
  121. package/src/components/modal/index.ts +0 -8
  122. package/src/components/modal-base/ds-mobile-modal-base.css +0 -378
  123. package/src/components/modal-base/ds-mobile-modal-base.ts +0 -261
  124. package/src/components/modal-base/index.ts +0 -2
  125. package/src/components/new-inquiry-modal/ds-mobile-new-inquiry-modal.css +0 -112
  126. package/src/components/new-inquiry-modal/ds-mobile-new-inquiry-modal.service.ts +0 -93
  127. package/src/components/new-inquiry-modal/ds-mobile-new-inquiry-modal.ts +0 -442
  128. package/src/components/new-inquiry-modal/index.ts +0 -4
  129. package/src/components/offline-banner/ds-mobile-offline-banner.ts +0 -135
  130. package/src/components/offline-banner/index.ts +0 -1
  131. package/src/components/page-details/ds-mobile-page-details.css +0 -83
  132. package/src/components/page-details/ds-mobile-page-details.ts +0 -282
  133. package/src/components/page-details/index.ts +0 -2
  134. package/src/components/page-main/ds-mobile-page-main.css +0 -68
  135. package/src/components/page-main/ds-mobile-page-main.ts +0 -421
  136. package/src/components/page-main/index.ts +0 -2
  137. package/src/components/post-composer/ds-mobile-post-composer.ts +0 -140
  138. package/src/components/post-composer/index.ts +0 -2
  139. package/src/components/post-detail-modal/ds-mobile-post-detail-modal.css +0 -390
  140. package/src/components/post-detail-modal/ds-mobile-post-detail-modal.service.ts +0 -108
  141. package/src/components/post-detail-modal/ds-mobile-post-detail-modal.ts +0 -722
  142. package/src/components/post-detail-modal/index.ts +0 -9
  143. package/src/components/property-banner/ds-mobile-property-banner.ts +0 -95
  144. package/src/components/property-banner/index.ts +0 -2
  145. package/src/components/section/ds-mobile-section.ts +0 -263
  146. package/src/components/section/index.ts +0 -2
  147. package/src/components/shared/directives/index.ts +0 -2
  148. package/src/components/shared/directives/long-press.directive.ts +0 -212
  149. package/src/components/shared/index.ts +0 -3
  150. package/src/components/shared/mobile-modal-base.ts +0 -457
  151. package/src/components/shared/mobile-page-base.ts +0 -204
  152. package/src/components/swiper/ds-mobile-swiper-with-nav.ts +0 -160
  153. package/src/components/swiper/ds-mobile-swiper.ts +0 -327
  154. package/src/components/swiper/index.ts +0 -3
  155. package/src/components/system-message-banner/ds-mobile-system-message-banner.ts +0 -129
  156. package/src/components/system-message-banner/index.ts +0 -2
  157. package/src/components/tab-bar/ds-mobile-tab-bar.css +0 -533
  158. package/src/components/tab-bar/ds-mobile-tab-bar.ts +0 -735
  159. package/src/components/tab-bar/index.ts +0 -2
  160. package/src/components/tabs/ds-mobile-tabs.css +0 -25
  161. package/src/components/tabs/ds-mobile-tabs.ts +0 -89
  162. package/src/components/tabs/index.ts +0 -2
  163. package/src/components/text-input/ds-text-input.ts +0 -287
  164. package/src/components/text-input/index.ts +0 -2
  165. package/src/examples/booking.page.ts +0 -434
  166. package/src/examples/community.page.ts +0 -776
  167. package/src/examples/handbook.page.ts +0 -324
  168. package/src/examples/home.page.ts +0 -347
  169. package/src/examples/index.ts +0 -12
  170. package/src/examples/inquiries.example.ts +0 -273
  171. package/src/examples/inquiry-detail.example.css +0 -189
  172. package/src/examples/inquiry-detail.example.ts +0 -415
  173. package/src/examples/mobile-tabs-example.component.ts +0 -208
  174. package/src/examples/post-create.page.ts +0 -311
  175. package/src/examples/post-detail.page.ts +0 -296
  176. package/src/examples/sign-in.page.ts +0 -291
  177. package/src/examples/whitelabel-demo-modal.component.ts +0 -1094
  178. package/src/examples/whitelabel-demo-modal.service.ts +0 -77
  179. package/src/models/index.ts +0 -7
  180. package/src/models/post.model.ts +0 -41
  181. package/src/pages/community.page.ts +0 -769
  182. package/src/pages/handbook.page.ts +0 -388
  183. package/src/pages/home.page.ts +0 -303
  184. package/src/pages/index.ts +0 -11
  185. package/src/pages/inquiries.example.ts +0 -273
  186. package/src/pages/inquiry-detail.example.css +0 -189
  187. package/src/pages/inquiry-detail.example.ts +0 -415
  188. package/src/pages/mobile-tabs-example.component.ts +0 -179
  189. package/src/pages/post-create.page.ts +0 -311
  190. package/src/pages/post-detail.page.ts +0 -296
  191. package/src/pages/sign-in.page.ts +0 -291
  192. package/src/pages/whitelabel-demo-modal.component.ts +0 -1094
  193. package/src/pages/whitelabel-demo-modal.service.ts +0 -77
  194. package/src/public-api.ts +0 -6
  195. package/src/services/base-modal.service.ts +0 -101
  196. package/src/services/index.ts +0 -11
  197. package/src/services/posts.service.ts +0 -542
  198. package/src/services/tracking-permission.service.ts +0 -88
  199. package/src/services/user.service.ts +0 -60
  200. package/src/services/whitelabel.service.ts +0 -675
  201. package/tsconfig.lib.json +0 -17
  202. package/tsconfig.lib.prod.json +0 -9
  203. package/tsconfig.spec.json +0 -13
  204. /package/{src/assets → assets}/fonts/Brockmann-Bold.otf +0 -0
  205. /package/{src/assets → assets}/fonts/Brockmann-BoldItalic.otf +0 -0
  206. /package/{src/assets → assets}/fonts/Brockmann-Medium.otf +0 -0
  207. /package/{src/assets → assets}/fonts/Brockmann-MediumItalic.otf +0 -0
  208. /package/{src/assets → assets}/fonts/Brockmann-Regular.otf +0 -0
  209. /package/{src/assets → assets}/fonts/Brockmann-RegularItalic.otf +0 -0
  210. /package/{src/assets → assets}/fonts/Brockmann-SemiBold.otf +0 -0
  211. /package/{src/assets → assets}/fonts/Brockmann-SemiBoldItalic.otf +0 -0
  212. /package/{src/assets → assets}/fonts/Brockmann_desktop_license.pdf +0 -0
  213. /package/{src/assets → assets}/fonts/brockmann-medium-webfont.woff2 +0 -0
  214. /package/{src/assets → assets}/fonts/brockmann-mediumitalic-webfont.woff2 +0 -0
  215. /package/{src/assets → assets}/fonts/brockmann-regular-webfont.woff2 +0 -0
  216. /package/{src/assets → assets}/fonts/brockmann-regularitalic-webfont.woff2 +0 -0
  217. /package/{src/assets → assets}/fonts/brockmann-semibold-webfont.woff2 +0 -0
  218. /package/{src/assets → assets}/fonts/brockmann-semibolditalic-webfont.woff2 +0 -0
  219. /package/{src/styles → styles}/ionic.css +0 -0
  220. /package/{src/components/shared → styles}/mobile-common.css +0 -0
  221. /package/{src/components/shared → styles}/mobile-page-base.css +0 -0
@@ -1,421 +0,0 @@
1
- import { Component, input, output, HostListener, ElementRef, ViewChild, AfterViewInit, computed, inject } from '@angular/core';
2
- import { CommonModule } from '@angular/common';
3
- import { Router } from '@angular/router';
4
- import { IonHeader, IonToolbar, IonTitle, IonContent, IonRefresher, IonRefresherContent, Platform, ModalController } from '@ionic/angular/standalone';
5
- import { Haptics, ImpactStyle } from '@capacitor/haptics';
6
- import { DsAvatarComponent } from '@propbinder/design-system';
7
- import { DsLogoComponent } from '../logo/ds-logo';
8
- import { DsMobileLoaderOverlayComponent } from '../loader-overlay';
9
- import { MobilePageBase } from '../shared/mobile-page-base';
10
- import { DsMobileProfileActionsSheetComponent, ActionResult, ActionGroup, Language } from '../bottom-sheet';
11
- import { disableModalShadowPointerEvents } from '../bottom-sheet/modal-shadow-fix';
12
- import { UserService } from '../../services/user.service';
13
- import { WhitelabelDemoModalService } from '../../pages/whitelabel-demo-modal.service';
14
-
15
- /**
16
- * DsMobilePageMainComponent
17
- *
18
- * A complete mobile page layout for main/tab pages with:
19
- * - Fixed header with logomark + title + avatar
20
- * - Purple expandable header section (scrolls with content)
21
- * - White rounded content wrapper
22
- * - Pull-to-refresh support
23
- * - Auto scroll title fade-in
24
- *
25
- * @example
26
- * ```html
27
- * <!-- Simple page -->
28
- * <ds-mobile-page-main
29
- * title="Inquiries"
30
- * [avatarInitials]="'JD'">
31
- * <div class="page-content">
32
- * <!-- Your content -->
33
- * </div>
34
- * </ds-mobile-page-main>
35
- *
36
- * <!-- Page with custom header content -->
37
- * <ds-mobile-page-main
38
- * title="Home"
39
- * headerTitle="Welcome, Lars"
40
- * headerSubtitle="Your rental property at a glance."
41
- * [avatarInitials]="'L'">
42
- *
43
- * <div header-content class="property-tiles">
44
- * <!-- Custom header content like tiles -->
45
- * </div>
46
- *
47
- * <div class="page-content">
48
- * <!-- Main page content -->
49
- * </div>
50
- * </ds-mobile-page-main>
51
- * ```
52
- */
53
- @Component({
54
- selector: 'ds-mobile-page-main',
55
- standalone: true,
56
- imports: [CommonModule, IonHeader, IonToolbar, IonTitle, IonContent, IonRefresher, IonRefresherContent, DsAvatarComponent, DsLogoComponent, DsMobileLoaderOverlayComponent],
57
- styleUrls: ['../shared/mobile-page-base.css', './ds-mobile-page-main.css'],
58
- host: {
59
- '[style.--content-wrapper-padding]': 'contentPadding()'
60
- },
61
- template: `
62
- <!-- Fixed header at top -->
63
- <ion-header>
64
- <ion-toolbar>
65
- <div class="header-main">
66
- <!-- Whitelabel logo (full in header, logomark used for app icon/avatars) -->
67
- <ds-logo variant="full" size="lg" />
68
-
69
- <!-- Title - fades in on scroll -->
70
- <ion-title class="header-main__title">{{ title() }}</ion-title>
71
-
72
- <!-- Avatar -->
73
- <div class="header-main__actions">
74
- <ds-avatar
75
- [size]="'md'"
76
- [type]="avatarType()"
77
- [initials]="avatarInitials()"
78
- [src]="avatarSrc()"
79
- [iconName]="avatarIconName()"
80
- (click)="handleAvatarClick()"
81
- style="cursor: pointer;"
82
- />
83
- </div>
84
- </div>
85
- </ion-toolbar>
86
- </ion-header>
87
-
88
- <!-- Content with expandable header -->
89
- <ion-content [scrollEvents]="true" [forceOverscroll]="true" (ionScroll)="handleScroll($event)">
90
- <!-- Condensed header for Ionic scroll effects -->
91
- @if (showCondensedHeader()) {
92
- <ion-header collapse="condense">
93
- <ion-toolbar>
94
- <ion-title size="large">{{ title() }}</ion-title>
95
- </ion-toolbar>
96
- </ion-header>
97
- }
98
-
99
- <!-- Pull to refresh (only on native iOS/Android) -->
100
- @if (showRefresh() && isNativePlatform()) {
101
- <ion-refresher slot="fixed" (ionRefresh)="handleRefresh($event)" [pullFactor]="0.4" [pullMin]="80" [pullMax]="240" closeDuration="600ms">
102
- <ion-refresher-content pullingIcon="remixArrowDownS" refreshingSpinner="crescent"> </ion-refresher-content>
103
- </ion-refresher>
104
- }
105
-
106
- <!-- Expandable header section (purple background) -->
107
- <div class="header-expandable">
108
- <div class="header-expandable-inner">
109
- <div class="header-expandable__text">
110
- <h1 class="header-expandable__title">
111
- {{ headerTitle() || title() }}
112
- </h1>
113
- @if (headerSubtitle()) {
114
- <p class="header-expandable__subtitle">{{ headerSubtitle() }}</p>
115
- }
116
- </div>
117
-
118
- <!-- Slot for custom header content (e.g., property tiles) -->
119
- <ng-content select="[header-content]"></ng-content>
120
- </div>
121
- </div>
122
-
123
- <!-- Content wrapper -->
124
- <div class="content-wrapper">
125
- @if (contentLoading()) {
126
- <ds-mobile-loader-overlay />
127
- }
128
-
129
- <!-- Offline indicator slot (appears at top of content) -->
130
- <ng-content select="[offline-indicator]"></ng-content>
131
-
132
- <div class="content-inner">
133
- <!-- Main page content -->
134
- <ng-content></ng-content>
135
- </div>
136
- </div>
137
- </ion-content>
138
- `,
139
- })
140
- export class DsMobilePageMainComponent extends MobilePageBase implements AfterViewInit {
141
- @ViewChild(IonContent) ionContent?: IonContent;
142
-
143
- // Platform detection
144
- private platform = inject(Platform);
145
- private modalController = inject(ModalController);
146
- private router = inject(Router);
147
- private userService = inject(UserService);
148
- private whitelabelDemoModal = inject(WhitelabelDemoModalService);
149
-
150
- // Computed property to check if running on native platform
151
- isNativePlatform = computed(() => this.platform.is('ios') || this.platform.is('android') || this.platform.is('capacitor'));
152
-
153
- // Inputs - Title
154
- title = input.required<string>(); // For fixed header title
155
- headerTitle = input<string>(''); // Optional different title for expandable header
156
- headerSubtitle = input<string>('');
157
-
158
- // Inputs - Avatar
159
- avatarType = input<'initials' | 'photo' | 'icon'>('initials');
160
- avatarInitials = input<string>('U');
161
- avatarSrc = input<string>('');
162
- avatarIconName = input<string>('remixUser3Line');
163
-
164
- // Inputs - Features
165
- showRefresh = input<boolean>(true);
166
- showCondensedHeader = input<boolean>(true);
167
- scrollThreshold = input<number>(160); // Pixels to scroll before title appears
168
- headerFadeDistance = input<number>(150); // Distance over which header fades out
169
-
170
- /**
171
- * Content wrapper padding
172
- * - '0' (default) - No padding, use ds-mobile-section for content organization
173
- * - '20px' - Legacy padding for content without sections
174
- * - Any custom CSS padding value
175
- *
176
- * Note: Bottom padding for safe area and tab bar is always preserved
177
- *
178
- * @example
179
- * ```html
180
- * <!-- Default: sections handle padding -->
181
- * <ds-mobile-page-main title="Home">
182
- * <ds-mobile-section>...</ds-mobile-section>
183
- * </ds-mobile-page-main>
184
- *
185
- * <!-- Legacy: content without sections -->
186
- * <ds-mobile-page-main title="Home" contentPadding="20px">
187
- * <div>Content without sections...</div>
188
- * </ds-mobile-page-main>
189
- * ```
190
- */
191
- contentPadding = input<string>('0');
192
-
193
- /**
194
- * Profile menu action groups to display when avatar is clicked.
195
- * If not provided, a default menu will be used (without Whitelabel Demo).
196
- *
197
- * @example
198
- * ```typescript
199
- * profileMenuItems: ActionGroup[] = [
200
- * {
201
- * actions: [
202
- * { action: 'profile', title: 'Min profil', icon: 'remixUser3Line' },
203
- * { action: 'settings', title: 'Indstillinger', icon: 'remixSettings3Line' }
204
- * ]
205
- * },
206
- * {
207
- * actions: [
208
- * { action: 'logout', title: 'Log ud', icon: 'remixLogoutBoxLine', destructive: true }
209
- * ]
210
- * }
211
- * ];
212
- * ```
213
- */
214
- profileMenuItems = input<ActionGroup[] | undefined>(undefined);
215
-
216
- // Outputs
217
- avatarClick = output<void>();
218
-
219
- /**
220
- * Emitted when a profile menu action is selected.
221
- * Parent component should handle the action logic (navigation, logout, etc.).
222
- */
223
- profileActionSelected = output<ActionResult>();
224
-
225
- refresh = output<any>();
226
- scroll = output<any>();
227
-
228
- constructor(private elementRef: ElementRef) {
229
- super();
230
- }
231
-
232
- ngAfterViewInit(): void {
233
- // Initialize network monitoring
234
- this.initNetworkMonitoring(this.isNativePlatform());
235
- }
236
-
237
- /**
238
- * Handle avatar click - opens profile actions bottom sheet
239
- */
240
- async handleAvatarClick(): Promise<void> {
241
- // Emit the event for any parent listeners
242
- this.avatarClick.emit();
243
-
244
- // Use input if provided, otherwise fall back to service, otherwise use default menu
245
- const menuItems = this.profileMenuItems() ||
246
- this.userService.profileMenuItems() || [
247
- {
248
- actions: [
249
- {
250
- action: 'profile',
251
- title: 'Min profil',
252
- icon: 'remixUser3Line',
253
- destructive: false,
254
- },
255
- {
256
- action: 'settings',
257
- title: 'Indstillinger',
258
- icon: 'remixSettings3Line',
259
- destructive: false,
260
- },
261
- {
262
- action: 'appearance',
263
- title: 'Udseende',
264
- icon: 'remixPaletteLine',
265
- destructive: false,
266
- },
267
- ],
268
- },
269
- {
270
- actions: [
271
- {
272
- action: 'language',
273
- title: 'Sprog',
274
- subtitle: 'Dansk',
275
- flagIcon: '/Assets/country-flags/denmark.svg',
276
- icon: 'remixGlobalLine',
277
- destructive: false,
278
- showChevron: true,
279
- },
280
- ],
281
- },
282
- {
283
- actions: [
284
- {
285
- action: 'logout',
286
- title: 'Log ud',
287
- icon: 'remixLogoutBoxLine',
288
- destructive: true,
289
- },
290
- ],
291
- },
292
- ];
293
-
294
- // If no menu items configured, just emit and return
295
- if (!menuItems || menuItems.length === 0) {
296
- return;
297
- }
298
-
299
- const sheet = await this.modalController.create({
300
- component: DsMobileProfileActionsSheetComponent,
301
- componentProps: {
302
- actionGroups: menuItems,
303
- currentLanguage: 'da', // TODO: Get from language service
304
- availableLanguages: [
305
- {
306
- code: 'da',
307
- nativeName: 'Dansk',
308
- englishName: 'Danish',
309
- flagIcon: '/Assets/country-flags/denmark.svg',
310
- },
311
- {
312
- code: 'en',
313
- nativeName: 'English',
314
- englishName: 'English',
315
- flagIcon: '/Assets/country-flags/united kingdom.svg',
316
- },
317
- {
318
- code: 'sv',
319
- nativeName: 'Svenska',
320
- englishName: 'Swedish',
321
- flagIcon: '/Assets/country-flags/sweden.svg',
322
- },
323
- {
324
- code: 'no',
325
- nativeName: 'Norsk',
326
- englishName: 'Norwegian',
327
- flagIcon: '/Assets/country-flags/norway.svg',
328
- },
329
- {
330
- code: 'de',
331
- nativeName: 'Deutsch',
332
- englishName: 'German',
333
- flagIcon: '/Assets/country-flags/germany.svg',
334
- },
335
- ],
336
- },
337
- breakpoints: [0, 1],
338
- initialBreakpoint: 1,
339
- handle: true,
340
- cssClass: ['ds-bottom-sheet', 'auto-height'],
341
- });
342
-
343
- await sheet.present();
344
- disableModalShadowPointerEvents(sheet);
345
-
346
- const result = await sheet.onWillDismiss<ActionResult>();
347
- if (result.data?.action) {
348
- // Handle appearance/whitelabel-demo action internally (works on all pages)
349
- if (result.data.action === 'appearance' || result.data.action === 'whitelabel-demo') {
350
- // Small delay to ensure bottom sheet is fully dismissed
351
- setTimeout(async () => {
352
- try {
353
- await this.whitelabelDemoModal.open();
354
- } catch (error) {
355
- console.error('Failed to open whitelabel demo modal:', error);
356
- }
357
- }, 100);
358
- }
359
-
360
- // Emit the selected action to parent (for other actions)
361
- this.profileActionSelected.emit(result.data);
362
- // Also notify globally via UserService
363
- this.userService.notifyProfileAction(result.data);
364
- }
365
- }
366
-
367
- /**
368
- * Handle scroll events
369
- * - Shows title in fixed header when scrolled past threshold
370
- * - Fades out expandable header content based on scroll position
371
- * - Emits scroll event for custom handling
372
- */
373
- handleScroll(event: any): void {
374
- const scrollTop = event.detail.scrollTop;
375
- const header = this.elementRef.nativeElement.querySelector('ion-header:not([collapse])');
376
- const headerExpandable = this.elementRef.nativeElement.querySelector('.header-expandable');
377
-
378
- // Show title in fixed header when scrolled past threshold
379
- if (scrollTop > this.scrollThreshold()) {
380
- header?.classList.add('header-scrolled');
381
- } else {
382
- header?.classList.remove('header-scrolled');
383
- }
384
-
385
- // Fade out header-expandable content based on scroll
386
- if (headerExpandable) {
387
- const fadeDistance = this.headerFadeDistance();
388
- const fadeProgress = Math.min(scrollTop / fadeDistance, 1);
389
-
390
- // Calculate opacity (1 to 0)
391
- const opacity = 1 - fadeProgress;
392
-
393
- // Calculate transform (0px to -20px upward)
394
- const translateY = fadeProgress * -20;
395
-
396
- // Apply styles
397
- headerExpandable.style.opacity = opacity.toString();
398
- headerExpandable.style.transform = `translateY(${translateY}px)`;
399
- }
400
-
401
- this.scroll.emit(event);
402
- }
403
-
404
- /**
405
- * Handle pull-to-refresh
406
- * Emits refresh event - parent should call event.target.complete()
407
- */
408
- async handleRefresh(event: any): Promise<void> {
409
- // Haptic feedback for pull-to-refresh
410
- try {
411
- await Haptics.impact({ style: ImpactStyle.Medium });
412
- } catch {
413
- // Fallback to Web Vibration API if Capacitor Haptics is not available
414
- if ('vibrate' in navigator) {
415
- navigator.vibrate(50);
416
- }
417
- }
418
-
419
- this.refresh.emit(event);
420
- }
421
- }
@@ -1,2 +0,0 @@
1
- export * from './ds-mobile-page-main';
2
-
@@ -1,140 +0,0 @@
1
- import { Component, input, output } from '@angular/core';
2
- import { CommonModule } from '@angular/common';
3
- import { DsAvatarComponent } from '@propbinder/design-system';
4
-
5
- /**
6
- * DsMobilePostComposerComponent
7
- *
8
- * A "fake" input composer for creating new posts in the community feed.
9
- * Features a user avatar, placeholder input, and post button.
10
- * Clicking opens the full post creation modal/page.
11
- *
12
- * @example
13
- * ```html
14
- * <ds-mobile-post-composer
15
- * [avatarInitials]="'LM'"
16
- * [avatarType]="'photo'"
17
- * [avatarSrc]="'...'"
18
- * (composerClick)="openPostCreator()">
19
- * </ds-mobile-post-composer>
20
- * ```
21
- */
22
- @Component({
23
- selector: 'ds-mobile-post-composer',
24
- standalone: true,
25
- imports: [CommonModule, DsAvatarComponent],
26
- host: {
27
- '(click)': 'handleClick()'
28
- },
29
- styles: [`
30
- :host {
31
- display: block;
32
- max-width: 640px;
33
- cursor: pointer;
34
- transition: all 0.2s ease;
35
- }
36
-
37
- .composer-container {
38
- display: flex;
39
- align-items: center;
40
- gap: 12px;
41
- }
42
-
43
- .composer-input-wrapper {
44
- flex: 1;
45
- min-width: 0;
46
- }
47
-
48
- .composer-input {
49
- width: 100%;
50
- background: rgba(var(--header-content-color-rgb, 255, 255, 255), 0.1);
51
- border: none;
52
- border-radius: 24px;
53
- padding: 10px 16px;
54
- font-family: 'Brockmann', sans-serif;
55
- font-size: var(--font-size-sm);
56
- font-weight: 400;
57
- line-height: 20px;
58
- letter-spacing: -0.3px;
59
- color: rgba(var(--header-content-color-rgb, 255, 255, 255), 0.75);
60
- outline: none;
61
- cursor: pointer;
62
- transition: all 0.2s ease;
63
- pointer-events: none;
64
- user-select: none;
65
- }
66
-
67
- .composer-input::placeholder {
68
- color: rgba(var(--header-content-color-rgb, 255, 255, 255), 0.75);
69
- opacity: 1;
70
- }
71
-
72
- /* Hover effects for desktop */
73
- @media (hover: hover) {
74
- :host:hover .composer-input {
75
- opacity: 0.8;
76
- }
77
- }
78
- `],
79
- template: `
80
- <div class="composer-container">
81
- <ds-avatar
82
- [initials]="avatarInitials()"
83
- [type]="avatarType()"
84
- [src]="avatarSrc()"
85
- [iconName]="avatarIconName()"
86
- size="md" />
87
-
88
- <div class="composer-input-wrapper">
89
- <input
90
- type="text"
91
- class="composer-input"
92
- [placeholder]="placeholder()"
93
- readonly
94
- tabindex="-1"
95
- />
96
- </div>
97
- </div>
98
- `
99
- })
100
- export class DsMobilePostComposerComponent {
101
- /**
102
- * Avatar initials (for initials type)
103
- */
104
- avatarInitials = input<string>('');
105
-
106
- /**
107
- * Avatar type
108
- */
109
- avatarType = input<'initials' | 'photo' | 'icon'>('initials');
110
-
111
- /**
112
- * Avatar photo source (for photo type)
113
- */
114
- avatarSrc = input<string>('');
115
-
116
- /**
117
- * Icon name (for icon type avatars)
118
- */
119
- avatarIconName = input<string>('remixUser3Fill');
120
-
121
- /**
122
- * Placeholder text for the input
123
- */
124
- placeholder = input<string>("Hvad er nyt?");
125
-
126
- /**
127
- * Text for the post button
128
- */
129
- buttonText = input<string>('Slå op');
130
-
131
- /**
132
- * Emits when the composer is clicked
133
- */
134
- composerClick = output<void>();
135
-
136
- handleClick(): void {
137
- this.composerClick.emit();
138
- }
139
- }
140
-
@@ -1,2 +0,0 @@
1
- export * from './ds-mobile-post-composer';
2
-