皮膚配置文件創建
1、皮膚顏色資源和圖片路徑配置
如圖所示,創建 light.json 和 dark.json ( light 和 dark 配置路徑key 一樣,對應的value 不同)
light.json 配置示例
{
"statusBarStyle": "black",
"colors":{
"mainFunction":"#E92424",
"gradientStockUp":[
"#0FFFFFFF",
"#0FE92424"
]
},
"images": {
"selfStock_info_icon": "appres/skinImage/light/selfStock_info_icon.png",
"selfStock_money_icon": "appres/skinImage/light/selfStock_money_icon.png",
}
// appres/skinImage/light/selfStock_info_icon.png 對應的圖片文件夾路徑
}
dark.json 配置示例
{
"statusBarStyle": "red",
"colors":{
"mainFunction":"#BC935C",
"gradientStockUp":[
"#26171717",
"#26E92424"
]
},
"images": {
"selfStock_info_icon": "appres/skinImage/dark/selfStock_info_icon.png",
"selfStock_money_icon": "appres/skinImage/dark/selfStock_money_icon.png",
}
}
2、設置全局的colorKey 來對應顏色路徑 imageKey 來對應圖片路徑,利于維護
皮膚使用
1、獲取皮膚資源協議方法
// 獲取皮膚資源協議方法
- (HJThemeDataModel *)getThemeModelWithName:(NSString *)name {
NSString *path = [NSString stringWithFormat:@"appres/theme/%@",name];
NSDictionary *colorDic = [self getDictFromJsonName:path][@"colors"];
NSDictionary *imageDic = [self getDictFromJsonName:path][@"images"];
HJThemeDataModel *model = [HJThemeDataModel new];
model.colorDic = colorDic;
model.imageDic = imageDic;
return model;
}
/// 設置默認主題(使用皮膚,至少有一個默認皮膚)
- (HJThemeDataModel *)getDefaultThemeModel {
return [self getThemeModelWithName:@"light"];
}
2、皮膚使用
// 導入頭文件
#import "HJThemeManager.h"
// 設置當前皮膚 或切換 皮膚為 @"light"
[[HJThemeManager sharedInstance] switchThemeWithName:@"light"];
// 設置當前view 的背景色
//1、適配皮膚
self.view.themeBackgroundColor = backgroundColorKey;
//2、不適配皮膚,必須帶#號
self.view.themeBackgroundColor = @“#333333”;
//3、適配皮膚,隨皮膚變化
self.view.themeBackgroundColor = [HJThemeManager getThemeColor:backgroundColorKey];
//4、指定皮膚,不會隨皮膚變化
self.view.themeBackgroundColor = [HJThemeManager getThemeColor:backgroundColorKey themeName:@"light"];
/**
* [HJThemeManager getThemeColor:backgroundColorKey];
* 實質上是 theme://"backgroundColorKey"?
*
* [HJThemeManager getThemeColor:backgroundColorKey themeName:@"light"];
* 實質上是 theme://"backgroundColorKey"?themeName=light
*/
//所以可以直接寫URL 例如:
self.view.themeBackgroundColor = theme://backgroundColorKey?themeName=light;
// 設置當前imageView 的image
//1、適配皮膚
imageView.themeImage = imageKey;
//2、適配皮膚,隨皮膚變化
imageView.themeImage = [HJThemeManager getThemeImage:imageKey];
//3、指定皮膚,不會隨皮膚變化
imageView.themeImage = [HJThemeManager getThemeImage:imageKey themeName:@"light"];
/**
* [HJThemeManager getThemeImage:imageKey];
* 實質上是 theme://"imageKey"?
*
* [HJThemeManager getThemeImage:imageKey themeName:@"light"];
* 實質上是 theme://"imageKey"?themeName=light
*/
//完整寫法,指定皮膚
imageView.themeImage = theme://"imageKey"?themeName=light;
// 兼容不適配皮膚寫法
// imageNamed 加載圖片
imageView.themeImage = bundle://"imageKey";
// sdwebimage 解析 http/https 加載圖片
imageView.themeImage = http://imagePath;
// 使用serverManager getimage 的協議方法獲取圖片
imageView.themeImage = imagePath;
3、皮膚的實現原理
1、創建一個NSObject
分類(category),然后關聯一個字典屬性(themes),用于進行緩存UI控件調用的顏色方法和參數或者是圖片方法和參數。再關聯屬性的時候添加一個通知監聽,用于切換皮膚時,發送通知,然后再次調用緩存的方法和參數,進行顏色和圖片的更換。
2、創建UI控件的分類(category),然后每個分類都有themes字典,然后設置新的方法來設置顏色或圖片。在該方法內,需要做的處理有:
顏色舉例說明:themeBackgroundColor = colorKey
a、在 themeBackgroundColor 的set方法中,判斷是否是皮膚設置,皮膚的設置都是帶有 theme:// 的字符串。這個(theme://)字符串是約定的。
b、皮膚適配模式,即帶有 theme:// 字符串,就會用 themes 字典保存 系統的方法setBackgroundColor:
方法和參數colorKey
和themeName
,當切換皮膚時,再次調用setBackgroundColor:
方法和參數colorKey
和themeName
c、@"#333333", 直接是色值方法的 不需要 themes 字典保存,只需要直接調用系統方法 setBackgroundColor:[UIColor colorFromHexString:@"#333333"];
圖片舉例說明:imageView.themeImage = imageKey
a、在 themeImage 的set方法中,判斷是否是皮膚設置,皮膚的設置都是帶有 theme:// 的字符串。這個(theme://)字符串是約定的。
b、皮膚適配模式,即帶有 theme:// 字符串,就會用 themes 字典保存 系統的方法setImage:
方法和參數imageKey
和themeName
,當切換皮膚時,再次調用setImage:
方法和參數imageKey
和themeName
c、bundle://, 直接是調用系統方法setImage:[UIImage imageNamed:@"imageNamed"] 進行賦值,不需要進行 themes 字典保存處理;
d、http:// 或 https:// , 采用SD框架加載圖片,不需要進行 themes 字典保存處理;
3、主要的UI控件的分類
#import <UIKit/UIKit.h>
#import <Foundation/Foundation.h>
@interface UIView (CMSThemeView)
/// 設置皮膚文件名稱 默認為空值,取當前皮膚
/// 可以設置指定皮膚 例如: @"Dark" / @"Light" ;
/// defaultThemeKey 為默認皮膚
/// 如何設置 Color 或 Image 有 themeName ,優先使用 themeName
指定皮膚
@property (nonatomic, copy) NSString *themeStyle;
@property (nonatomic, copy) NSString *themeBackgroundColor;
@property (nonatomic, copy) NSString *themeTintColor;
/// 根據路徑獲取color 并緩存方法和參數 ()
- (void)setThemeColorWithIvarName:(NSString *)ivarName colorPath:(NSString *)path;
@end
@interface UILabel (ThemeLabel)
@property (nonatomic, copy) NSString *themeTextColor;
@property (nonatomic, copy) NSString *themeHighlightedTextColor;
@property (nonatomic, copy) NSString *themeShadowColor;
/// 主要是顏色
@property (nonatomic, strong) NSAttributedString *themeAttributedText;
@end
@interface UITextField (ThemeTextField)
@property (nonatomic, copy) NSString *themeTextColor;
@end
@interface UIImageView (CMSThemeImageView)
@property (nonatomic, copy) NSString *themeImage;
// 帶有 UIImageRenderingMode 的處理,image 修改渲染色的,即tintColor
- (void)themeSetImageKey:(NSString *)imageKey
renderingMode:(UIImageRenderingMode)mode;
@end
@interface UIButton (ThemeButton)
- (void)themeSetImage:(NSString *)path forState:(UIControlState)state;
- (void)themeSetImage:(NSString *)path forState:(UIControlState)state renderingMode:(UIImageRenderingMode)mode;
- (void)themeSetBackgroundImage:(NSString *)path forState:(UIControlState)state;
- (void)themeSetTitleColor:(NSString *)path forState:(UIControlState)state;
@end
@interface UITableView (ThemeTableView)
@property (nonatomic, copy) NSString *themeSeparatorColor;
@end
@interface CALayer (ThemeLayer)
/// 設置皮膚文件名稱 默認為空值,取當前皮膚 eg: @"Dark" / @"Light" ; defaultThemeKey 為默認皮膚
@property (nonatomic, copy) NSString *themeStyle;
@property (nonatomic, copy) NSString *themeBackgroundColor;
@property (nonatomic, copy) NSString *themeBorderColor;
@property (nonatomic, copy) NSString *themeShadowColor;
/// 根據路徑獲取cgcolor 并緩存方法和參數 ()
- (void)setThemeCGColorWithIvarName:(NSString *)ivarName colorPath:(NSString *)path;
@end
以上是簡單列舉了幾個,其他UIKIt 控件一樣分類處理即可
皮膚顏色流程圖
皮膚圖片流程圖
存在的缺陷
1、不能全局統一處理,需要一處一處的設置,比較麻煩。
2、目前還不支持網絡下載皮膚功能,需要其他位置處理下載解壓過程。
3、XIB的使用還需要其他的處理,這個比較重要