[go: nahoru, domu]

blob: d362f56c16d33c6a3d052afaaec2d786fb4d0721 [file] [log] [blame]
Igor Demin1eb703eb2021-04-24 02:57:27 +03001/*
2 * Copyright 2021 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package androidx.compose.ui.window
18
19import androidx.compose.runtime.Composable
20import androidx.compose.runtime.getValue
21import androidx.compose.runtime.mutableStateOf
22import androidx.compose.runtime.saveable.Saver
23import androidx.compose.runtime.saveable.listSaver
24import androidx.compose.runtime.saveable.rememberSaveable
25import androidx.compose.runtime.setValue
26import androidx.compose.ui.unit.dp
27
28/**
29 * Creates a [WindowState] that is remembered across compositions.
30 *
31 * Changes to the provided initial values will **not** result in the state being recreated or
32 * changed in any way if it has already been created.
33 *
34 * @param placement the initial value for [WindowState.placement]
35 * @param isMinimized the initial value for [WindowState.isMinimized]
36 * @param position the initial value for [WindowState.position]
37 * @param size the initial value for [WindowState.size]
38 */
39@Composable
40fun rememberWindowState(
41 placement: WindowPlacement = WindowPlacement.Floating,
42 isMinimized: Boolean = false,
43 position: WindowPosition = WindowPosition.PlatformDefault,
44 size: WindowSize = WindowSize(800.dp, 600.dp),
45): WindowState = rememberSaveable(saver = WindowStateImpl.Saver(position)) {
46 WindowStateImpl(
47 placement,
48 isMinimized,
49 position,
50 size
51 )
52}
53
54/**
55 * A state object that can be hoisted to control and observe window attributes
56 * (size/position/state).
57 *
58 * In most cases, this will be created via [rememberWindowState].
59 *
60 * @param placement the initial value for [WindowState.placement]
61 * @param isMinimized the initial value for [WindowState.isMinimized]
62 * @param position the initial value for [WindowState.position]
63 * @param size the initial value for [WindowState.size]
64 */
65fun WindowState(
66 placement: WindowPlacement = WindowPlacement.Floating,
67 isMinimized: Boolean = false,
68 position: WindowPosition = WindowPosition.PlatformDefault,
69 size: WindowSize = WindowSize(800.dp, 600.dp)
70): WindowState = WindowStateImpl(
71 placement, isMinimized, position, size
72)
73
74/**
75 * A state object that can be hoisted to control and observe window attributes
76 * (size/position/state).
77 *
78 * In most cases, this will be created via [rememberWindowState].
79 */
80interface WindowState {
81 /**
82 * Describes how the window is placed on the screen.
83 */
84 var placement: WindowPlacement
85
86 /**
87 * `true` if the window is minimized.
88 */
89 var isMinimized: Boolean
90
91 /**
92 * Current position of the window. If position is not specified ([WindowPosition.isSpecified]
93 * is false) then once the window shows on the screen the position will be set to
94 * absolute values [WindowPosition.Absolute].
95 */
96 var position: WindowPosition
97
98 /**
99 * Current size of the window.
100 */
101 var size: WindowSize
102}
103
104private class WindowStateImpl(
105 placement: WindowPlacement,
106 isMinimized: Boolean,
107 position: WindowPosition,
108 size: WindowSize
109) : WindowState {
110 override var placement by mutableStateOf(placement)
111 override var isMinimized by mutableStateOf(isMinimized)
112 override var position by mutableStateOf(position)
113 override var size by mutableStateOf(size)
114
115 companion object {
116 /**
117 * The default [Saver] implementation for [WindowStateImpl].
118 */
119 fun Saver(unspecifiedPosition: WindowPosition) = listSaver<WindowState, Any>(
120 save = {
121 listOf(
122 it.placement.ordinal,
123 it.isMinimized,
124 it.position.isSpecified,
125 it.position.x.value,
126 it.position.y.value,
127 it.size.width.value,
128 it.size.height.value,
129 )
130 },
131 restore = { state ->
132 WindowStateImpl(
133 placement = WindowPlacement.values()[state[0] as Int],
134 isMinimized = state[1] as Boolean,
135 position = if (state[2] as Boolean) {
136 WindowPosition((state[3] as Float).dp, (state[4] as Float).dp)
137 } else {
138 unspecifiedPosition
139 },
140 size = WindowSize((state[5] as Float).dp, (state[6] as Float).dp),
141 )
142 }
143 )
144 }
145}