swiftui
In a previous article, I showed you how to build an expandable button with Swift and UIKit. With SwiftUI gaining traction, I decided to share an updated article showing how we can implement this same functionality using SwiftUI.
在上一篇文章中 ,我向您展示了如何使用Swift和UIKit构建可扩展按钮。 随着SwiftUI的吸引,我决定分享一篇更新的文章,展示如何使用SwiftUI实现相同的功能。
Implementing custom views with SwiftUI is extremely simple, and we will leverage its power to build an expandable button that will look like the one below:
使用SwiftUI实现自定义视图非常简单,我们将利用其强大功能来构建一个可扩展按钮,如下所示:
Our buttons will simply need to be embedded in a VStack
. Whenever the primary button is tapped, we will either show or hide the secondary buttons, signaled in the diagram below, depending on their current state.
我们的按钮只需要嵌入到VStack
。 每当点击主按钮时,我们将根据其当前状态显示或隐藏辅助按钮,如下图所示。
Let’s start by creating a custom struct
called ExpandableButtonItem
, which will be used to represent the content for each of the buttons in our button panel. The ExpandableButtonItem
will include a label
to show on the button (an emoji String
in our case) and an optional action
that is executed whenever the button is tapped. We also have an id
in order to conform to the Identifiable
protocol.
让我们开始创建一个名为ExpandableButtonItem
的自定义struct
,该struct
将用于表示按钮面板中每个按钮的内容。 ExpandableButtonItem
将包括一个在按钮上显示的label
(在本例中为emoji String
),以及一个可选action
,该操作在每次点击按钮时都会执行。 我们也有一个id
,以符合可Identifiable
协议。
Then we’ll create another custom struct
called ExpandableButtonPanel
with two instance properties, primaryItem
and secondaryItems
. The primaryItem
corresponds to the button that is always visible. The secondaryItems
is a list correspond to each of the buttons that will be shown or hidden when the primary button is tapped.
然后,我们将创建另一个名为ExpandableButtonPanel
自定义struct
具有两个实例属性primaryItem
和secondaryItems
。 primaryItem
对应于始终可见的按钮。 secondaryItems
是与每个按钮相对应的列表,当点击主按钮时,这些按钮将显示或隐藏。
We will first embed the buttons for each of the secondaryItems
in a VStack
, and the button for the primaryItem
last.
首先,我们将嵌入每个的按钮secondaryItems
在VStack
,按钮的primaryItem
最后。
To show and hide the secondary buttons, we will add a State
boolean––isExpanded
––to keep track of the current expanded state. The isExpanded
boolean will be toggled whenever the primary button is tapped, causing the frame of each secondary button to change to handle showing/hiding.
为了显示和隐藏次要的按钮,我们将添加一个State
boolean-- isExpanded
当前展开状态的--to跟踪。 只要轻按主按钮,就会切换isExpanded
布尔值,从而导致每个辅助按钮的框架都更改为处理显示/隐藏。
To animate the panel, all we need to do is embed the call to toggle isExpanded
inside a withAnimation
block. This will automatically cause our secondary buttons to animate, since their frames depend on the isExpanded
State
. In the end, our ExpandableButtonPanel
struct
will look similar to this:
要为面板设置动画,我们需要做的就是将调用isExpanded
嵌入到withAnimation
块中。 这将自动使我们的辅助按钮具有动画效果,因为它们的帧取决于isExpanded
State
。 最后,我们的ExpandableButtonPanel
struct
将类似于以下内容:
You may notice I also added some styling to our panel by changing its background color, its corner radius (for rounded corners), its font size, and its shadow. Feel free to modify this as you like.
您可能会注意到,我还通过更改面板的背景色,圆角半径(圆角),字体大小和阴影为面板添加了一些样式。 随意修改它。
To use an ExpandableButtonPanel
, we can now do something like this:
要使用ExpandableButtonPanel
,我们现在可以执行以下操作:
ExpandableButtonPanel(
primaryItem: ExpandableButtonItem(label: "➕"), // No action
secondaryItems: [
ExpandableButtonItem(label: "🌞") {
// Can add action, if necessary
},
ExpandableButtonItem(label: "🥑") {
// Can add action, if necessary
}
]
)
We can also use our expandable button as a Floating Action Button (FAB). To achieve this, we can embed our main view’s content on a ZStack
, making sure that the ExpandableButtonPanel
is the top-most subview. We can embed the ExpandableButtonPanel
in a VStack
and/or HStack
and use a Spacer
to achieve any positioning we want. For example, if we want the FAB to be on the bottom right corner of our screen, we can do something like so:
我们还可以将可扩展按钮用作浮动操作按钮(FAB)。 为此,我们可以将主视图的内容嵌入ZStack
,确保ExpandableButtonPanel
是最顶层的子视图。 我们可以将ExpandableButtonPanel
嵌入VStack
和/或HStack
并使用Spacer
来实现所需的任何定位。 例如,如果我们希望FAB位于屏幕的右下角,则可以执行以下操作:
If we run our app, we should see the following result:
如果运行我们的应用程序,我们应该看到以下结果:
Thanks for reading! I hope you found this article useful. You can find a finished demo on GitHub.
谢谢阅读! 希望本文对您有所帮助。 您可以在GitHub上找到完成的演示。
翻译自: https://medium.com/swlh/expandable-button-in-swiftui-d87ab23a83d8
swiftui