Demo連接git
Sketch程序員
Sketch 是一款Mac上小巧但功能強大的矢量繪圖軟件,這是專爲設計師而打造的矢量繪圖軟件,擁有簡約的設計,調色板,面板,菜單,窗口,控件和功能強大的矢量繪圖和文字工具;包含針對UI設計的操做和交互模式,讓你設計圖標、移動手機UI、網站UI等更加簡單高效。github
PaintCodeobjective-c
PaintCode 是一款 Mac 上的 iOS 矢量繪圖編程軟件,不管是程序員仍是設計師,PaintCode 可以讓你像在PS中畫圖同樣繪製各類UI圖形,PaintCode 會自動幫你生成針對 Mac OS X 或 iOS 平臺 Objective-C 或 C# 代碼,可以節約大量的編程時間,支持將代碼直接導入到 Xcode 中或導出爲 PSD 文件,支持最新的 iOS 和 iWatch SDK,很是的實用!編程
推薦使用 HighChart 地圖數據,在這裏你能夠自由的選擇國內的某個省份地圖下載相應的 svg 文件,這裏選擇福建省做爲一個例子。數組
因爲經過 HighChart 地圖數據下載的 svg 文件有一些 logo 文字信息的部分圖層是咱們開發時不須要的,並且會干擾地圖的顯示,因此使用 Sketch 去除這些部分。ide
使用 Sketch 打開下載的 svg 文件,屏蔽這些無用的信息圖層svg
從新導出得新 svg 文件纔是咱們接下來要用到地圖文件工具
經過 PaintCode 打開 svg 文件字體
咱們能夠看到 PaintCode 已經自動爲咱們生成了 Objective-C 代碼,可是這只是圖塊的 UIBezierPath 路徑代碼,咱們還須要添加文字和圖釘的相應位置,接下來咱們經過 PaintCode 添加這些內容。
添加 Text,設置文字,調節文字位置以及字體大小爲11,PaintCode 也自動生成了相應的代碼。
添加圖釘 Rect,調節 Rect 的位置,寬高都設置爲20。
按照上面的步驟添加其餘的市名和圖釘位置,而且導出代碼文件。
PaintCode 生成的文件包含了圖塊,文字,圖釘三項內容的繪製代碼,咱們須要對這三項內容進行抽取和整理,這裏以福建省爲例。
+ (void)drawCanvas2WithFrame: (CGRect)targetFrame resizing: (FujianResizingBehavior)resizing
{
//// General Declarations
CGContextRef context = UIGraphicsGetCurrentContext();
//// Resize to Target Frame
CGContextSaveGState(context);
CGRect resizedFrame = FujianResizingBehaviorApply(resizing, CGRectMake(0, 0, 308, 340), targetFrame);
CGContextTranslateCTM(context, resizedFrame.origin.x, resizedFrame.origin.y);
CGContextScaleCTM(context, resizedFrame.size.width / 308, resizedFrame.size.height / 340);
UIColor* strokeColor = [UIColor colorWithRed: 0.8 green: 0.8 blue: 0.8 alpha: 1];
UIColor* fillColor = [UIColor colorWithRed: 0.486 green: 0.71 blue: 0.925 alpha: 1];
//// 頁面1
{
//// chart-(1)
{
//// Clipped
{
//// Group 編組 5
{
//// Group 6
{
//// Bezier 形狀 2 Drawing
UIBezierPath* bezier2Path = [UIBezierPath bezierPath];
[bezier2Path moveToPoint: CGPointMake(215.48, 200.9)];
[bezier2Path addLineToPoint: CGPointMake(214.85, 200.27)];
[bezier2Path addLineToPoint: CGPointMake(215.17, 199.01)];
[bezier2Path addLineToPoint: CGPointMake(215.8, 199.32)];
[bezier2Path addLineToPoint: CGPointMake(216.43, 198.06)];
......
[bezier2Path closePath];
[bezier2Path moveToPoint:
[bezier2Path closePath];
[fillColor setFill];
[bezier2Path fill];
[strokeColor setStroke];
bezier2Path.lineWidth = 1;
bezier2Path.miterLimit = 4;
[bezier2Path stroke];
}
......
}
}
}
}
//// Text Drawing
CGRect textRect = CGRectMake(128, 71, 39, 26);
{
NSString* textContent = @"南平市";
NSMutableParagraphStyle* textStyle = [[NSMutableParagraphStyle alloc] init];
textStyle.alignment = NSTextAlignmentLeft;
NSDictionary* textFontAttributes = @{NSFontAttributeName: [UIFont systemFontOfSize: 11], NSForegroundColorAttributeName: UIColor.blackColor, NSParagraphStyleAttributeName: textStyle};
CGFloat textTextHeight = [textContent boundingRectWithSize: CGSizeMake(textRect.size.width, INFINITY) options: NSStringDrawingUsesLineFragmentOrigin attributes: textFontAttributes context: nil].size.height;
CGContextSaveGState(context);
CGContextClipToRect(context, textRect);
[textContent drawInRect: CGRectMake(CGRectGetMinX(textRect), CGRectGetMinY(textRect) + (textRect.size.height - textTextHeight) / 2, textRect.size.width, textTextHeight) withAttributes: textFontAttributes];
CGContextRestoreGState(context);
}
......
//// Rectangle Drawing
UIBezierPath* rectanglePath = [UIBezierPath bezierPathWithRect: CGRectMake(135, 56, 20, 20)];
[UIColor.grayColor setFill];
[rectanglePath fill];
......
CGContextRestoreGState(context);
}
複製代碼
咱們只須要摘取 UIBezierPath
的路徑部分代碼便可,也就是每個 bezierPath
在如下代碼以前的路徑代碼(換個說法就是刪除每一個bezierPath
的如下代碼)
[fillColor setFill];
[bezier2Path fill];
[strokeColor setStroke];
bezier2Path.lineWidth = 1;
bezier2Path.miterLimit = 4;
[bezier2Path stroke];
複製代碼
整理後的 bezierPath
放在 FujianMapPath
的 pathArray
中。
咱們只須要摘取每段 textRect
的 frame 便可,
CGRect textRect = CGRectMake(128, 71, 39, 26);
複製代碼
整理後的 textRect
放在 FujianMapPath
的 textRectArray
中,使用 NSValue
存儲。文字內容須要另外存儲在在 FujianMapPath
的 textArray
中。
咱們只須要摘取每段 rectanglePath
的起始點便可,
UIBezierPath* rectanglePath = [UIBezierPath bezierPathWithRect: CGRectMake(135, 56, 20, 20)];
=> CGPointMake(135, 56)
複製代碼
整理後的 point
放在 FujianMapPath
的 pinPointArray
中。
須要注意的是,咱們自行繪製的文字部分和圖塊部分的市區順序通常是不一致的,因此咱們要根據圖塊順序調換 textArray、textRectArray 和 pinPointArray 中市區的順序
/// 自定義的地圖快捷建立方法
/// @param mapPath svg 繪圖數據
/// @param mapSize svg 繪圖尺寸,即 svg 文件中圖層的寬高
/// @param frame 視圖控件的frame
- (instancetype)initWithMapPath:(ChinaMapPath *)mapPath andMapSize:(CGSize)mapSize andFrame:(CGRect)frame;
複製代碼
示例:
- (void)viewDidLoad {
[super viewDidLoad];
self.view.backgroundColor = [UIColor whiteColor];
// 福建省市數據
FujianMapPath *mapPath = [[FujianMapPath alloc] init];
self.chinaMapView = [[CXProvincesMapView alloc]initWithMapPath:mapPath andMapSize:CGSizeMake(308, 340) andFrame:CGRectMake(0, 0, self.view.bounds.size.width, 400)];
_chinaMapView.backgroundColor = [UIColor colorWithRed:230/255.0 green:1.0 blue:1.0 alpha:1.0];
_chinaMapView.maximumZoomScale = 5.0;
_chinaMapView.center = self.view.center;
_chinaMapView.delegate = self;
// _chinaMapView.pinAnimation = NO;
// 直接設置圖片
// _chinaMapView.pinImage = [UIImage imageNamed:@"pin"];
// 添加按鈕點擊
UIButton *pinButton = [[UIButton alloc]initWithFrame:_chinaMapView.pinView.bounds];
[pinButton setImage:[UIImage imageNamed:@"pin"] forState:UIControlStateNormal];
[pinButton addTarget:self action:@selector(pinTest) forControlEvents:UIControlEventTouchUpInside];
[_chinaMapView.pinView addSubview:pinButton];
[self.view addSubview:_chinaMapView];
}
複製代碼
效果:
以上步驟看起來繁瑣,實際上操做起來並非很複雜,主要的代碼部分 PaintCode 已經爲咱們生成好了,能夠在有 svg 圖片的前提下生成任意的地圖區域控件,CXProvincesMapView
中國省份地圖區域的控件也是這樣子生成的。假如你不須要文字或者圖釘部分,你能夠不用另外繪製文字或者圖釘,相對應的數組傳入空值就好了。
完結散花(^▽^),但願這篇教程對你有幫助!