PluginProbe
OpenStation: Desktop Windows, Dock & Virtual Desktops for WP Admin / 1.1.10
OpenStation: Desktop Windows, Dock & Virtual Desktops for WP Admin v1.1.10
1.1.10 1.1.9 1.1.8 1.1.7 1.1.6 1.1.5 1.1.4 1.1.3 1.1.2 1.1.1 1.1.0 1.0.1 1.0.0 0.9.8 0.9.7 0.9.6 0.9.4 0.9.5 0.9.3 0.9.2 0.9.1 0.9.0 0.8.9 0.8.8 0.8.7 All 34 releases
← All changes | includes/os-settings.php +103 -24 1.1.41.1.10 View file →
@@ -62,8 +62,18 @@
62 62 */
63 63 const OPENSTATION_OS_SETTINGS_DOCK_BEHAVIORS = array( 'static', 'dynamic' );
64 64
65 65 /**
66 + * `mobileLayout` — which experience the shell renders. `auto`
67 + * follows the viewport; the other two force it either way.
68 + * Mirrors `OsModePreference` in `src/mode/index.ts`.
69 + */
70 +const OPENSTATION_OS_SETTINGS_MOBILE_LAYOUTS = array( 'auto', 'desktop', 'mobile' );
71 +
72 +/** `mobileTabs` — at most this many ids pinned to the phone tab bar. */
73 +const OPENSTATION_OS_SETTINGS_MOBILE_TABS_MAX = 3;
74 +
75 +/**
66 76 * Playable range for the window-reveal duration override, in ms.
67 77 * Mirrors `MIN_REVEAL_DURATION_MS` / `MAX_REVEAL_DURATION_MS` in
68 78 * `src/reveals/registry.ts`.
69 79 *
@@ -83,8 +93,10 @@
83 93 */
84 94 function openstation_default_os_settings() {
85 95 return array(
86 96 'wallpaper' => 'galaxy',
97 + // Pulse, the brand's signature. Mirrors `DEFAULTS` in
98 + // `src/settings/constants.ts`.
87 99 'accent' => 'pulse',
88 100 // Only read when `accent` is `custom`. Seeded with Pulse so
89 101 // picking Custom before touching the wheel is a no-op rather
90 102 // than a jump to black. Mirrors `DEFAULTS` in
@@ -200,8 +212,13 @@
200 212 // window (e.g. array( 'author', 'tags' )). Empty array means
201 213 // every column is visible. The sticky 'title' column is always
202 214 // shown — the UI prevents toggling it.
203 215 'nativePostsHiddenColumns' => array(),
216 + // Per-user list of column keys hidden in the native Pages
217 + // window (e.g. array( 'author', 'parent' )). Empty array means
218 + // every column is visible. The sticky 'title' column is always
219 + // shown — the UI prevents toggling it.
220 + 'nativePagesHiddenColumns' => array(),
204 221 // Per-user opt-IN for the native Pages window. Same posture as
205 222 // nativePostsEnabled — defaults OFF (Beta), users opt in to swap
206 223 // the classic `edit.php?post_type=page` iframe for the native UI.
207 224 'nativePagesEnabled' => false,
@@ -224,21 +241,11 @@
224 241 // (including any custom dashboard a plugin builds there) opens
225 242 // as a chromeless iframe until the user opts in via OS
226 243 // Settings → Features → Beta features.
227 244 'stationHomeEnabled' => false,
228 - // Per-user opt-IN for the service worker's shared admin-asset
229 - // cache (Experimental). Defaults OFF. The value feeds the
230 - // `openstation_pwa_admin_asset_cache` filter's default via
231 - // `openstation_pwa_admin_asset_cache_enabled()` and reaches the
232 - // SW inside the served `sw.js` bytes, so a change applies via a
233 - // normal SW update on the user's next reload.
234 - 'adminAssetCacheEnabled' => false,
235 - // Per-user opt-IN for hover-intent window prewarming
236 - // (Experimental). Defaults OFF. When on, a sustained mouse
237 - // hover on a dock tile speculatively builds that page's window
238 - // hidden so it appears already rendered on click. Read live by
239 - // the dock JS; no server-side behavior attaches to it.
240 - 'windowPrewarmEnabled' => false,
245 + // Performance enhancements are enabled unless explicitly disabled.
246 + 'adminAssetCacheEnabled' => true,
247 + 'windowPrewarmEnabled' => true,
241 248 // When true, left-clicking the empty wallpaper triggers the
242 249 // "Show desktop" toggle (macOS-style) and the matching entry is
243 250 // hidden from the wallpaper context menu. When false (default),
244 251 // the entry stays in the menu and left clicks on the wallpaper
@@ -243,13 +250,20 @@
243 250 // hidden from the wallpaper context menu. When false (default),
244 251 // the entry stays in the menu and left clicks on the wallpaper
245 252 // do nothing. Per-user.
246 253 'showDesktopOnWallpaperClick' => false,
254 + // Whether the close-all-windows shortcut (Alt+Cmd/Ctrl+W) asks
255 + // before it closes. The dialog's "Don't ask again" checkbox is
256 + // what writes false; OpenStation Preferences -> Windows is what
257 + // turns it back on. Per-user.
258 + 'confirmCloseAllWindows' => true,
247 259 // Mio — a soft-body companion that floats over
248 260 // the wallpaper, settles onto nearby windows, and watches the
249 261 // pointer. Off by default; toggled from the wallpaper context
250 262 // menu. Per-user. See `docs/mio.md`.
251 263 'mioEnabled' => false,
264 + 'mioApiEnabled' => false,
265 + 'mioShowOnWallpaper' => true,
252 266 // The user's own Mio, as built in "Make it yours": partial
253 267 // appearance + silhouette overrides, both empty until they
254 268 // touch a control. Stored per user rather than per browser
255 269 // because it is a preference about the person — ten minutes
@@ -300,8 +314,14 @@
300 314 // Per-user ordering, flat across every dock/sidebar zone. Ids
301 315 // not in the list keep their registration order and render
302 316 // after the listed ones. Unknown ids are tolerated.
303 317 'navOrder' => array(),
318 + // Which experience the shell renders: 'auto' follows the
319 + // viewport, 'desktop' / 'mobile' force it. See `includes/mobile.php`.
320 + 'mobileLayout' => 'auto',
321 + // Ids pinned to the phone tab bar, at most three. Empty means
322 + // the server default (`openstation_mobile_tab_bar`).
323 + 'mobileTabs' => array(),
304 324 // Persisted desktop position for every item the user has
305 325 // promoted to the wallpaper via `navPlacement[id]=desktop|both`.
306 326 // Keyed by item id, value is `{ x: int, y: int }`. The JS
307 327 // synthesizer reads this when building a synthetic placement so
@@ -322,14 +342,14 @@
322 342 */
323 343 function openstation_get_os_settings( $user_id ) {
324 344 $user_id = (int) $user_id;
325 345 if ( $user_id <= 0 ) {
326 - return openstation_default_os_settings();
346 + return openstation_sanitize_os_settings( array() );
327 347 }
328 348
329 349 $raw = get_user_meta( $user_id, OPENSTATION_OS_SETTINGS_META_KEY, true );
330 350 if ( ! is_array( $raw ) ) {
331 - return openstation_default_os_settings();
351 + return openstation_sanitize_os_settings( array() );
332 352 }
333 353
334 354 return openstation_sanitize_os_settings( $raw );
335 355 }
@@ -432,9 +452,9 @@
432 452 function openstation_sanitize_os_settings( $raw ) {
433 453 $defaults = openstation_default_os_settings();
434 454
435 455 if ( ! is_array( $raw ) ) {
436 - return $defaults;
456 + $raw = array();
437 457 }
438 458
439 459 // Wallpaper — any non-empty string; registry membership is validated
440 460 // client-side at apply time.
@@ -765,8 +785,27 @@
765 785 // user meta indefinitely.
766 786 $native_posts_hidden_columns = array_slice( array_values( array_unique( $native_posts_hidden_columns ) ), 0, 32 );
767 787 }
768 788
789 + $native_pages_hidden_columns = $defaults['nativePagesHiddenColumns'];
790 + if ( isset( $raw['nativePagesHiddenColumns'] ) && is_array( $raw['nativePagesHiddenColumns'] ) ) {
791 + $native_pages_hidden_columns = array();
792 + foreach ( $raw['nativePagesHiddenColumns'] as $col ) {
793 + if ( ! is_string( $col ) || '' === $col ) {
794 + continue;
795 + }
796 + $slug = sanitize_key( $col );
797 + if ( '' === $slug ) {
798 + continue;
799 + }
800 + $native_pages_hidden_columns[] = $slug;
801 + }
802 + // Cap to a sane upper bound — far more than any plausible
803 + // column count, but blocks a malicious payload from bloating
804 + // user meta indefinitely.
805 + $native_pages_hidden_columns = array_slice( array_values( array_unique( $native_pages_hidden_columns ) ), 0, 32 );
806 + }
807 +
769 808 $native_pages_enabled = isset( $raw['nativePagesEnabled'] )
770 809 ? (bool) $raw['nativePagesEnabled']
771 810 : $defaults['nativePagesEnabled'];
772 811
@@ -785,23 +824,25 @@
785 824 $station_home_enabled = isset( $raw['stationHomeEnabled'] )
786 825 ? (bool) $raw['stationHomeEnabled']
787 826 : $defaults['stationHomeEnabled'];
788 827
789 - $admin_asset_cache_enabled = isset( $raw['adminAssetCacheEnabled'] )
790 - ? (bool) $raw['adminAssetCacheEnabled']
791 - : $defaults['adminAssetCacheEnabled'];
828 + // Site-wide performance controls supersede the legacy per-user values.
829 + // Keep the snapshot keys so existing window consumers can read them.
830 + $extended_options = openstation_get_extended_options();
831 + $admin_asset_cache_enabled = $extended_options['admin_asset_cache'];
832 + $window_prewarm_enabled = $extended_options['window_prewarm'];
792 833
793 - $window_prewarm_enabled = isset( $raw['windowPrewarmEnabled'] )
794 - ? (bool) $raw['windowPrewarmEnabled']
795 - : $defaults['windowPrewarmEnabled'];
796 -
797 834 $show_desktop_on_wallpaper_click = isset( $raw['showDesktopOnWallpaperClick'] )
798 835 ? (bool) $raw['showDesktopOnWallpaperClick']
799 836 : $defaults['showDesktopOnWallpaperClick'];
800 837
838 + $confirm_close_all_windows = isset( $raw['confirmCloseAllWindows'] )
839 + ? (bool) $raw['confirmCloseAllWindows']
840 + : $defaults['confirmCloseAllWindows'];
841 +
801 842 $mio_enabled = isset( $raw['mioEnabled'] )
802 843 ? (bool) $raw['mioEnabled']
803 - : $defaults['mioEnabled'];
844 + : ( isset( $raw['mioApiEnabled'] ) ? (bool) $raw['mioApiEnabled'] : $defaults['mioEnabled'] );
804 845
805 846 // A missing key means "no look saved yet", which sanitizes to the
806 847 // same pair of empty arrays the defaults carry — so this needs no
807 848 // isset() branch of its own.
@@ -816,8 +857,35 @@
816 857 $developer_mode_enabled = isset( $raw['developerModeEnabled'] )
817 858 ? (bool) $raw['developerModeEnabled']
818 859 : $defaults['developerModeEnabled'];
819 860
861 + // mobileLayout — the phone/desktop override.
862 + $mobile_layout = isset( $raw['mobileLayout'] )
863 + && in_array( $raw['mobileLayout'], OPENSTATION_OS_SETTINGS_MOBILE_LAYOUTS, true )
864 + ? (string) $raw['mobileLayout']
865 + : $defaults['mobileLayout'];
866 +
867 + // mobileTabs — ordered nav ids pinned to the phone tab bar. Same
868 + // id grammar as navOrder, capped at the tab bar's slot count.
869 + $mobile_tabs = array();
870 + if ( isset( $raw['mobileTabs'] ) && is_array( $raw['mobileTabs'] ) ) {
871 + $seen_tabs = array();
872 + foreach ( $raw['mobileTabs'] as $id ) {
873 + if ( ! is_string( $id ) || '' === $id ) {
874 + continue;
875 + }
876 + $slug = sanitize_key( openstation_canonical_nav_id( $id ) );
877 + if ( '' === $slug || isset( $seen_tabs[ $slug ] ) ) {
878 + continue;
879 + }
880 + $seen_tabs[ $slug ] = true;
881 + $mobile_tabs[] = $slug;
882 + if ( count( $mobile_tabs ) >= OPENSTATION_OS_SETTINGS_MOBILE_TABS_MAX ) {
883 + break;
884 + }
885 + }
886 + }
887 +
820 888 $folders_sharing_enabled = isset( $raw['foldersSharingEnabled'] )
821 889 ? (bool) $raw['foldersSharingEnabled']
822 890 : $defaults['foldersSharingEnabled'];
823 891
@@ -960,8 +1028,9 @@
960 1028 'heartbeatRate' => $heartbeat_rate,
961 1029 'nativePostsEnabled' => $native_posts_enabled,
962 1030 'nativePostsHiddenColumns' => $native_posts_hidden_columns,
963 1031 'nativePagesEnabled' => $native_pages_enabled,
1032 + 'nativePagesHiddenColumns' => $native_pages_hidden_columns,
964 1033 'nativeUsersEnabled' => $native_users_enabled,
965 1034 'nativePluginsEnabled' => $native_plugins_enabled,
966 1035 'nativeCommentsEnabled' => $native_comments_enabled,
967 1036 'stationHomeEnabled' => $station_home_enabled,
@@ -967,9 +1036,12 @@
967 1036 'stationHomeEnabled' => $station_home_enabled,
968 1037 'adminAssetCacheEnabled' => $admin_asset_cache_enabled,
969 1038 'windowPrewarmEnabled' => $window_prewarm_enabled,
970 1039 'showDesktopOnWallpaperClick' => $show_desktop_on_wallpaper_click,
1040 + 'confirmCloseAllWindows' => $confirm_close_all_windows,
971 1041 'mioEnabled' => $mio_enabled,
1042 + 'mioApiEnabled' => $mio_enabled,
1043 + 'mioShowOnWallpaper' => isset( $raw['mioShowOnWallpaper'] ) ? (bool) $raw['mioShowOnWallpaper'] : $defaults['mioShowOnWallpaper'],
972 1044 'mioStyle' => $mio_style,
973 1045 'showPostStatusRibbons' => $show_post_status_ribbons,
974 1046 'developerModeEnabled' => $developer_mode_enabled,
975 1047 'foldersSharingEnabled' => $folders_sharing_enabled,
@@ -974,8 +1046,10 @@
974 1046 'developerModeEnabled' => $developer_mode_enabled,
975 1047 'foldersSharingEnabled' => $folders_sharing_enabled,
976 1048 'navPlacement' => $nav_placement,
977 1049 'navOrder' => $nav_order,
1050 + 'mobileLayout' => $mobile_layout,
1051 + 'mobileTabs' => $mobile_tabs,
978 1052 'dockPromotedPositions' => $dock_promoted_positions,
979 1053 );
980 1054 }
981 1055
@@ -1075,8 +1149,13 @@
1075 1149 // true of every path into this handler, not just the ones the
1076 1150 // schema happens to guard.
1077 1151 if ( ! is_array( $payload ) ) {
1078 1152 return rest_ensure_response( openstation_get_os_settings( $user_id ) );
1153 + }
1154 +
1155 + // Normalize an alias-only patch before merging it with the saved master value.
1156 + if ( ! array_key_exists( 'mioEnabled', $payload ) && array_key_exists( 'mioApiEnabled', $payload ) ) {
1157 + $payload['mioEnabled'] = $payload['mioApiEnabled'];
1079 1158 }
1080 1159
1081 1160 openstation_save_os_settings(
1082 1161 $user_id,