SwiftUI 6.0(iOS 18/macOS 15)关于颜色 Color 的新玩法

概览
WWDC 2024 重装升级的 SwiftUI 6.0 让 Apple 不同平台(iOS 18/macOS 15)显得愈发的冰壶玉衡、美轮美奂。

之前梦寐以求的颜色混合功能在 WWDC 24 里终于美梦成真啦!
在本篇博文中,您将学到如下内容:
- 概览
- 1. 梦想成真:混合 Colors
- 2. 混合两种以上颜色
- 总结
相信学完本课之后,在 SwiftUI 6.0 中混合两种颜色将会变得轻而易举、小菜一碟。
那还等什么呢?让我们马上开始 Color 大“混战”吧!
Let‘s go!!!😉
1. 梦想成真:混合 Colors
何曾几时,在 SwiftUI 中我们希望有一种恣意混合多种颜色的方法。这不,在本届 WWDC 24 中苹果仿佛听到了我们秃头码农的心声。
于是乎,在 SwiftUI 6.0 中 Apple 终于为 Color 结构新增了 mix() 方法让“难关”冰解的破:


mix 方法签名很简单:我们只需传入两个需要混合的颜色、一个混合百分比(blending fraction)外加一个颜色空间(color space)即可。
值得说明的是,这里的颜色空间参数有两种选择:device 和 perceptual,默认情况下我们应该使用后者(perceptual)。因为从理论上来说,混合颜色的方式应该对人眼有意义,并且在不同设备屏幕之间是一致的。
而基于设备颜色空间(device)的混合可能产生不同的结果,这些结果也许是我们想要的,也许不是我们想要的。最佳方式是通过实验来查看实际的效果差异。
在下面的代码中,我们让粉色和蓝色以 50% 的混合度融合在了一起:
let leftColor = Color.pink
let rightColor = Color.blue
let mix = 0.5RoundedRectangle(cornerRadius: 16).fill(leftColor.mix(with: rightColor, by: mix, in: .perceptual)).frame(width: 100, height: 100)
在 Playground 中运行的效果如下图所示:

由于现在颜色可以神采飞扬的混合在一起了,所以这种混合效果可以被轻而易举的动画化。
struct ContentView: View {@State var showMixing = falsevar body: some View {VStack(spacing: 100) {RoundedRectangle(cornerRadius: 15).foregroundStyle(.red.mix(with: showMixing ? .black.opacity(0.88) : .red, by: 0.9, in: .perceptual)).frame(width: 200, height: 200)Toggle(isOn: $showMixing) {Text("显示混合动画")}.font(.largeTitle).toggleStyle(.button)}.animation(.smooth(duration: 5.0, extraBounce: 0.1), value: showMixing)}
}
在上面的代码中,我们通过 mix() 方法辅以万能的 animation() 动画修改器,让颜色渐变动画“活灵活现”:

借助 ColorPicker 颜色选择器视图,我们还可以恣意观赏不同颜色相互混合后的效果:
struct ColorMix: View {@State private var leftColor = Color.blue@State private var rightColor = Color.pink@State private var mix = 0.5var body: some View {VStack {HStack(spacing: 8) {ColorPicker("Left", selection: $leftColor).labelsHidden()ColorPicker("Right", selection: $rightColor).labelsHidden()}HStack {VStack {RoundedRectangle(cornerRadius: 16).fill(leftColor).frame(width: 100, height: 100)Text("\((1 - mix), format: .percent.precision(.fractionLength(0...2)))")}VStack {RoundedRectangle(cornerRadius: 16).fill(rightColor).frame(width: 100, height: 100)Text("\(mix, format: .percent.precision(.fractionLength(0...2)))")}}RoundedRectangle(cornerRadius: 16).fill(leftColor.mix(with: rightColor, by: mix, in: .perceptual)).frame(width: 100, height: 100).animation(.bouncy, value: mix)Slider(value: $mix, in: 0...1)}.padding()}
}
如上代码所示:我们使用两个 ColorPicker 视图来让用户选择自己心仪的颜色,并在底部的圆角矩形中通过颜色的 mix() 方法将它们的混合结果显示出来;我们还利用 SwiftUI 动画将混合效果表现的淋漓尽致、丝般顺滑。
编译并在 Xcode 预览中即可见运行效果:

2. 混合两种以上颜色
从 mix() 方法的参数上来看,貌似只能混合两种颜色。不过只要“略施小计”我们即可混合多种颜色:
struct ColorMix: View {@State private var leftColor = Color.blue@State private var rightColor = Color.pink@State private var midColor = Color.green@State private var mix = 0.5private var mixedColor: Color {let twoMix = leftColor.mix(with: rightColor, by: mix, in: .perceptual)return midColor.mix(with: twoMix, by: mix, in: .perceptual)}var body: some View {VStack {HStack(spacing: 8) {ColorPicker("Left", selection: $leftColor).labelsHidden()ColorPicker("Right", selection: $midColor).labelsHidden()ColorPicker("Right", selection: $rightColor).labelsHidden()}HStack {VStack {RoundedRectangle(cornerRadius: 16).fill(leftColor).frame(width: 100, height: 100)Text("\((1 - mix), format: .percent.precision(.fractionLength(0...2)))")}VStack {RoundedRectangle(cornerRadius: 16).fill(midColor).frame(width: 100, height: 100)Text("\(mix, format: .percent.precision(.fractionLength(0...2)))")}VStack {RoundedRectangle(cornerRadius: 16).fill(rightColor).frame(width: 100, height: 100)Text("\(mix, format: .percent.precision(.fractionLength(0...2)))")}}RoundedRectangle(cornerRadius: 16).fill(mixedColor).frame(width: 100, height: 100).animation(.bouncy, value: mixedColor)Slider(value: $mix, in: 0...1)}.padding()}
}
如上代码所示,我们通过 mixedColor 计算属性将左右两种颜色的混合结果再和中间的颜色相混合:
private var mixedColor: Color {let twoMix = leftColor.mix(with: rightColor, by: mix, in: .perceptual)return midColor.mix(with: twoMix, by: mix, in: .perceptual)
}
编译运行可见分晓:

现在,利用 SwiftUI 6.0 中颜色新增的 mix() 方法,让任何两种颜色“其乐融融”真是轻松的不要不要的!棒棒哒!💯
总结
在本篇博文中,我们讨论了在 SwiftUI 6.0(iOS 18/macOS 15)中颜色 Color 结构新增的 mix() 方法,现在融合任何颜色再也不是“黄粱一梦”了!
感谢观赏,再会!😎
相关文章:
SwiftUI 6.0(iOS 18/macOS 15)关于颜色 Color 的新玩法
概览 WWDC 2024 重装升级的 SwiftUI 6.0 让 Apple 不同平台(iOS 18/macOS 15)显得愈发的冰壶玉衡、美轮美奂。 之前梦寐以求的颜色混合功能在 WWDC 24 里终于美梦成真啦! 在本篇博文中,您将学到如下内容: 概览1. 梦想…...
C++核心编程运算符的重载
C核心编程运算符的重载 文章目录 C核心编程运算符的重载1.“”运算符的重载1.1 作为成员函数重载1.2 作为全局函数重载 2."<<"运算符重载2.1为什么需要重载左移运算符2.2如何重载左移运算符2.3注意事项 3.""运算符重载3.1 前置递增运算符重载3.2后置…...
雷达标定与解析
融合雷达与解析雷达数据的相关代码。感谢开源社区的贡献。以下代码继承了很多人的工作。 如果是单雷达: 直接进行标定,所以就是接收相关的话题然后发布。 lidar_calibration_params.yaml: calibration:在这个接口里面x_offset: 0.0y_offset:…...
养殖自动化温控系统:现代养殖场的智能守护神
现代农业养殖业中,养殖自动化温控系统已经成为提高生产效率和保障动物福利的关键技术之一。本篇文章将深入介绍养殖自动化温控系统的原理、组成、优势及其在不同类型养殖场中的应用实例,并展望该技术的未来发展。 一、养殖自动化温控系统概述 养殖自动…...
用python打印——九九乘法表2
for i in range(1, 10):for j in range(1, i 1):print(f"{j} * {i} {j * i}\t", end)j 1print()外层的 for 循环从 1 到 9 遍历 i。对于每个 i,内层的 for 循环从 1 到 i 遍历 j。在每次循环中,打印出 j 乘以 i 的结果,并以制表…...
如何系统学习机器学习?
我不是计算机专业,第一次接触机器学习还是在研一的时候,当时是看到机器学习可以做号码识别,就觉得好厉害,想学这个。 首次了解到Python这门语言,知道了机器学习可以做什么后,就感觉打开了新世界一样。再后来…...
Qt:1.杂谈
1.前端开发和Qt: 前端开发可以分为网页开发、移动端开发、桌面应用开发。Qt这个技术,是来开发电脑桌面应用程序的,也就是客户端程序的开发。属于比较经典的前端开发体系下。客户端开发的任务:编写和用户交互的界面或者应用程序。大…...
AI视频模型Sora核心功能以及应用场景
随着人工智能技术的飞速发展,AI在视频处理和生成领域的应用正变得越来越广泛。Sora,作为新一代AI视频模型,展示了前所未有的潜力和创新能力。本文将深入探讨Sora的功能、应用场景以及它所带来的革命性变化。 一、Sora的核心功能 1.1 视频生…...
面试-细聊synchronized
1.线程安全问题的主要诱因: 存在多条共享数据(临界资源) 存在多条线程共同操作这些共享数据 解决问题的根本方法: 同一时刻有且仅有一个线程在操作共享数据,其他线程必须等到该线程处理完数据后在对共享数据进行操作。 2.synchroized锁 分…...
AI降重新突破:chatgpt降重工具在学术论文中的应用与效果
论文降重一直是困扰各界毕业生的“拦路虎”,还不容易熬过修改的苦,又要迎来降重的痛。 其实想要给论文降重达标,我有一些独家秘诀。话不多说直接上干货! 1、同义词改写(针对整段整句重复) 这是最靠谱也是…...
Spring学习02-[Spring容器核心技术IOC学习]
Spring容器核心技术IOC学习 什么是bean?如何配置bean?Component方式bean配合配置类的方式import导入方式 什么是bean? 被Spring管理的对象就是bean,和普通对象的区别就是里面bean对象里面的属性也被注入了。 如何配置bean? Component方式、bean配合配置类的方式、import…...
2024上海CDIE 参展预告 | 一站式云原生数字化平台已成趋势
为什么企业需要进行数字化转型?大家都在讨论的数字化转型面临哪些困境?2024.6.25-26 CDIE数字化创新博览会现场,展位【A18】,期待与您相遇,共同探讨企业如何利用数字化技术驱动业务增长。 一、展会介绍——CDIE数字化…...
高考专业组 07组 08组 武汉大学
武汉大学的招生都什么废物点心,搜个专业组都没官方解释! 07组:理学,详见下表专业代码07xxxx,例如数学、物理、化学 08组:工学,详见下表专业代码08xxxx,例如机械、电子信息、自动化、…...
解析JavaScript中逻辑运算符和||的返回值机制
本文主要内容:了解逻辑运算符 &&(逻辑与)和 ||(逻辑或)的返回值。 在JavaScript中,逻辑运算符 &&(逻辑与)和 ||(逻辑或)的返回值可能并不总…...
Java中的数据结构与算法探秘
Java中的数据结构与算法探秘 大家好,我是免费搭建查券返利机器人省钱赚佣金就用微赚淘客系统3.0的小编,也是冬天不穿秋裤,天冷也要风度的程序猿! 引言 数据结构与算法是计算机科学的基础,对于Java程序员来说&#x…...
AST反混淆实战|嵌套的赋值语句通用还原处理
关注它,不迷路。 本文章中所有内容仅供学习交流,不可用于任何商业用途和非法用途,否则后果自负,如有侵权,请联系作者立即删除! 1.混淆代码 下面的这段代码是来自px3验证码核心混淆代码: function _u…...
Unity的ScrollView滚动视图复用
发现问题 在游戏开发中有一个常见的需求,就是需要在屏幕显示多个(多达上百)显示item,然后用户用手指滚动视图可以选择需要查看的item。 现在的情况是在100个data的时候,Unity引擎是直接创建出对应的100个显示item。 …...
详解Spring AOP(二)
目录 1.切点表达式 1.1execution表达式 1.2 annotation 1.2.1自定义注解MyAspect 1.2.3添加自定义注解 2.Sping AOP原理 2.1代理模式 2.1.1静态代理 2.1.2动态代理 2.1.3JDK动态代理 2.1.4CGLIB动态代理 3.总结 承接上文:详解Spring AOP(一&…...
sql-analysis
文章目录 痛点: 1、无法提前发现慢sql,可能恶化为慢sql的语句 2、线上出现慢sql后,无法快速止损 后果:一般是以响应时间来发现慢sql,这时候已经对业务产生了一定影响,这时候就要改代码重新发布上线或者改数…...
后台管理台字典localStorage缓存删除
localStorage里存放了如以下dictItems_开头的字典数据,localStorage缓存是没有过期时间的,需要手动删除。同时localStorage里还存有其他不需要删除的数据。 这里的方案是遍历localStorage,利用正则和所有key进行匹配,匹配到dict…...
<6>-MySQL表的增删查改
目录 一,create(创建表) 二,retrieve(查询表) 1,select列 2,where条件 三,update(更新表) 四,delete(删除表…...
【力扣数据库知识手册笔记】索引
索引 索引的优缺点 优点1. 通过创建唯一性索引,可以保证数据库表中每一行数据的唯一性。2. 可以加快数据的检索速度(创建索引的主要原因)。3. 可以加速表和表之间的连接,实现数据的参考完整性。4. 可以在查询过程中,…...
【SpringBoot】100、SpringBoot中使用自定义注解+AOP实现参数自动解密
在实际项目中,用户注册、登录、修改密码等操作,都涉及到参数传输安全问题。所以我们需要在前端对账户、密码等敏感信息加密传输,在后端接收到数据后能自动解密。 1、引入依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId...
macOS多出来了:Google云端硬盘、YouTube、表格、幻灯片、Gmail、Google文档等应用
文章目录 问题现象问题原因解决办法 问题现象 macOS启动台(Launchpad)多出来了:Google云端硬盘、YouTube、表格、幻灯片、Gmail、Google文档等应用。 问题原因 很明显,都是Google家的办公全家桶。这些应用并不是通过独立安装的…...
【论文笔记】若干矿井粉尘检测算法概述
总的来说,传统机器学习、传统机器学习与深度学习的结合、LSTM等算法所需要的数据集来源于矿井传感器测量的粉尘浓度,通过建立回归模型来预测未来矿井的粉尘浓度。传统机器学习算法性能易受数据中极端值的影响。YOLO等计算机视觉算法所需要的数据集来源于…...
华为OD机试-食堂供餐-二分法
import java.util.Arrays; import java.util.Scanner;public class DemoTest3 {public static void main(String[] args) {Scanner in new Scanner(System.in);// 注意 hasNext 和 hasNextLine 的区别while (in.hasNextLine()) { // 注意 while 处理多个 caseint a in.nextIn…...
Axios请求超时重发机制
Axios 超时重新请求实现方案 在 Axios 中实现超时重新请求可以通过以下几种方式: 1. 使用拦截器实现自动重试 import axios from axios;// 创建axios实例 const instance axios.create();// 设置超时时间 instance.defaults.timeout 5000;// 最大重试次数 cons…...
【MATLAB代码】基于最大相关熵准则(MCC)的三维鲁棒卡尔曼滤波算法(MCC-KF),附源代码|订阅专栏后可直接查看
文章所述的代码实现了基于最大相关熵准则(MCC)的三维鲁棒卡尔曼滤波算法(MCC-KF),针对传感器观测数据中存在的脉冲型异常噪声问题,通过非线性加权机制提升滤波器的抗干扰能力。代码通过对比传统KF与MCC-KF在含异常值场景下的表现,验证了后者在状态估计鲁棒性方面的显著优…...
【 java 虚拟机知识 第一篇 】
目录 1.内存模型 1.1.JVM内存模型的介绍 1.2.堆和栈的区别 1.3.栈的存储细节 1.4.堆的部分 1.5.程序计数器的作用 1.6.方法区的内容 1.7.字符串池 1.8.引用类型 1.9.内存泄漏与内存溢出 1.10.会出现内存溢出的结构 1.内存模型 1.1.JVM内存模型的介绍 内存模型主要分…...
《信号与系统》第 6 章 信号与系统的时域和频域特性
目录 6.0 引言 6.1 傅里叶变换的模和相位表示 6.2 线性时不变系统频率响应的模和相位表示 6.2.1 线性与非线性相位 6.2.2 群时延 6.2.3 对数模和相位图 6.3 理想频率选择性滤波器的时域特性 6.4 非理想滤波器的时域和频域特性讨论 6.5 一阶与二阶连续时间系统 6.5.1 …...
