深色模式是iOS 13系统推出的界面颜色系统,区别于原有的浅色模式。
深色适配几种情况
1> 默认情况下应用不做任何处理是需要跟随手机系统做深色适配
2> 如果整个应用中坚持是Light 或者Dark模式,需要在info.plist
中 添加 UIUserInterfaceStyle 为 Light 或者Dark
3> 部分UIView / UIViewcontroller / UIWindow 不跟随手机深色适配,需要在界面上重写overrideUserInterfaceStyle.
系统颜色(UIColor)
iOS13之前UIColor只能表示一种颜色,从iOS13开始UIColor是一个动态的颜色,在不同模式下可以分别代表不同的颜色;
下面是iOS13系统提供的动态颜色种类, 使用以下颜色值, 在模式切换时, 则不需要做特殊处理
@interface UIColor (UIColorSystemColors)
#pragma mark System colors
@property (class, nonatomic, readonly) UIColor *systemRedColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemGreenColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemBlueColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemOrangeColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemYellowColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemPinkColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemPurpleColor API_AVAILABLE(ios(9.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemTealColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemIndigoColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
// 灰色种类, 在Light模式下, systemGray6Color更趋向于白色
@property (class, nonatomic, readonly) UIColor *systemGrayColor API_AVAILABLE(ios(7.0), tvos(9.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *systemGray2Color API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *systemGray3Color API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *systemGray4Color API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *systemGray5Color API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *systemGray6Color API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
#pragma mark Foreground colors
@property (class, nonatomic, readonly) UIColor *labelColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *secondaryLabelColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *tertiaryLabelColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *quaternaryLabelColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
// 系统链接的前景色
@property (class, nonatomic, readonly) UIColor *linkColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
// 占位文字的颜色
@property (class, nonatomic, readonly) UIColor *placeholderTextColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
// 边框或者分割线的颜色
@property (class, nonatomic, readonly) UIColor *separatorColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
@property (class, nonatomic, readonly) UIColor *opaqueSeparatorColor API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
#pragma mark Background colors
@property (class, nonatomic, readonly) UIColor *systemBackgroundColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *secondarySystemBackgroundColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *tertiarySystemBackgroundColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *systemGroupedBackgroundColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *secondarySystemGroupedBackgroundColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *tertiarySystemGroupedBackgroundColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
#pragma mark Fill colors
@property (class, nonatomic, readonly) UIColor *systemFillColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *secondarySystemFillColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *tertiarySystemFillColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
@property (class, nonatomic, readonly) UIColor *quaternarySystemFillColor API_AVAILABLE(ios(13.0)) API_UNAVAILABLE(tvos, watchos);
#pragma mark Other colors
// 这两个是非动态颜色值
@property(class, nonatomic, readonly) UIColor *lightTextColor API_UNAVAILABLE(tvos); // for a dark background
@property(class, nonatomic, readonly) UIColor *darkTextColor API_UNAVAILABLE(tvos); // for a light background
@property(class, nonatomic, readonly) UIColor *groupTableViewBackgroundColor API_DEPRECATED_WITH_REPLACEMENT("systemGroupedBackgroundColor", ios(2.0, 13.0), tvos(13.0, 13.0));
@property(class, nonatomic, readonly) UIColor *viewFlipsideBackgroundColor API_DEPRECATED("", ios(2.0, 7.0)) API_UNAVAILABLE(tvos);
@property(class, nonatomic, readonly) UIColor *scrollViewTexturedBackgroundColor API_DEPRECATED("", ios(3.2, 7.0)) API_UNAVAILABLE(tvos);
@property(class, nonatomic, readonly) UIColor *underPageBackgroundColor API_DEPRECATED("", ios(5.0, 7.0)) API_UNAVAILABLE(tvos);
@end
系统新增的api:提供一个block,可以根据当前的模式返回不同的颜色
+ (UIColor *)colorWithDynamicProvider:(UIColor * (^)(UITraitCollection *traitCollection))dynamicProvider API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
- (UIColor *)initWithDynamicProvider:(UIColor * (^)(UITraitCollection *traitCollection))dynamicProvider API_AVAILABLE(ios(13.0), tvos(13.0)) API_UNAVAILABLE(watchos);
例如:
UIColor *color = [UIColor colorWithDynamicProvider:^UIColor * _Nonnull(UITraitCollection * _Nonnull traitCollection) {
if (traitCollection.userInterfaceStyle == UIUserInterfaceStyleDark) {
return [UIColor blackColor];
} else {
return [UIColor whiteColor];
}
}];
self.backgroundColor = color;
颜色整理(参考appstore)
1.背景色
导航栏(状态栏)底色:灰色带透明度,返回按钮蓝色箭头,导航栏左侧文字蓝色,中间文字白色、右侧文字蓝色
标签栏背景色:灰色1带透明度,标签栏图标灰色2和蓝色
标签子模块界面背景色:黑色
分割线条背景色:灰色
按钮背景色:灰色4,文字白色或蓝色
搜索框背景色:灰色5,取消文字蓝色,搜索文字白色
信息界面:左侧文字灰色、右侧文字白色,右侧图标蓝色、箭头灰色
更多、查看全部、链接文字颜色:蓝色
评论回复:文字白色,右侧文字灰色、更多蓝色、日期灰色、用户名灰色
横向滚动列表背景色:黑色,外部单元格黑色,内部单元格无色
纵向滚动列表背景色:黑色,外部单元格灰色,内部单元格无色
列表组头:文字颜色白色
单元格:标题文字白色,描述文字灰色,按钮背景色灰色4,按钮文字颜色蓝色
详情页背景色:黑色
2.字体颜色
导航栏:中间白色、左右侧蓝色
标签栏:蓝色、灰色
文本文字:标题白色、描述灰色,
按钮文字:蓝色或白色
代码层面
1.Info.plist文件移除UIUserInterfaceStyle
2.AppDelegate.m:去掉主窗口的固定模式
if (@available(iOS 13.0, *)) {
self.window.overrideUserInterfaceStyle = UIUserInterfaceStyleLight;
}
3.设置状态栏样式:重载界面的属性preferredStatusBarStyle,放基类统一处理
-(UIStatusBarStyle)preferredStatusBarStyle{
if (@available(iOS 13.0, *)) {
UIUserInterfaceStyle style = UITraitCollection.currentTraitCollection.userInterfaceStyle;
if (style == UIUserInterfaceStyleDark) {
return UIStatusBarStyleLightContent;
}
else{
return UIStatusBarStyleDarkContent;
}
} else {
// Fallback on earlier versions
return UIStatusBarStyleLightContent;
}
}
4.设置导航栏统一底色、文字颜色:放根视图控制器
-(void)initNavigateBarStyle{
self.navBar = [UINavigationBar appearance];
NSDictionary *dict;
if (@available(iOS 13.0, *)) {
UIUserInterfaceStyle style = UITraitCollection.currentTraitCollection.userInterfaceStyle;
if (style == UIUserInterfaceStyleDark) {
[self.navBar setBarTintColor:colorWithRGB(NAVIGATIONBAR_BARTINTCOLOR_DARK)];
dict = @{NSForegroundColorAttributeName : [UIColor whiteColor]};
}
else{
[self.navBar setBarTintColor:colorWithRGB(NAVIGATIONBAR_BARTINTCOLOR)];
dict = @{NSForegroundColorAttributeName : [UIColor colorWithRed:40/255.0 green:40/255.0 blue:40/255.0 alpha:1]};
}
} else {
// Fallback on earlier versions
[self.navBar setBarTintColor:colorWithRGB(NAVIGATIONBAR_BARTINTCOLOR)];
dict = @{NSForegroundColorAttributeName : [UIColor colorWithRed:40/255.0 green:40/255.0 blue:40/255.0 alpha:1]};
}
self.navBar.translucent = NO;
[self.navBar setShadowImage:[UIImage new]];
[self.navBar setTitleTextAttributes:dict];
}
5.监听深色、浅色模式切换:UIViewController和UIView都有实现UITraitEnvironment协议
-(void)traitCollectionDidChange:(UITraitCollection *)previousTraitCollection{
NSLog(@"traitCollectionDidChange");
//UIViewController监听:需要更新导航栏样式、界面的uiview样式
//UIView监听:需要更新控件的颜色样式
}
6.UIViewController和UIView初始化:需要判断当前模式设置界面元素的颜色样式