@rdlabo/ionic-theme-ios27 1.2.0-beta.pr231.sha22a35d481cf3 → 1.2.0-beta.pr233.sha647eef34274b
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/README.md +9 -0
- package/dist/native/components/searchable-tabs.d.ts.map +1 -1
- package/dist/native/components/searchable-tabs.js +6 -7
- package/dist/native/definitions.d.ts +4 -15
- package/dist/native/definitions.d.ts.map +1 -1
- package/dist/native/definitions.js +1 -6
- package/dist/native/index.d.ts +1 -2
- package/dist/native/index.d.ts.map +1 -1
- package/dist/native/index.js +57 -27
- package/dist/native/runtime.d.ts.map +1 -1
- package/dist/native/runtime.js +18 -10
- package/dist/native/vertical-bars-web.d.ts.map +1 -1
- package/dist/native/vertical-bars-web.js +2 -0
- package/dist/tab-bar-searchable/index.d.ts.map +1 -1
- package/dist/tab-bar-searchable/index.js +39 -11
- package/dist/vertical-bars.d.ts +1 -2
- package/dist/vertical-bars.d.ts.map +1 -1
- package/dist/vertical-bars.js +0 -1
- package/docs/iphone-duo-with-original-theme.md +16 -8
- package/docs/iphone-duo.md +57 -44
- package/docs/native-ui-shell.md +5 -3
- package/ios/Sources/IonicNativeUIShellPlugin/Components/ShellSearchController.swift +1 -1
- package/ios/Sources/IonicNativeUIShellPlugin/Components/ShellVerticalBars.swift +27 -2
- package/ios/Sources/IonicNativeUIShellPlugin/Components/ShellVerticalSearch.swift +118 -0
- package/ios/Sources/IonicNativeUIShellPlugin/IonicNativeUIShellPlugin.swift +27 -179
- package/ios/Tests/IonicNativeUIShellPluginTests/ShellSnapshotTests.swift +37 -0
- package/package.json +1 -1
- package/src/native/components/searchable-tabs.ts +8 -11
- package/src/native/definitions.ts +6 -19
- package/src/native/index.ts +60 -29
- package/src/native/runtime.ts +16 -10
- package/src/native/vertical-bars-web.ts +2 -0
- package/src/tab-bar-searchable/index.ts +40 -9
- package/src/vertical-bars.ts +1 -2
|
@@ -64,6 +64,8 @@ export const attachTabBarSearchable = (
|
|
|
64
64
|
// Initialize
|
|
65
65
|
ionFooter.style.pointerEvents = 'none';
|
|
66
66
|
ionFooter.style.opacity = '0';
|
|
67
|
+
// Search dismissal belongs beside the Web search field, never in the vertical rail.
|
|
68
|
+
ionFooter.querySelector('ion-buttons[slot=start]')?.classList.add('ios-theme-horizontal-only');
|
|
67
69
|
const nativeSearch = registerNativeSearch(ionTabBar, ionFabButton, ionFooter);
|
|
68
70
|
|
|
69
71
|
// Saved Params
|
|
@@ -72,6 +74,8 @@ export const attachTabBarSearchable = (
|
|
|
72
74
|
// Leave is valid both while native Enter awaits its ack and after it completes.
|
|
73
75
|
let nativeEntry = false;
|
|
74
76
|
let nativeRequest = 0;
|
|
77
|
+
let verticalSearch = false;
|
|
78
|
+
let tabVisibilityObserver: MutationObserver | undefined;
|
|
75
79
|
|
|
76
80
|
return async (event: Event, type: TabBarSearchableType) => {
|
|
77
81
|
const selector = type === TabBarSearchableType.Enter ? 'ion-fab-button' : 'ion-buttons[slot=start] ion-button';
|
|
@@ -93,19 +97,38 @@ export const attachTabBarSearchable = (
|
|
|
93
97
|
return;
|
|
94
98
|
}
|
|
95
99
|
if (type === TabBarSearchableType.Enter) {
|
|
96
|
-
|
|
100
|
+
verticalSearch = !!ionTabBar.closest('ion-app.ios-theme-vertical-bars');
|
|
101
|
+
if (verticalSearch) {
|
|
102
|
+
// Ionic hides horizontal tabs when the keyboard opens; keep this rail available.
|
|
103
|
+
const keepTabsVisible = () => {
|
|
104
|
+
if (ionTabBar.classList.contains('tab-bar-hidden') && ionTabBar.closest('ion-app.ios-theme-vertical-bars')) {
|
|
105
|
+
ionTabBar.classList.remove('tab-bar-hidden');
|
|
106
|
+
}
|
|
107
|
+
};
|
|
108
|
+
tabVisibilityObserver?.disconnect();
|
|
109
|
+
tabVisibilityObserver = new MutationObserver(keepTabsVisible);
|
|
110
|
+
tabVisibilityObserver.observe(ionTabBar, { attributes: true, attributeFilter: ['class'] });
|
|
111
|
+
keepTabsVisible();
|
|
112
|
+
}
|
|
113
|
+
resumeNative ??= await suspendNativeUIShell([
|
|
114
|
+
...(verticalSearch ? [] : [ionTabBar]),
|
|
115
|
+
ionFooter,
|
|
116
|
+
ionFabButton.closest('ion-fab') ?? ionFabButton,
|
|
117
|
+
]);
|
|
97
118
|
try {
|
|
98
|
-
searchableEventCache = await enterEvent(event, ionTabBar, ionFabButton, ionFooter);
|
|
119
|
+
searchableEventCache = await enterEvent(event, ionTabBar, ionFabButton, ionFooter, verticalSearch);
|
|
99
120
|
} catch (error) {
|
|
121
|
+
tabVisibilityObserver?.disconnect();
|
|
100
122
|
resumeNative();
|
|
101
123
|
resumeNative = undefined;
|
|
102
124
|
throw error;
|
|
103
125
|
}
|
|
104
126
|
} else if (searchableEventCache !== undefined) {
|
|
105
127
|
try {
|
|
106
|
-
await leaveEvent(event, searchableEventCache, ionTabBar, ionFabButton, ionFooter);
|
|
128
|
+
await leaveEvent(event, searchableEventCache, ionTabBar, ionFabButton, ionFooter, verticalSearch);
|
|
107
129
|
searchableEventCache = undefined;
|
|
108
130
|
} finally {
|
|
131
|
+
tabVisibilityObserver?.disconnect();
|
|
109
132
|
resumeNative?.();
|
|
110
133
|
resumeNative = undefined;
|
|
111
134
|
}
|
|
@@ -120,6 +143,7 @@ const enterEvent = async (
|
|
|
120
143
|
ionTabBar: HTMLElement,
|
|
121
144
|
ionFabButton: HTMLElement,
|
|
122
145
|
ionFooter: HTMLElement,
|
|
146
|
+
verticalSearch: boolean,
|
|
123
147
|
): Promise<SearchableEventCache> => {
|
|
124
148
|
if (!(event.target as HTMLElement)?.closest('ion-fab-button')) {
|
|
125
149
|
throw throwErrorByFailedClickElement('ion-fab-button');
|
|
@@ -131,10 +155,12 @@ const enterEvent = async (
|
|
|
131
155
|
? getComputedStyle(references.selectedTabButton).getPropertyValue('--color-selected').trim()
|
|
132
156
|
: '';
|
|
133
157
|
|
|
134
|
-
|
|
158
|
+
if (verticalSearch) references.closeButtonIcon.setAttribute('name', 'close');
|
|
159
|
+
const tabAnimations = verticalSearch
|
|
160
|
+
? []
|
|
161
|
+
: [createTabBarAnimation(ionTabBar, references, sizes), createEffectAnimation(references, sizes)];
|
|
135
162
|
const searchContainerAnimation = createSearchContainerAnimation(references, sizes);
|
|
136
163
|
const closeButtonsAnimation = createCloseButtonsAnimation(references);
|
|
137
|
-
const tabBarAnimation = createTabBarAnimation(ionTabBar, references, sizes);
|
|
138
164
|
const fabButtonAnimation = createFabButtonAnimation(ionFabButton);
|
|
139
165
|
|
|
140
166
|
await createAnimation()
|
|
@@ -144,7 +170,7 @@ const enterEvent = async (
|
|
|
144
170
|
.addElement(ionFooter)
|
|
145
171
|
.afterAddWrite(() => (ionFooter.style.pointerEvents = 'auto'))
|
|
146
172
|
.fromTo('opacity', '0.8', '1')
|
|
147
|
-
.addAnimation([
|
|
173
|
+
.addAnimation([...tabAnimations, fabButtonAnimation, searchContainerAnimation, closeButtonsAnimation])
|
|
148
174
|
.play();
|
|
149
175
|
|
|
150
176
|
return {
|
|
@@ -159,6 +185,7 @@ const leaveEvent = async (
|
|
|
159
185
|
ionTabBar: HTMLElement,
|
|
160
186
|
ionFabButton: HTMLElement,
|
|
161
187
|
ionFooter: HTMLElement,
|
|
188
|
+
verticalSearch: boolean,
|
|
162
189
|
): Promise<void> => {
|
|
163
190
|
if (!(event.target as HTMLElement)?.closest('ion-buttons[slot=start] ion-button')) {
|
|
164
191
|
throw throwErrorByFailedClickElement('ion-buttons[slot=start] ion-button');
|
|
@@ -166,10 +193,14 @@ const leaveEvent = async (
|
|
|
166
193
|
|
|
167
194
|
const references = getElementReferences(ionTabBar, ionFooter);
|
|
168
195
|
|
|
169
|
-
const
|
|
196
|
+
const tabAnimations = verticalSearch
|
|
197
|
+
? []
|
|
198
|
+
: [
|
|
199
|
+
createReverseTabBarAnimation(ionTabBar, references, searchableEventCache.elementSizes),
|
|
200
|
+
createReverseEffectAnimation(references, searchableEventCache.elementSizes, searchableEventCache.colorSelected),
|
|
201
|
+
];
|
|
170
202
|
const searchContainerAnimation = createReverseSearchContainerAnimation(references, searchableEventCache.elementSizes);
|
|
171
203
|
const closeButtonsAnimation = createReverseCloseButtonsAnimation(references);
|
|
172
|
-
const tabBarAnimation = createReverseTabBarAnimation(ionTabBar, references, searchableEventCache.elementSizes);
|
|
173
204
|
const fabButtonAnimation = createReverseFabButtonAnimation(ionFabButton, searchableEventCache.elementSizes);
|
|
174
205
|
|
|
175
206
|
await createAnimation()
|
|
@@ -179,6 +210,6 @@ const leaveEvent = async (
|
|
|
179
210
|
.addElement(ionFooter)
|
|
180
211
|
.afterAddWrite(() => (ionFooter.style.pointerEvents = 'none'))
|
|
181
212
|
.fromTo('opacity', '1', '0')
|
|
182
|
-
.addAnimation([
|
|
213
|
+
.addAnimation([...tabAnimations, fabButtonAnimation, searchContainerAnimation, closeButtonsAnimation])
|
|
183
214
|
.play();
|
|
184
215
|
};
|
package/src/vertical-bars.ts
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
1
|
export { enableVerticalControlArea, setVerticalControlAreaPlacement, IonicNativeUIShell } from './native';
|
|
2
|
-
export { HingeStatus } from './native';
|
|
3
2
|
export { withNativeUIShellTransition } from './native-integration/transition';
|
|
4
|
-
export type {
|
|
3
|
+
export type { NativeUIShellStatus, NativeUIShellSuspension, VerticalBarEdge, VerticalControlAreaHandle } from './native';
|