携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第16天,点击查看活动详情。
项目背景
使用掘金App以来,对于掘金App端的设计风格和交互都是比较满意的。但某一天当我无聊点开“设置”页面的时候,一股浓浓的“不协调感”扑面而来。
啊这……这也太原始了吧,一点都不优雅。我不能让这种不优雅一直存在,于是就动手尝试做一个新的“设置”页面。
项目搭建
首先,创建一个新的SwiftUI
项目,命名为SettingView
。
页面样式
我们先来看下修改后最终的效果,示例:
在绘制整个页面之前,我们需要先行分析整个页面的结构,它包括顶部导航、个人信息栏、设置功能栏、退出登录按钮组成。
因此,在我们最开始写代码时,需要梳理好页面结构部分。
顶部导航
对于顶部导航栏来说,我们可以使用NavigationView
构建标准的顶部导航。示例:
NavigationView {
ZStack {
Color(red: 246 / 255, green: 246 / 255, blue: 246 / 255).edgesIgnoringSafeArea(.all)
}
.navigationBarTitle("设置", displayMode: .inline)
}
复制代码
上述代码中,我们除了使用navigationBarTitle
修饰符创建标题外,还使用ZStack
叠加视图和edgesIgnoringSafeArea
修饰符,给整个页面填充了一个背景颜色。
对于左侧返回按钮,我们可以单独构建样式,示例:
// 返回上一页
private var backToMineView: some View {
Button(action: {
}) {
Image(systemName: "arrow.backward")
.foregroundColor(.black)
}
}
复制代码
再使用navigationBarItems
修饰符创建导航栏按钮,示例:
.navigationBarItems(leading: backToMineView)
复制代码
个人信息栏
个人信息栏目需要突出个人的基础的账号信息,这里考虑的是使用用户头像、用户昵称、用户职务作为主要展示信息。示例:
// 个人信息
private var mineMessageView: some View {
Button(action: {
}) {
HStack(spacing: 15) {
Image("me")
.resizable()
.aspectRatio(contentMode: .fit)
.frame(width: 60)
.clipShape(Circle())
.overlay(Circle().stroke(Color(.systemGray5), lineWidth: 1))
VStack(alignment: .leading, spacing: 5) {
Text("文如秋雨")
.font(.system(size: 17))
.foregroundColor(.black)
Text("高级产品经理")
.font(.system(size: 14))
.foregroundColor(.gray)
}
}
.padding(.vertical, 10)
}
}
复制代码
上述代码中,我们使用Image
和Text
构建样式部分,文字部分使用VStack
纵向排布,整个文字部分和Image
图片采用HStack
横向排布,至于样式修饰符这里就不展开说了。
而在我们将视图展示前,我们还做需要做一件事情,由于个人信息栏、设置功能栏、退出按钮都是呈现分段式卡片效果,我们可以使用Form
表单和Section
段落来构建样式,示例:
Form {
Section {
mineMessageView
}
}
复制代码
我们发现了存在2个问题,一是整个App
的背景颜色由于Form
表单的样式影响被覆盖了,二是整个个人信息栏缺少了右边的“向右”按钮。
关于表单样式部分被覆盖的情况,我们可以在渲染页面时去掉背景颜色,这个我们之前做过,示例:
init() {
UITableView.appearance().backgroundColor = .clear
}
复制代码
而缺少“向右”的指示按钮,是因为我们要使用到基于NavigationView
顶部导航的跳转,当我们使用NavigationLink
作为跳转方法时,系统会自带指示按钮,所以在这里我们没有自己绘制按钮样式。
我们继续完成下面的内容。
设置功能栏
下一部分是设置功能栏,我们发现这样式之间有共通的地方,左侧图标加设置功能文字,右侧次要说明文字加跳转指示。
跳转指示我们依旧放在一边,我们面对具有相同样式式,常用的方式是抽离出来,这样可以减少代码量。示例:
// MARK: 栏目结构
struct listItemView: View {
var itemImage: String
var itemName: String
var itemContent: String
var body: some View {
Button(action: {
}) {
HStack {
Image(systemName: itemImage)
.font(.system(size: 17))
.foregroundColor(.black)
Text(itemName)
.foregroundColor(.black)
.font(.system(size: 17))
Spacer()
Text(itemContent)
.font(.system(size: 14))
.foregroundColor(.gray)
}.padding(.vertical, 15)
}
}
}
复制代码
我们构建一个新的视图listItemView
,声明一个必要变量:itemImage
图标、itemName
功能名称、itemContent
功能次要文字。
然后构建基础的样式框架,使用HStack
构建横向视图,放置1个Image
图片、2个Text
文本。
构建好后,我们在新的的Section
段落中构建样式。示例:
Section {
listItemView(itemImage: "lock", itemName: "账号绑定", itemContent: "已绑定")
listItemView(itemImage: "gear.circle", itemName: "通用设置", itemContent: "")
listItemView(itemImage: "briefcase", itemName: "简历管理", itemContent: "未上传")
listItemView(itemImage: "icloud.and.arrow.down", itemName: "版本更新", itemContent: "Version 6.2.8")
listItemView(itemImage: "leaf", itemName: "清理缓存", itemContent: "0.00MB")
listItemView(itemImage: "person", itemName: "关于掘金", itemContent: "")
}
复制代码
退出登录按钮
最后是退出登录按钮,我们构建一个新的视图,示例:
// 退出登录
private var signOutView: some View {
Button(action: {
}) {
Text("退出登录")
.font(.system(size: 17))
.frame(minWidth: 0, maxWidth: .infinity, minHeight: 30, maxHeight: 30)
.foregroundColor(.red)
.cornerRadius(8)
.padding(.vertical, 5)
}
}
复制代码
我们也在新的段落中构建样式,示例:
var body: some View {
NavigationView {
ZStack {
Color(red: 246 / 255, green: 246 / 255, blue: 246 / 255).edgesIgnoringSafeArea(.all)
Form {
Section {
mineMessageView
}
Section {
listItemView(itemImage: "lock", itemName: "账号绑定", itemContent: "已绑定")
listItemView(itemImage: "gear.circle", itemName: "通用设置", itemContent: "")
listItemView(itemImage: "briefcase", itemName: "简历管理", itemContent: "未上传")
listItemView(itemImage: "icloud.and.arrow.down", itemName: "版本更新", itemContent: "Version 6.2.8")
listItemView(itemImage: "leaf", itemName: "清理缓存", itemContent: "0.00MB")
listItemView(itemImage: "person", itemName: "关于掘金", itemContent: "")
}
Section {
signOutView
}
}
}
.navigationBarTitle("设置", displayMode: .inline)
.navigationBarItems(leading: backToMineView)
}
}
复制代码
项目展示
恭喜你,完成了本章的全部内容!
接下里的章节,我们将继续完成掘金App设置页面的功能详情页,敬请期待!
快来动手试试吧。
如果本专栏对你有帮助,不妨点赞、评论、关注~