@ionic/core 8.8.19-dev.11786730389.1a1927bf → 8.8.19-dev.11786735826.1fad7c0a
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/components/ion-action-sheet.js +1 -1
- package/components/ion-alert.js +1 -1
- package/components/ion-back-button.js +1 -1
- package/components/ion-button.js +1 -1
- package/components/ion-card.js +1 -1
- package/components/ion-chip.js +1 -1
- package/components/ion-datetime-button.js +1 -1
- package/components/ion-datetime.js +1 -1
- package/components/ion-fab-button.js +1 -1
- package/components/ion-infinite-scroll-content.js +1 -1
- package/components/ion-input-otp.js +1 -1
- package/components/ion-input-password-toggle.js +1 -1
- package/components/ion-input.js +1 -1
- package/components/ion-item-divider.js +1 -1
- package/components/ion-item-group.js +1 -1
- package/components/ion-item-option.js +1 -1
- package/components/ion-item-options.js +1 -1
- package/components/ion-item-sliding.js +1 -1
- package/components/ion-item.js +1 -1
- package/components/ion-label.js +1 -1
- package/components/ion-list-header.js +1 -1
- package/components/ion-list.js +1 -1
- package/components/ion-loading.js +1 -1
- package/components/ion-menu-button.js +1 -1
- package/components/ion-menu-toggle.js +1 -1
- package/components/ion-menu.js +1 -1
- package/components/ion-modal.js +1 -1
- package/components/ion-nav-link.js +1 -1
- package/components/ion-nav.js +1 -1
- package/components/ion-note.js +1 -1
- package/components/ion-picker-column-option.js +1 -1
- package/components/ion-popover.js +1 -1
- package/components/ion-progress-bar.js +1 -1
- package/components/ion-radio-group.js +1 -1
- package/components/ion-radio.js +1 -1
- package/components/ion-range.js +1 -1
- package/components/ion-refresher-content.js +1 -1
- package/components/ion-refresher.js +1 -1
- package/components/ion-reorder-group.js +1 -1
- package/components/ion-reorder.js +1 -1
- package/components/ion-ripple-effect.js +1 -1
- package/components/ion-router-link.js +1 -1
- package/components/ion-router-outlet.js +1 -1
- package/components/ion-row.js +1 -1
- package/components/ion-searchbar.js +1 -1
- package/components/ion-segment-button.js +1 -1
- package/components/ion-segment-content.js +1 -1
- package/components/ion-segment-view.js +1 -1
- package/components/ion-segment.js +1 -1
- package/components/ion-select-modal.js +1 -1
- package/components/ion-select-option.js +1 -1
- package/components/ion-select-popover.js +1 -1
- package/components/ion-select.js +1 -1
- package/components/ion-skeleton-text.js +1 -1
- package/components/ion-spinner.js +1 -1
- package/components/ion-split-pane.js +1 -1
- package/components/ion-tab-bar.js +1 -1
- package/components/ion-tab-button.js +1 -1
- package/components/ion-tab.js +1 -1
- package/components/ion-tabs.js +1 -1
- package/components/ion-text.js +1 -1
- package/components/ion-textarea.js +1 -1
- package/components/ion-thumbnail.js +1 -1
- package/components/ion-title.js +1 -1
- package/components/ion-toast.js +1 -1
- package/components/ion-toggle.js +1 -1
- package/components/ion-toolbar.js +1 -1
- package/components/{p-C1O9GEug.js → p--m5cCjbK.js} +1 -1
- package/components/{p-CfnGxjv-.js → p-B4uHHhPK.js} +1 -1
- package/components/{p-BxUIQcD9.js → p-BOvLNVKq.js} +1 -1
- package/components/{p-D_XD0pVT.js → p-BWBigMsI.js} +1 -1
- package/components/{p-xOjr4bwc.js → p-BZ4-QTes.js} +1 -1
- package/components/{p-tYCT3JGl.js → p-BjluhQMI.js} +1 -1
- package/components/{p-ClFYbgND.js → p-BlsIikdZ.js} +1 -1
- package/components/{p-Obm7si-x.js → p-Blug1Vxu.js} +1 -1
- package/components/{p-DTY4otpr.js → p-C91npEel.js} +1 -1
- package/components/{p-CVnwvOBD.js → p-CVb3x_r3.js} +1 -1
- package/components/{p-B6dUPQXq.js → p-CWLrHG8Y.js} +1 -1
- package/components/{p-0Pyit076.js → p-CfnNZz_d.js} +1 -1
- package/components/{p-DyePCNGr.js → p-DKrhJJV0.js} +1 -1
- package/components/p-DSzSbVP2.js +4 -0
- package/components/{p-BsVxQGUT.js → p-DgZOZQjJ.js} +1 -1
- package/components/{p-BO4sUqUv.js → p-Dmd2xqCe.js} +1 -1
- package/components/{p-83oP9gzn.js → p-GG5GhznE.js} +1 -1
- package/components/{p-Bc4wROfM.js → p-UQSiXX2Z.js} +1 -1
- package/components/{p-Dm7h4Nyv.js → p-qT1szVjw.js} +1 -1
- package/components/p-ypuYdSDB.js +4 -0
- package/dist/cjs/input.utils-BZdMWVrt.js +35 -0
- package/dist/cjs/ion-app_8.cjs.entry.js +5 -5
- package/dist/cjs/ion-avatar_3.cjs.entry.js +1 -1
- package/dist/cjs/ion-col_3.cjs.entry.js +1 -1
- package/dist/cjs/ion-input-otp.cjs.entry.js +3 -3
- package/dist/cjs/ion-input-password-toggle.cjs.entry.js +3 -3
- package/dist/cjs/ion-input.cjs.entry.js +42 -56
- package/dist/cjs/ion-item-option_3.cjs.entry.js +4 -4
- package/dist/cjs/ion-item_8.cjs.entry.js +12 -12
- package/dist/cjs/ion-loading.cjs.entry.js +2 -2
- package/dist/cjs/ion-menu_3.cjs.entry.js +6 -6
- package/dist/cjs/ion-modal.cjs.entry.js +4 -4
- package/dist/cjs/ion-nav_2.cjs.entry.js +2 -2
- package/dist/cjs/ion-picker-column-option.cjs.entry.js +2 -2
- package/dist/cjs/ion-popover.cjs.entry.js +2 -2
- package/dist/cjs/ion-progress-bar.cjs.entry.js +1 -1
- package/dist/cjs/ion-radio_2.cjs.entry.js +4 -4
- package/dist/cjs/ion-range.cjs.entry.js +3 -3
- package/dist/cjs/ion-refresher_2.cjs.entry.js +2 -2
- package/dist/cjs/ion-reorder_2.cjs.entry.js +2 -2
- package/dist/cjs/ion-ripple-effect.cjs.entry.js +1 -1
- package/dist/cjs/ion-route_4.cjs.entry.js +2 -2
- package/dist/cjs/ion-searchbar.cjs.entry.js +4 -4
- package/dist/cjs/ion-segment-content.cjs.entry.js +1 -1
- package/dist/cjs/ion-segment-view.cjs.entry.js +2 -2
- package/dist/cjs/ion-segment_2.cjs.entry.js +4 -4
- package/dist/cjs/ion-select-modal.cjs.entry.js +1 -1
- package/dist/cjs/ion-select_3.cjs.entry.js +41 -59
- package/dist/cjs/ion-spinner.cjs.entry.js +1 -1
- package/dist/cjs/ion-split-pane.cjs.entry.js +2 -2
- package/dist/cjs/ion-tab-bar_2.cjs.entry.js +4 -4
- package/dist/cjs/ion-tab_2.cjs.entry.js +3 -3
- package/dist/cjs/ion-text.cjs.entry.js +2 -2
- package/dist/cjs/ion-textarea.cjs.entry.js +44 -55
- package/dist/cjs/ion-toast.cjs.entry.js +2 -2
- package/dist/cjs/ion-toggle.cjs.entry.js +4 -4
- package/dist/cjs/slot-mutation-controller-CgTGFqlW.js +397 -0
- package/dist/collection/components/input/input.ios.css +56 -24
- package/dist/collection/components/input/input.js +36 -51
- package/dist/collection/components/input/input.md.css +78 -41
- package/dist/collection/components/input-otp/input-otp.js +3 -3
- package/dist/collection/components/input-password-toggle/input-password-toggle.js +3 -3
- package/dist/collection/components/item-divider/item-divider.js +2 -2
- package/dist/collection/components/item-group/item-group.js +1 -1
- package/dist/collection/components/item-option/item-option.js +2 -2
- package/dist/collection/components/item-options/item-options.js +1 -1
- package/dist/collection/components/item-sliding/item-sliding.js +1 -1
- package/dist/collection/components/label/label.js +2 -2
- package/dist/collection/components/list/list.js +1 -1
- package/dist/collection/components/list-header/list-header.js +2 -2
- package/dist/collection/components/loading/loading.js +2 -2
- package/dist/collection/components/menu/menu.js +2 -2
- package/dist/collection/components/menu-button/menu-button.js +2 -2
- package/dist/collection/components/menu-toggle/menu-toggle.js +2 -2
- package/dist/collection/components/modal/modal.js +4 -4
- package/dist/collection/components/nav/nav.js +1 -1
- package/dist/collection/components/nav-link/nav-link.js +1 -1
- package/dist/collection/components/note/note.js +2 -2
- package/dist/collection/components/picker-column-option/picker-column-option.js +2 -2
- package/dist/collection/components/popover/popover.js +2 -2
- package/dist/collection/components/progress-bar/progress-bar.js +1 -1
- package/dist/collection/components/radio/radio.js +3 -3
- package/dist/collection/components/radio-group/radio-group.js +1 -1
- package/dist/collection/components/range/range.js +3 -3
- package/dist/collection/components/refresher/refresher.js +1 -1
- package/dist/collection/components/refresher-content/refresher-content.js +1 -1
- package/dist/collection/components/reorder/reorder.js +1 -1
- package/dist/collection/components/reorder-group/reorder-group.js +1 -1
- package/dist/collection/components/ripple-effect/ripple-effect.js +1 -1
- package/dist/collection/components/router-link/router-link.js +2 -2
- package/dist/collection/components/router-outlet/router-outlet.js +1 -1
- package/dist/collection/components/row/row.js +1 -1
- package/dist/collection/components/searchbar/searchbar.js +4 -4
- package/dist/collection/components/segment/segment.js +2 -2
- package/dist/collection/components/segment-button/segment-button.js +2 -2
- package/dist/collection/components/segment-content/segment-content.js +1 -1
- package/dist/collection/components/segment-view/segment-view.js +2 -2
- package/dist/collection/components/select/select.ios.css +63 -69
- package/dist/collection/components/select/select.js +40 -55
- package/dist/collection/components/select/select.md.css +85 -85
- package/dist/collection/components/select-modal/select-modal.js +1 -1
- package/dist/collection/components/select-option/select-option.js +1 -1
- package/dist/collection/components/select-popover/select-popover.js +1 -1
- package/dist/collection/components/skeleton-text/skeleton-text.js +2 -2
- package/dist/collection/components/spinner/spinner.js +1 -1
- package/dist/collection/components/split-pane/split-pane.js +2 -2
- package/dist/collection/components/tab/tab.js +2 -2
- package/dist/collection/components/tab-bar/tab-bar.js +2 -2
- package/dist/collection/components/tab-button/tab-button.js +2 -2
- package/dist/collection/components/tabs/tabs.js +1 -1
- package/dist/collection/components/text/text.js +2 -2
- package/dist/collection/components/textarea/textarea.ios.css +94 -62
- package/dist/collection/components/textarea/textarea.js +39 -51
- package/dist/collection/components/textarea/textarea.md.css +103 -77
- package/dist/collection/components/thumbnail/thumbnail.js +1 -1
- package/dist/collection/components/title/title.js +2 -2
- package/dist/collection/components/toast/toast.js +2 -2
- package/dist/collection/components/toggle/toggle.js +3 -3
- package/dist/collection/components/toolbar/toolbar.js +2 -2
- package/dist/collection/utils/forms/index.js +1 -0
- package/dist/collection/utils/forms/start-container-controller.js +132 -0
- package/dist/docs.json +22 -6
- package/dist/esm/input.utils-B1ValN_N.js +33 -0
- package/dist/esm/ion-app_8.entry.js +5 -5
- package/dist/esm/ion-avatar_3.entry.js +1 -1
- package/dist/esm/ion-col_3.entry.js +1 -1
- package/dist/esm/ion-input-otp.entry.js +3 -3
- package/dist/esm/ion-input-password-toggle.entry.js +3 -3
- package/dist/esm/ion-input.entry.js +40 -54
- package/dist/esm/ion-item-option_3.entry.js +4 -4
- package/dist/esm/ion-item_8.entry.js +12 -12
- package/dist/esm/ion-loading.entry.js +2 -2
- package/dist/esm/ion-menu_3.entry.js +6 -6
- package/dist/esm/ion-modal.entry.js +4 -4
- package/dist/esm/ion-nav_2.entry.js +2 -2
- package/dist/esm/ion-picker-column-option.entry.js +2 -2
- package/dist/esm/ion-popover.entry.js +2 -2
- package/dist/esm/ion-progress-bar.entry.js +1 -1
- package/dist/esm/ion-radio_2.entry.js +4 -4
- package/dist/esm/ion-range.entry.js +3 -3
- package/dist/esm/ion-refresher_2.entry.js +2 -2
- package/dist/esm/ion-reorder_2.entry.js +2 -2
- package/dist/esm/ion-ripple-effect.entry.js +1 -1
- package/dist/esm/ion-route_4.entry.js +2 -2
- package/dist/esm/ion-searchbar.entry.js +4 -4
- package/dist/esm/ion-segment-content.entry.js +1 -1
- package/dist/esm/ion-segment-view.entry.js +2 -2
- package/dist/esm/ion-segment_2.entry.js +4 -4
- package/dist/esm/ion-select-modal.entry.js +1 -1
- package/dist/esm/ion-select_3.entry.js +40 -58
- package/dist/esm/ion-spinner.entry.js +1 -1
- package/dist/esm/ion-split-pane.entry.js +2 -2
- package/dist/esm/ion-tab-bar_2.entry.js +4 -4
- package/dist/esm/ion-tab_2.entry.js +3 -3
- package/dist/esm/ion-text.entry.js +2 -2
- package/dist/esm/ion-textarea.entry.js +43 -54
- package/dist/esm/ion-toast.entry.js +2 -2
- package/dist/esm/ion-toggle.entry.js +4 -4
- package/dist/esm/slot-mutation-controller-u741eD3Z.js +393 -0
- package/dist/ionic/ionic.esm.js +1 -1
- package/dist/ionic/{p-dbfd2d52.entry.js → p-06533d51.entry.js} +1 -1
- package/dist/ionic/{p-a641d428.entry.js → p-141f5b47.entry.js} +1 -1
- package/dist/ionic/p-14a5e8f5.entry.js +4 -0
- package/dist/ionic/{p-12589d59.entry.js → p-19269e04.entry.js} +1 -1
- package/dist/ionic/{p-efef6788.entry.js → p-19abbc33.entry.js} +1 -1
- package/dist/ionic/{p-5394e1d4.entry.js → p-4204184c.entry.js} +1 -1
- package/dist/ionic/p-4bc3ecdb.entry.js +4 -0
- package/dist/ionic/{p-21a7fb2a.entry.js → p-4eed9ca1.entry.js} +1 -1
- package/dist/ionic/p-5521dc1f.entry.js +4 -0
- package/dist/ionic/p-5c3626de.entry.js +4 -0
- package/dist/ionic/{p-374b10cb.entry.js → p-5d3b411c.entry.js} +1 -1
- package/dist/ionic/p-60576951.entry.js +4 -0
- package/dist/ionic/{p-1d2e53e8.entry.js → p-711a8319.entry.js} +1 -1
- package/dist/ionic/{p-48b6835f.entry.js → p-71419a55.entry.js} +1 -1
- package/dist/ionic/{p-ba8a598f.entry.js → p-79325ffe.entry.js} +1 -1
- package/dist/ionic/p-84a38904.entry.js +4 -0
- package/dist/ionic/{p-bf7c1f05.entry.js → p-8f204f1e.entry.js} +1 -1
- package/dist/ionic/p-9055e897.entry.js +4 -0
- package/dist/ionic/{p-6277efba.entry.js → p-9658e083.entry.js} +1 -1
- package/dist/ionic/{p-74f30659.entry.js → p-988baee1.entry.js} +1 -1
- package/dist/ionic/p-DAztxQR0.js +4 -0
- package/dist/ionic/p-DkUB-ROc.js +4 -0
- package/dist/ionic/{p-3835a020.entry.js → p-a71232d6.entry.js} +1 -1
- package/dist/ionic/{p-08f1ed1c.entry.js → p-a73d8742.entry.js} +1 -1
- package/dist/ionic/{p-8a21bdbd.entry.js → p-a8421d18.entry.js} +1 -1
- package/dist/ionic/{p-2ce59395.entry.js → p-a8c2c343.entry.js} +1 -1
- package/dist/ionic/{p-c3f65965.entry.js → p-bc2bad5f.entry.js} +1 -1
- package/dist/ionic/{p-f622796d.entry.js → p-be08d500.entry.js} +1 -1
- package/dist/ionic/p-be9a4f51.entry.js +4 -0
- package/dist/ionic/{p-33829e94.entry.js → p-ccc5044d.entry.js} +1 -1
- package/dist/ionic/{p-3c5fdd27.entry.js → p-ce32912b.entry.js} +1 -1
- package/dist/ionic/p-ded69ceb.entry.js +4 -0
- package/dist/ionic/{p-cec87704.entry.js → p-e0c6e31e.entry.js} +1 -1
- package/dist/ionic/{p-09b47b7d.entry.js → p-e8c3e08a.entry.js} +1 -1
- package/dist/ionic/{p-8f3a1995.entry.js → p-ed5d540d.entry.js} +1 -1
- package/dist/ionic/{p-6b286c5c.entry.js → p-f2802440.entry.js} +1 -1
- package/dist/ionic/{p-62e71297.entry.js → p-fe1bfbcf.entry.js} +1 -1
- package/dist/types/components/input/input.d.ts +11 -5
- package/dist/types/components/select/select.d.ts +12 -6
- package/dist/types/components/textarea/textarea.d.ts +12 -5
- package/dist/types/utils/forms/index.d.ts +1 -0
- package/dist/types/utils/forms/start-container-controller.d.ts +34 -0
- package/hydrate/index.js +350 -267
- package/hydrate/index.mjs +350 -267
- package/package.json +4 -4
- package/components/p-DIgGHN7D.js +0 -4
- package/components/p-MCJ7HjWe.js +0 -4
- package/dist/cjs/input.utils-CP4fzrqk.js +0 -149
- package/dist/cjs/notch-controller-BEUpEgb5.js +0 -155
- package/dist/esm/input.utils-J6HWocLA.js +0 -146
- package/dist/esm/notch-controller-CrUGyHYz.js +0 -153
- package/dist/ionic/p-0266b7e1.entry.js +0 -4
- package/dist/ionic/p-214e000a.entry.js +0 -4
- package/dist/ionic/p-91c6faf1.entry.js +0 -4
- package/dist/ionic/p-9b865fe6.entry.js +0 -4
- package/dist/ionic/p-BnMQxWON.js +0 -4
- package/dist/ionic/p-ac6ef997.entry.js +0 -4
- package/dist/ionic/p-b24dc0a1.entry.js +0 -4
- package/dist/ionic/p-c8fbe544.entry.js +0 -4
- package/dist/ionic/p-cb12f6c3.entry.js +0 -4
- package/dist/ionic/p-ede019ef.entry.js +0 -4
- package/dist/ionic/p-kJA95YWg.js +0 -4
|
@@ -112,20 +112,6 @@
|
|
|
112
112
|
box-sizing: border-box;
|
|
113
113
|
}
|
|
114
114
|
|
|
115
|
-
/**
|
|
116
|
-
* Since the label sits on top of the element,
|
|
117
|
-
* the component needs to be taller otherwise the
|
|
118
|
-
* label will appear too close to the textarea text.
|
|
119
|
-
* Also, floating and stacked labels should not
|
|
120
|
-
* push the label down since it it
|
|
121
|
-
* sits on top of the textarea.
|
|
122
|
-
*/
|
|
123
|
-
:host(.textarea-label-placement-floating),
|
|
124
|
-
:host(.textarea-label-placement-stacked) {
|
|
125
|
-
--padding-top: 0px;
|
|
126
|
-
min-height: 56px;
|
|
127
|
-
}
|
|
128
|
-
|
|
129
115
|
/**
|
|
130
116
|
* When the cols property is set we should
|
|
131
117
|
* respect that width instead of defaulting
|
|
@@ -248,8 +234,8 @@
|
|
|
248
234
|
padding-inline-start: var(--padding-start);
|
|
249
235
|
-webkit-padding-end: var(--padding-end);
|
|
250
236
|
padding-inline-end: var(--padding-end);
|
|
251
|
-
padding-top:
|
|
252
|
-
padding-bottom:
|
|
237
|
+
padding-top: 0;
|
|
238
|
+
padding-bottom: 0;
|
|
253
239
|
border-radius: var(--border-radius);
|
|
254
240
|
display: flex;
|
|
255
241
|
position: relative;
|
|
@@ -262,23 +248,46 @@
|
|
|
262
248
|
line-height: normal;
|
|
263
249
|
}
|
|
264
250
|
|
|
251
|
+
.textarea-control {
|
|
252
|
+
padding-left: 0;
|
|
253
|
+
padding-right: 0;
|
|
254
|
+
padding-top: var(--padding-top);
|
|
255
|
+
padding-bottom: var(--padding-bottom);
|
|
256
|
+
display: flex;
|
|
257
|
+
flex-grow: 1;
|
|
258
|
+
align-items: start;
|
|
259
|
+
align-self: stretch;
|
|
260
|
+
width: 100%;
|
|
261
|
+
/**
|
|
262
|
+
* Allows the control to shrink below the label and textarea's intrinsic
|
|
263
|
+
* width, preventing the start and end slots from being pushed outside
|
|
264
|
+
* the wrapper. The label and textarea truncate independently, so it can
|
|
265
|
+
* use whatever space remains after accounting for the slots.
|
|
266
|
+
*/
|
|
267
|
+
min-width: 0;
|
|
268
|
+
}
|
|
269
|
+
|
|
265
270
|
.native-wrapper {
|
|
266
271
|
position: relative;
|
|
267
272
|
width: 100%;
|
|
268
273
|
height: 100%;
|
|
269
274
|
}
|
|
270
275
|
|
|
271
|
-
|
|
272
|
-
|
|
276
|
+
/**
|
|
277
|
+
* When the label sits beside the textarea, the label should size to its content
|
|
278
|
+
* and the textarea should take the remaining space. A zero flex basis prevents
|
|
279
|
+
* the textarea from requesting its full width and forcing the label to shrink.
|
|
280
|
+
* Stacked and floating placements use a column layout, so their flex basis
|
|
281
|
+
* controls height instead and does not need to be overridden.
|
|
282
|
+
*/
|
|
283
|
+
:host(.textarea-label-placement-start) .native-wrapper,
|
|
284
|
+
:host(.textarea-label-placement-end) .native-wrapper,
|
|
285
|
+
:host(.textarea-label-placement-fixed) .native-wrapper {
|
|
286
|
+
flex: 1 1 0;
|
|
273
287
|
}
|
|
274
288
|
|
|
275
|
-
.
|
|
276
|
-
-
|
|
277
|
-
padding-inline-start: 0px;
|
|
278
|
-
-webkit-padding-end: 0px;
|
|
279
|
-
padding-inline-end: 0px;
|
|
280
|
-
padding-top: var(--padding-top);
|
|
281
|
-
padding-bottom: var(--padding-bottom);
|
|
289
|
+
:host(.has-focus) textarea {
|
|
290
|
+
caret-color: var(--highlight-color);
|
|
282
291
|
}
|
|
283
292
|
|
|
284
293
|
.native-wrapper {
|
|
@@ -305,8 +314,8 @@
|
|
|
305
314
|
.native-wrapper::after {
|
|
306
315
|
padding-left: 0;
|
|
307
316
|
padding-right: 0;
|
|
308
|
-
padding-top:
|
|
309
|
-
padding-bottom:
|
|
317
|
+
padding-top: 0;
|
|
318
|
+
padding-bottom: 0;
|
|
310
319
|
margin-left: 0;
|
|
311
320
|
margin-right: 0;
|
|
312
321
|
margin-top: 0;
|
|
@@ -332,12 +341,6 @@
|
|
|
332
341
|
word-break: break-word;
|
|
333
342
|
}
|
|
334
343
|
|
|
335
|
-
.textarea-wrapper-inner {
|
|
336
|
-
display: flex;
|
|
337
|
-
width: 100%;
|
|
338
|
-
min-height: inherit;
|
|
339
|
-
}
|
|
340
|
-
|
|
341
344
|
:host(.ion-touched.ion-invalid) {
|
|
342
345
|
--highlight-color: var(--highlight-color-invalid);
|
|
343
346
|
}
|
|
@@ -421,12 +424,12 @@
|
|
|
421
424
|
}
|
|
422
425
|
|
|
423
426
|
.label-text-wrapper {
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
427
|
+
/**
|
|
428
|
+
* Allows the label to shrink below its intrinsic content width.
|
|
429
|
+
* Without this the label keeps its full width and can push the
|
|
430
|
+
* textarea and end slot outside the wrapper.
|
|
431
|
+
*/
|
|
432
|
+
min-width: 0;
|
|
430
433
|
/**
|
|
431
434
|
* Label text should not extend
|
|
432
435
|
* beyond the bounds of the textarea.
|
|
@@ -445,6 +448,18 @@
|
|
|
445
448
|
pointer-events: none;
|
|
446
449
|
}
|
|
447
450
|
|
|
451
|
+
/**
|
|
452
|
+
* When start/end slots are added or removed, we temporarily
|
|
453
|
+
* disable the label transition to prevent the floating label
|
|
454
|
+
* from animating as its position is adjusted.
|
|
455
|
+
*
|
|
456
|
+
* This class is applied by the start container controller, so
|
|
457
|
+
* renaming it here requires renaming it there too.
|
|
458
|
+
*/
|
|
459
|
+
:host(.skip-label-transition) .label-text-wrapper {
|
|
460
|
+
transition: none;
|
|
461
|
+
}
|
|
462
|
+
|
|
448
463
|
/**
|
|
449
464
|
* We need to use two elements instead of
|
|
450
465
|
* one. The .label-text-wrapper is responsible
|
|
@@ -488,7 +503,7 @@
|
|
|
488
503
|
* Label is on the left of the textarea in LTR and
|
|
489
504
|
* on the right in RTL.
|
|
490
505
|
*/
|
|
491
|
-
:host(.textarea-label-placement-start) .textarea-
|
|
506
|
+
:host(.textarea-label-placement-start) .textarea-control {
|
|
492
507
|
flex-direction: row;
|
|
493
508
|
}
|
|
494
509
|
|
|
@@ -510,7 +525,7 @@
|
|
|
510
525
|
* Label is on the right of the textarea in LTR and
|
|
511
526
|
* on the left in RTL.
|
|
512
527
|
*/
|
|
513
|
-
:host(.textarea-label-placement-end) .textarea-
|
|
528
|
+
:host(.textarea-label-placement-end) .textarea-control {
|
|
514
529
|
flex-direction: row-reverse;
|
|
515
530
|
}
|
|
516
531
|
|
|
@@ -560,8 +575,15 @@
|
|
|
560
575
|
* down when the textarea is focused or has a value.
|
|
561
576
|
*
|
|
562
577
|
*/
|
|
563
|
-
:host(.textarea-label-placement-stacked)
|
|
564
|
-
:host(.textarea-label-placement-floating)
|
|
578
|
+
:host(.textarea-label-placement-stacked),
|
|
579
|
+
:host(.textarea-label-placement-floating) {
|
|
580
|
+
--padding-top: 20px;
|
|
581
|
+
--padding-bottom: 6px;
|
|
582
|
+
}
|
|
583
|
+
|
|
584
|
+
:host(.textarea-label-placement-stacked) .textarea-control,
|
|
585
|
+
:host(.textarea-label-placement-floating) .textarea-control {
|
|
586
|
+
padding-top: 0;
|
|
565
587
|
flex-direction: column;
|
|
566
588
|
align-items: start;
|
|
567
589
|
}
|
|
@@ -574,12 +596,10 @@
|
|
|
574
596
|
:host(.textarea-label-placement-stacked) .label-text-wrapper,
|
|
575
597
|
:host(.textarea-label-placement-floating) .label-text-wrapper {
|
|
576
598
|
transform-origin: left top;
|
|
577
|
-
|
|
578
|
-
padding-
|
|
579
|
-
|
|
580
|
-
padding-
|
|
581
|
-
padding-top: 0px;
|
|
582
|
-
padding-bottom: 0px;
|
|
599
|
+
padding-left: 0;
|
|
600
|
+
padding-right: 0;
|
|
601
|
+
padding-top: 0;
|
|
602
|
+
padding-bottom: 0;
|
|
583
603
|
max-width: 100%;
|
|
584
604
|
/**
|
|
585
605
|
* The 2 ensures the label
|
|
@@ -614,13 +634,6 @@
|
|
|
614
634
|
margin-bottom: 0px;
|
|
615
635
|
}
|
|
616
636
|
|
|
617
|
-
:host(.textarea-label-placement-stacked) ::slotted([slot=start]),
|
|
618
|
-
:host(.textarea-label-placement-stacked) ::slotted([slot=end]),
|
|
619
|
-
:host(.textarea-label-placement-floating) ::slotted([slot=start]),
|
|
620
|
-
:host(.textarea-label-placement-floating) ::slotted([slot=end]) {
|
|
621
|
-
margin-top: 8px;
|
|
622
|
-
}
|
|
623
|
-
|
|
624
637
|
/**
|
|
625
638
|
* This makes the label sit over the textarea
|
|
626
639
|
* when the textarea is blurred and has no value.
|
|
@@ -655,19 +668,17 @@
|
|
|
655
668
|
max-width: calc(100% / 0.75);
|
|
656
669
|
}
|
|
657
670
|
|
|
658
|
-
.start
|
|
659
|
-
|
|
660
|
-
padding-right: 0;
|
|
661
|
-
padding-top: var(--padding-top);
|
|
662
|
-
padding-bottom: var(--padding-bottom);
|
|
671
|
+
.textarea-start,
|
|
672
|
+
.textarea-end {
|
|
663
673
|
display: flex;
|
|
674
|
+
position: relative;
|
|
664
675
|
flex-shrink: 0;
|
|
665
676
|
align-self: start;
|
|
666
677
|
}
|
|
667
678
|
|
|
668
679
|
::slotted([slot=start]),
|
|
669
680
|
::slotted([slot=end]) {
|
|
670
|
-
margin-top:
|
|
681
|
+
margin-top: var(--padding-top);
|
|
671
682
|
}
|
|
672
683
|
|
|
673
684
|
::slotted([slot=start]:last-of-type) {
|
|
@@ -856,10 +867,31 @@
|
|
|
856
867
|
font-size: inherit;
|
|
857
868
|
}
|
|
858
869
|
|
|
870
|
+
/**
|
|
871
|
+
* Give stacked and floating textareas a taller minimum height to
|
|
872
|
+
* accommodate the label and textarea content.
|
|
873
|
+
*/
|
|
874
|
+
:host(.textarea-label-placement-floating),
|
|
875
|
+
:host(.textarea-label-placement-stacked) {
|
|
876
|
+
min-height: 56px;
|
|
877
|
+
}
|
|
878
|
+
|
|
859
879
|
:host(.textarea-disabled) {
|
|
860
880
|
opacity: 0.3;
|
|
861
881
|
}
|
|
862
882
|
|
|
883
|
+
::slotted(ion-button[slot=start]),
|
|
884
|
+
::slotted(ion-button[slot=end]) {
|
|
885
|
+
margin-top: 2px;
|
|
886
|
+
}
|
|
887
|
+
|
|
888
|
+
:host(.textarea-label-placement-floating) ::slotted(ion-button[slot=start]),
|
|
889
|
+
:host(.textarea-label-placement-floating) ::slotted(ion-button[slot=end]),
|
|
890
|
+
:host(.textarea-label-placement-stacked) ::slotted(ion-button[slot=start]),
|
|
891
|
+
:host(.textarea-label-placement-stacked) ::slotted(ion-button[slot=end]) {
|
|
892
|
+
margin-top: 10px;
|
|
893
|
+
}
|
|
894
|
+
|
|
863
895
|
/**
|
|
864
896
|
* Slotted buttons have a lot of default padding that can
|
|
865
897
|
* cause them to look misaligned from other pieces such
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* (C) Ionic http://ionicframework.com - MIT License
|
|
3
3
|
*/
|
|
4
4
|
import { Build, Host, forceUpdate, h, writeTask, } from "@stencil/core";
|
|
5
|
-
import { createNotchController, checkInvalidState } from "../../utils/forms/index";
|
|
5
|
+
import { createNotchController, createStartContainerController, checkInvalidState } from "../../utils/forms/index";
|
|
6
6
|
import { inheritAriaAttributes, debounceEvent, inheritAttributes, componentOnReady } from "../../utils/helpers";
|
|
7
7
|
import { createSlotMutationController } from "../../utils/slot-mutation-controller";
|
|
8
8
|
import { createColorClasses, hostContext } from "../../utils/theme";
|
|
@@ -30,9 +30,11 @@ export class Textarea {
|
|
|
30
30
|
textareaWrapper;
|
|
31
31
|
inheritedAttributes = {};
|
|
32
32
|
originalIonInput;
|
|
33
|
-
notchSpacerEl;
|
|
34
33
|
slotMutationController;
|
|
35
34
|
notchController;
|
|
35
|
+
notchSpacerEl;
|
|
36
|
+
startContainerController;
|
|
37
|
+
startContainerEl;
|
|
36
38
|
/**
|
|
37
39
|
* The value of the textarea when the textarea is focused.
|
|
38
40
|
*/
|
|
@@ -260,8 +262,15 @@ export class Textarea {
|
|
|
260
262
|
}
|
|
261
263
|
connectedCallback() {
|
|
262
264
|
const { el } = this;
|
|
263
|
-
this.slotMutationController = createSlotMutationController(el, ['label', 'start', 'end'], () =>
|
|
265
|
+
this.slotMutationController = createSlotMutationController(el, ['label', 'start', 'end'], () => {
|
|
266
|
+
this.startContainerController?.calculateStartContainerWidth();
|
|
267
|
+
forceUpdate(this);
|
|
268
|
+
});
|
|
264
269
|
this.notchController = createNotchController(el, () => this.notchSpacerEl, () => this.labelSlot);
|
|
270
|
+
this.startContainerController = createStartContainerController(el, () => this.startContainerEl, () => {
|
|
271
|
+
return Build.isBrowser && getIonMode(this) === 'md' && this.fill === 'outline';
|
|
272
|
+
});
|
|
273
|
+
this.startContainerController.calculateStartContainerWidth();
|
|
265
274
|
// Watch for class changes to update validation state
|
|
266
275
|
if (Build.isBrowser && typeof MutationObserver !== 'undefined') {
|
|
267
276
|
this.validationObserver = new MutationObserver(() => {
|
|
@@ -300,6 +309,10 @@ export class Textarea {
|
|
|
300
309
|
this.notchController.destroy();
|
|
301
310
|
this.notchController = undefined;
|
|
302
311
|
}
|
|
312
|
+
if (this.startContainerController) {
|
|
313
|
+
this.startContainerController.destroy();
|
|
314
|
+
this.startContainerController = undefined;
|
|
315
|
+
}
|
|
303
316
|
// Clean up validation observer to prevent memory leaks
|
|
304
317
|
if (this.validationObserver) {
|
|
305
318
|
this.validationObserver.disconnect();
|
|
@@ -318,6 +331,7 @@ export class Textarea {
|
|
|
318
331
|
}
|
|
319
332
|
componentDidRender() {
|
|
320
333
|
this.notchController?.calculateNotchWidth();
|
|
334
|
+
this.startContainerController?.calculateStartContainerWidth();
|
|
321
335
|
}
|
|
322
336
|
/**
|
|
323
337
|
* Sets focus on the native `textarea` in `ion-textarea`. Use this method instead of the global
|
|
@@ -480,43 +494,29 @@ export class Textarea {
|
|
|
480
494
|
return this.label !== undefined || this.labelSlot !== null;
|
|
481
495
|
}
|
|
482
496
|
/**
|
|
483
|
-
* Stops propagation
|
|
484
|
-
*
|
|
497
|
+
* Stops propagation for clicks on the textarea's own content (label text,
|
|
498
|
+
* textarea field) to prevent double-click events. Allows clicks on slotted
|
|
499
|
+
* content to propagate so event delegation works for parent handlers.
|
|
500
|
+
*
|
|
501
|
+
* Only slots belonging directly to this textarea should be considered.
|
|
502
|
+
* The textarea itself may have a slot attribute when placed in an item
|
|
503
|
+
* or toolbar, which does not make its content slotted content.
|
|
485
504
|
*/
|
|
486
505
|
onLabelClick = (ev) => {
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
if (
|
|
506
|
+
const target = ev.target;
|
|
507
|
+
const slotted = target.closest('[slot="start"], [slot="end"]');
|
|
508
|
+
if (slotted === null || slotted === this.el || !this.el.contains(slotted)) {
|
|
490
509
|
ev.stopPropagation();
|
|
491
510
|
}
|
|
492
511
|
};
|
|
493
512
|
/**
|
|
494
|
-
* Renders the border
|
|
513
|
+
* Renders the outline border with a notch for the label.
|
|
495
514
|
*/
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
* The outline fill has a special outline
|
|
502
|
-
* that appears around the textarea and the label.
|
|
503
|
-
* Certain stacked and floating label placements cause the
|
|
504
|
-
* label to translate up and create a "cut out"
|
|
505
|
-
* inside of that border by using the notch-spacer element.
|
|
506
|
-
*/
|
|
507
|
-
return [
|
|
508
|
-
h("div", { class: "textarea-outline-container" }, h("div", { class: "textarea-outline-start" }), h("div", { class: {
|
|
509
|
-
'textarea-outline-notch': true,
|
|
510
|
-
'textarea-outline-notch-hidden': !this.hasLabel,
|
|
511
|
-
} }, h("div", { class: "notch-spacer", "aria-hidden": "true", ref: (el) => (this.notchSpacerEl = el) }, this.label)), h("div", { class: "textarea-outline-end" })),
|
|
512
|
-
this.renderLabel(),
|
|
513
|
-
];
|
|
514
|
-
}
|
|
515
|
-
/**
|
|
516
|
-
* If not using the outline style,
|
|
517
|
-
* we can render just the label.
|
|
518
|
-
*/
|
|
519
|
-
return this.renderLabel();
|
|
515
|
+
renderOutlineContainer() {
|
|
516
|
+
return (h("div", { class: "textarea-outline-container" }, h("div", { class: "textarea-outline-start" }), h("div", { class: {
|
|
517
|
+
'textarea-outline-notch': true,
|
|
518
|
+
'textarea-outline-notch-hidden': !this.hasLabel,
|
|
519
|
+
} }, h("div", { class: "notch-spacer", "aria-hidden": "true", ref: (el) => (this.notchSpacerEl = el) }, this.label)), h("div", { class: "textarea-outline-end" })));
|
|
520
520
|
}
|
|
521
521
|
/**
|
|
522
522
|
* Renders the helper text or error text values
|
|
@@ -564,32 +564,20 @@ export class Textarea {
|
|
|
564
564
|
return (h("div", { class: "textarea-bottom" }, this.renderHintText(), this.renderCounter()));
|
|
565
565
|
}
|
|
566
566
|
render() {
|
|
567
|
-
const { inputId, disabled, fill, shape, labelPlacement,
|
|
567
|
+
const { inputId, disabled, fill, shape, labelPlacement, hasFocus } = this;
|
|
568
568
|
const mode = getIonMode(this);
|
|
569
569
|
const value = this.getValue();
|
|
570
570
|
const inItem = hostContext('ion-item', this.el);
|
|
571
571
|
const shouldRenderHighlight = mode === 'md' && fill !== 'outline' && !inItem;
|
|
572
572
|
const hasValue = this.hasValue();
|
|
573
|
-
const
|
|
573
|
+
const hasOutlineFill = mode === 'md' && fill === 'outline';
|
|
574
574
|
/**
|
|
575
575
|
* If the label is stacked, it should always sit above the textarea.
|
|
576
576
|
* For floating labels, the label should move above the textarea if
|
|
577
|
-
* the textarea has a value
|
|
578
|
-
* the start or end slot.
|
|
579
|
-
*
|
|
580
|
-
* If there is content in the start slot, the label would overlap
|
|
581
|
-
* it if not forced to float. This is also applied to the end slot
|
|
582
|
-
* because with the default or solid fills, the textarea is not
|
|
583
|
-
* vertically centered in the container, but the label is. This
|
|
584
|
-
* causes the slots and label to appear vertically offset from each
|
|
585
|
-
* other when the label isn't floating above the input. This doesn't
|
|
586
|
-
* apply to the outline fill, but this was not accounted for to keep
|
|
587
|
-
* things consistent.
|
|
588
|
-
*
|
|
589
|
-
* TODO(FW-5592): Remove hasStartEndSlots condition
|
|
577
|
+
* the textarea has a value or is focused.
|
|
590
578
|
*/
|
|
591
|
-
const labelShouldFloat = labelPlacement === 'stacked' || (labelPlacement === 'floating' && (hasValue || hasFocus
|
|
592
|
-
return (h(Host, { key: '
|
|
579
|
+
const labelShouldFloat = labelPlacement === 'stacked' || (labelPlacement === 'floating' && (hasValue || hasFocus));
|
|
580
|
+
return (h(Host, { key: '78da9c96e6a29f19b237f268dd8bfd044afe27b6', class: createColorClasses(this.color, {
|
|
593
581
|
[mode]: true,
|
|
594
582
|
'has-value': hasValue,
|
|
595
583
|
'has-focus': hasFocus,
|
|
@@ -598,7 +586,7 @@ export class Textarea {
|
|
|
598
586
|
[`textarea-shape-${shape}`]: shape !== undefined,
|
|
599
587
|
[`textarea-label-placement-${labelPlacement}`]: true,
|
|
600
588
|
'textarea-disabled': disabled,
|
|
601
|
-
}) }, h("label", { key: '
|
|
589
|
+
}) }, h("label", { key: 'c5ea3f26e01e66b857d3a1c88dbafbf2dbb81fdb', class: "textarea-wrapper", htmlFor: inputId, onClick: this.onLabelClick }, hasOutlineFill && this.renderOutlineContainer(), h("div", { key: '5a9d0efc8c13d9bd4ec4ceadf1bdb84205c47b3d', class: "textarea-start", ref: (el) => (this.startContainerEl = el) }, h("slot", { key: 'da08262e33f3a5b454847297338a74f07c5b60c9', name: "start" })), h("div", { key: '6461dc7381929eb83679ec07563b7bdf8bfc3f9f', class: "textarea-control" }, this.renderLabel(), h("div", { key: '8f7902a9e6040384d25d0e2061c04f6b49acf187', class: "native-wrapper", ref: (el) => (this.textareaWrapper = el) }, h("textarea", { key: '2149d8b2c23a164c536327c98d7a632e1e85428a', class: "native-textarea", ref: (el) => (this.nativeInput = el), id: inputId, disabled: disabled, autoCapitalize: this.autocapitalize, autoFocus: this.autofocus, enterKeyHint: this.enterkeyhint, inputMode: this.inputmode, minLength: this.minlength, maxLength: this.maxlength, name: this.name, placeholder: this.placeholder || '', readOnly: this.readonly, required: this.required, spellcheck: this.spellcheck, cols: this.cols, rows: this.rows, wrap: this.wrap, onInput: this.onInput, onChange: this.onChange, onBlur: this.onBlur, onFocus: this.onFocus, onKeyDown: this.onKeyDown, "aria-describedby": this.getHintTextID(), "aria-invalid": this.isInvalid ? 'true' : undefined, ...this.inheritedAttributes }, value))), h("div", { key: '84f5f42add89875c3f0cce734b512a9e7be81e03', class: "textarea-end" }, h("slot", { key: 'ea654d78013a00b8af33deb89d42c2b7f6c9cb99', name: "end" })), shouldRenderHighlight && h("div", { key: 'b72195d2606816b3b71e65214d78cef1740f4804', class: "textarea-highlight" })), this.renderBottomContent()));
|
|
602
590
|
}
|
|
603
591
|
static get is() { return "ion-textarea"; }
|
|
604
592
|
static get encapsulation() { return "scoped"; }
|