PaintCode 教程1:动态绘制按钮


PaintCode
 是一个可以让你像Photoshop同样去设计你的用户界面的软件 – 可是它并非仅仅保存一张图片看成资源让你来使用,它可以为你生成 CoreGraphic 源码直接使用到View的绘制中.
能够简单地说,咱们看重的是下面几点: ios

  • 节省了开发时间。 若是一行一行的去写 Core Graphics 代码,绝对会比用 PaintCode多不少时间。 而时间就是金钱!
  • 减小了程序包大小。 用代码去绘制各类view,可让你再也不去添加图片资源,减小了资源包大小。
  • 让它能作更动态的改变。. 最后,咱们能够作更多相比于使用图片作不到的事情,好比:能够在程序运行时轻松的改变控件的颜色。

深刻: 这篇教程实际基于咱们收到的一些 PaintCode 的使用反馈来写的。 可是, 教程里的的全部意见和建议绝对没有一点瞎掰,绝对原创。
想要尽量的利用学习这篇教程,你们至少知道一点iOS开发。 而且,懂一些 Core Graphics知识会更好(不是100%要求)。 若是你们历来没据说过 Core Graphics,真心推荐去看看 Core Graphics系列教程 
废话很少说,切入正题吧! spring

准备开始

PaintCodeIcon.175x175-75要学习这一系列的PaintCode 教程, 首先咱们须要有个 PaintCode 软件。你们能够在这里下载 试用版, 或者从 Mac App Store购买完整版。 canvas

尽管这个app仍是算比较贵的,可是就我看来,他在生产中的能发挥的价值彻底能物超所值。 若是你们还不肯定, 下载一个试用版在这个教程里试试吧! 数组


建立第一个动态按钮

在敲任何代码以前,咱们将会使用 PaintCode 来设计一个全新的按钮。
打开 PaintCode,选择 FileSave,而后把这个项目命名为 DynamicButton.。这样的话咱们就能够在进行这个教程的时候时时的保存了。
点击屏幕右下的Canvas 按钮, 而后把画布大小设置为宽 480 高 150 pixels,以下图所示:
PaintCode canvas size in new document
而后经过设置 Underlay color 的RGB值为 50 50 50来吧画布的颜色改成浅灰色,以下:
Canvas color in PaintCode xcode

注意: 咱们默认是在非高清画布上工做,若是你们想看高清的效果,点击Canvas按钮边上的 Retina按钮。这个按钮可让你在高清和非高清之间切换。 app

如今选中工具栏里的Round Rect 按钮,而后在画布里拖出一个方形来。
咱们能看到,当咱们在画布里选中一个形状的时候,左边会出现这个形状的全部属性。确保选中了刚才的这个方形,而后把它的属性修改成以下: 编辑器

  • X: 4
  • Y: 4
  • Width: 473
  • Height: 41

draw a rectangle in PaintCode
接下来,为了改变按钮的颜色,咱们须要设置它的Fill值。
在左边的属性栏里, 点击 Fill,,在弹出的选项里选择 Add New Gradient,而后命名为 ButtonGradient。如今, 点击 左下的 color stop。 这些在颜色区域底部圆形的颜色选取点是用来给渐变提供所需参数的。
接着,选着右下方的调色盘,而后RGB输入255 0 0,以下所示:
Setting the button gradient colors
再次点击调色盘按钮来关掉它。
如今, 用一样的办法把右边的颜色选取点的 RGB 改成 112 1 0 ,以下:
Setting the button gradient colors
PaintCode 让你可以去给每一个使用在形状上的颜色命名,由于它们以一样的名字出如今代码里。 若是界面下方没有代码窗口,选择 View > Code 来打开它。 下面图片里高亮的那两行应该就是刚才咱们建立的2个颜色。
Color variable in PaintCode Code view
为了更好的找到这些颜色,咱们最好给他们一个描述性较高的名字。
选中 Colors 选择栏,在左边栏下面找到并双击 Fill Color。在弹窗里把它的名字改成 ButtonColorDark,以下所示:
rename color in PaintCode
同理把Stroke Color 名字改成 ButtonColorLight。
如今回到位于中间的形状属性栏,选择 Stroke 下来框里的 System Colors > Common Colors > BlackColor,以下图所示,把描边颜色改成黑色。
add a stroke color in PaintCode
Increase the Width parameter to 2 under the Stroke sub-section, as so:
stroke width in PaintCode
如今,咱们要给按钮加一个为发光 ,选择 Add New Shadow… 在Fill的下拉框里选择 Outer Shadow,以下所示:
Add new shadow in PaintCode
像上面的按钮同样给这个阴影一个好的名字,把它名字改成 OuterGlow。 接下来, 选中 Color边上的下拉框,而后在颜色选取框里选着白色框, 打开边上的那个颜色调整按钮
把阴影偏移和阴影大小调整为下图同样:
Adding a glow in PaintCode
切换到 Colors 选项卡下面而后把 Glow 改成 InnerGlowColor。
接着,在Add New Shadow的下拉框里面给 Inner Shadow 加一个内高光。把这个高光命名为Highlight, 颜色设置为 白色,透明度为 130, 而后把offsets 和 blur radius设置为以下所示:

根据前面的教程。这个颜色的名字可能已是默认的 Shadow Color 2 ,若是不同,就把它改为这个名字。
如今,咱们的按钮应该和下面同样了:
Final Button
到这个时候,咱们的按钮已经看起来挺不错的了,可是他的大小是定死了的。要让它能够随意的改变大小,咱们须要给他加一个frame。 咱们会在代码里改变它的大小,接下来咱们会在PaintCode里面设置frame,这样可让里面的全部东西都是可变大小的。 ide

给按钮加Frame

在顶部工具栏里选择 Frame ,而后画一个框包住按钮。把这个frame的属性设置为以下:
Adding a frame for the button
同时选中Frame 和 Rounded Rectangle, 按下 Option-Command-G 组合键来把它们放在一个group里。 或者, 咱们能够选择去按菜单里的 Selection > Group来达到一样的效果。 最后吧这个group米命名为Button。
咱们如今能够看到在左边的边栏最顶上,可能看到button group 和它包括2个元素,以下所示:
Grouping elements
在左边面板里选中 Rounded Rectangle。 找到设置这个形状大小限定的区域 – 它是在坐标设置左边的一个方框, 里面包含了几个杆状,弹簧状的横条。
ResizeWindow
咱们如今须要这个按钮可以水平的竖直的去改变大小,同时又能保持水平中心不变。 因此咱们就要吧外部的约束设置为直的(固定了大小), 而后底部应该设置为弹簧条(可以随意的改变大小)。 这样就能让按钮保持在水平中心对齐了。
可是,为了能让按钮能随意的改变大小和frame同样,咱们须要吧方框里面的杆都改为弹簧。
咱们仅仅须要点一下这些杆,就可让他们在直杆和弹簧之间切换。
当你们完成了修改约束,样子应该以下所示:
Button constraints
到这里,已经完成了大部分工做了! 如今咱们选中按钮边上的 Frame,而后随便把这个按钮左右上下拖动试试,它的样子大概以下图:
Final button
如今PaintCode里的画图这部分的工做已经完成 —咱们接下来要开始把它加入xcode里了。 工具

加入iOS项目里

在完成了咱们项目所用到的按钮之后— 固然,咱们没有写一行代码!别急,如今卷起袖口准备开始撸代码吧!
我已经为你们准备了一个用开测试这个按钮的起始项目。下载这个起始项目, 解压,而后在xcode里打开。看看里面有什么吧。 学习

注意: 这个项目里的storyboard是关掉了Autolayout的。并非每一个项目都须要这样,可是在这里,咱们更偏向于使用springs和struts约束。

这是一个Tabbar 应用,里面包含了3个view controller,他们分别是为这个系列教程每次建立的控件准备的。 在此次的 PaintCode 教程里,咱们将会使用 ButtonViewController 来展现咱们的按钮。
在 Classes > Views下面有一个空文件夹。此次, 咱们在这里面建立本身的类。咱们会继承一个现有的控件,而后去改变他的绘制代码,而不是彻底的用一个空UIView来实现。
而在这个教程里,咱们继承UIButton。让咱们开始吧!

建立按钮

在 Classes 组下面, 右键 Views 组。选择 NewFile… 而后建立一个 iOSCocoa TouchObjective-C class模板,把这个类命名为 ButtonView,而后继承自 UIButton。
这个类将会使用咱们在 PaintCode里建立的绘制代码。
如今咱们作一些准备工做, 打开 ButtonView.m,删除 initWithFrame: 方法,而后反注释 drawRect:。以下所示:

[objc]  view plain copy
  1. #import "ButtonView.h"  
  2. @implementation ButtonView  
  3. - (void)drawRect:(CGRect)rect  
  4. {  
  5.     // Drawing code  
  6. }  
  7. @end   

drawRect: 这里就是咱们施展魔法的地方 – 这里咱们会把PaintCode生成的代码加上。 若是你不熟悉 drawRect:甚至不知道它是作什么的,最好先去看看咱们的 Core Graphics 系列教程吧。
回到 PaintCode 而后找到 Code View。若是没有找到, 选择 View > Code 来打开这个面板。找到代码生成配置模块:
PaintCode code settings
把平台设置为 iOS > Objective-C,系统版本设置为 iOS 5+, 默认原点为Default Origin,内存管理为 ARC。若是这是你第一次使用 PaintCode — 或者你历来没弄过这些东西 — PaintCode已经帮你作了无缺的内存管理了。
复制而且把这些代码从 PaintCode里粘贴到 drawRect:里面。这个方法应该和下图同样了:

[objc]  view plain copy
  1. - (void)drawRect:(CGRect)rect  
  2. {  
  3.     //// General Declarations  
  4.     CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();  
  5.     CGContextRef context = UIGraphicsGetCurrentContext();  
  6.    
  7.     //// Color Declarations  
  8.     UIColor* buttonColorDark = [UIColor colorWithRed0.439 green0.004 blue0 alpha: 1];  
  9.     UIColor* buttonColorLight = [UIColor colorWithRed1 green0 blue0 alpha: 1];  
  10.     UIColor* innerGlowColor = [UIColor colorWithRed1 green1 blue1 alpha0.502];  
  11.     UIColor* shadowColor2 = [UIColor colorWithRed1 green1 blue1 alpha0.51];  
  12.    
  13.     //// Gradient Declarations  
  14.     NSArray* buttonGradientColors = [NSArray arrayWithObjects:  
  15.                                      (id)buttonColorLight.CGColor,  
  16.                                      (id)buttonColorDark.CGColor, nil nil];  
  17.     CGFloat buttonGradientLocations[] = {01};  
  18.     CGGradientRef buttonGradient = CGGradientCreateWithColors(colorSpace, (__bridge CFArrayRef)buttonGradientColors, buttonGradientLocations);  
  19.    
  20.     //// Shadow Declarations  
  21.     UIColor* outerGlow = innerGlowColor;  
  22.     CGSize outerGlowOffset = CGSizeMake(0.1, -0.1);  
  23.     CGFloat outerGlowBlurRadius = 3;  
  24.     UIColor* highlight = shadowColor2;  
  25.     CGSize highlightOffset = CGSizeMake(0.12.1);  
  26.     CGFloat highlightBlurRadius = 2;  
  27.    
  28.     //// Frames  
  29.     CGRect frame = CGRectMake(0048049);  
  30.    
  31.     //// Button  
  32.     {  
  33.         //// Rounded Rectangle Drawing  
  34.         CGRect roundedRectangleRect = CGRectMake(CGRectGetMinX(frame) + 4, CGRectGetMinY(frame) + 4, CGRectGetWidth(frame) - 741);  
  35.         UIBezierPath* roundedRectanglePath = [UIBezierPath bezierPathWithRoundedRect: roundedRectangleRect cornerRadius: 6];  
  36.         CGContextSaveGState(context);  
  37.         CGContextSetShadowWithColor(context, outerGlowOffset, outerGlowBlurRadius, outerGlow.CGColor);  
  38.         CGContextBeginTransparencyLayer(context, NULL);  
  39.         [roundedRectanglePath addClip];  
  40.         CGContextDrawLinearGradient(context, buttonGradient,  
  41.                                     CGPointMake(CGRectGetMidX(roundedRectangleRect), CGRectGetMinY(roundedRectangleRect)),  
  42.                                     CGPointMake(CGRectGetMidX(roundedRectangleRect), CGRectGetMaxY(roundedRectangleRect)),  
  43.                                     0);  
  44.         CGContextEndTransparencyLayer(context);  
  45.    
  46.         ////// Rounded Rectangle Inner Shadow  
  47.         CGRect roundedRectangleBorderRect = CGRectInset([roundedRectanglePath bounds], -highlightBlurRadius, -highlightBlurRadius);  
  48.         roundedRectangleBorderRect = CGRectOffset(roundedRectangleBorderRect, -highlightOffset.width, -highlightOffset.height);  
  49.         roundedRectangleBorderRect = CGRectInset(CGRectUnion(roundedRectangleBorderRect, [roundedRectanglePath bounds]), -1, -1);  
  50.    
  51.         UIBezierPath* roundedRectangleNegativePath = [UIBezierPath bezierPathWithRect: roundedRectangleBorderRect];  
  52.         [roundedRectangleNegativePath appendPath: roundedRectanglePath];  
  53.         roundedRectangleNegativePath.usesEvenOddFillRule = YES;  
  54.    
  55.         CGContextSaveGState(context);  
  56.         {  
  57.             CGFloat xOffset = highlightOffset.width + round(roundedRectangleBorderRect.size.width);  
  58.             CGFloat yOffset = highlightOffset.height;  
  59.             CGContextSetShadowWithColor(context,  
  60.                                         CGSizeMake(xOffset + copysign(0.1, xOffset), yOffset + copysign(0.1, yOffset)),  
  61.                                         highlightBlurRadius,  
  62.                                         highlight.CGColor);  
  63.    
  64.             [roundedRectanglePath addClip];  
  65.             CGAffineTransform transform = CGAffineTransformMakeTranslation(-round(roundedRectangleBorderRect.size.width), 0);  
  66.             [roundedRectangleNegativePath applyTransform: transform];  
  67.             [[UIColor grayColor] setFill];  
  68.             [roundedRectangleNegativePath fill];  
  69.         }  
  70.         CGContextRestoreGState(context);  
  71.    
  72.         CGContextRestoreGState(context);  
  73.    
  74.         [[UIColor blackColor] setStroke];  
  75.         roundedRectanglePath.lineWidth = 2;  
  76.         [roundedRectanglePath stroke];  
  77.     }  
  78.    
  79.     //// Cleanup  
  80.     CGGradientRelease(buttonGradient);  
  81.     CGColorSpaceRelease(colorSpace);      
  82. }  

若是你们仔细的浏览了代码,会发现它是用Core Graphics来绘制的。 或多或少的方法你们可能都没见过,可是它们并不难于去理解。 而且,这也是咱们使用 PaintCode 的缘由之一;为了省掉学习 Core Graphics而且花更少的时间去在那里慢慢的调试绘制代码! :]

注意: 你们暂时不用去太担忧 drawRect: 里面代码的缩进和语法。咱们等会儿会再回来,而且作一些修改 ,包括把语法改成 moden Objective-C。

如今该来测试咱们的按钮了。
在 Project Navigator 找到咱们的storyboard 而后选中 ButtonViewController。在Object Library里拖出来一个View 而后把它的 X 和 Y坐标为 20, 35。而后, 把它的 Width 和 Height 设置为 280,41。
最后, 把它的 Autosizing 设置 修改成只能水平扩张,以下所示:
Button view autosizing
切换到Identity Inspector 而后把它的类名设置为 ButtonView。

注意:你们可能有疑问为何在storyboard里面是一个 UIView , 可是 ButtonView又继承与UIButton。 缘由很简单 UIButton 它继承于 UIView所以一个按钮任然是一个 view。

在此次 PaintCode 教程的后部分 ,咱们会让它和真正的按钮同样起做用。毕竟 —他继承了UIButton。

Subclass watch out
是时候检测咱们漂亮的新按钮了!
点击 Run 看看咱们的按钮什么样的吧:
First button test
额…按钮貌似被砍掉了一块,怎么回事儿?
如今找到ButtonView.m里的 drawRect::

[objc]  view plain copy
  1. - (void)drawRect:(CGRect)rect  
  2. {  
  3.     ...  
  4.     //// Frames  
  5.     CGRect frame = CGRectMake(0048049);  
  6.    
  7.     ...  
  8. }  

原来!!!!这个按钮的frame是定死了的。咱们想要的是一个能够动态改变大小的按钮 — 而且可以适应咱们给它设置的大小。
这个问题很简单,修改设置 frame的那行代码为以下:

[objc]  view plain copy
  1. - (void)drawRect:(CGRect)rect  
  2. {  
  3.     ...  
  4.     //// Frames  
  5.     CGRect frame = rect;  
  6.    
  7.     ...  
  8. }  

上面那段代码是把view的frame设置为绘制的frame的大小。
点击Run,让咱们再来一发!
First button test fixed
耶!按钮的绘制终于和咱们想要的同样了。旋转模拟器(或者设备) 咱们会看到按钮和咱们指望的同样保持水平位置,改变着宽。
咱们已经完成了大部分了 — 可是咱们怎让才能让它变得更动态呢?

动态的设置按钮属性

动态的控制按钮大小是挺不错的 —可是如今,咱们要作一件更神奇的事情;在 ButtonViewController 里面加一些滑动条来控制按钮的RGB值。
回到storyboard,拖3个Slider 而且把它们放在按钮下面。 在 Size Inspector里面, 把3个slider的 Autosizingwidget 设置为以下所示:
Slider Autosizing
你们还能够把按钮往下移一点,而后放一个label 写着 “Tap Me”,这样的话可让你的用户知道按钮是能够点击的。Storyboard应该以下图同样的:
Scene with sliders
找到Attributes Inspector,把slider的 Min Track Tint 的颜色设置为以下的RGB值:

  • Top slider: R:255 G:0 B:0
  • Middle slider: R:0 G:255 B:0
  • Bottom slider: R:0 G:0 B:255

咱们的slider应该和下面的差很少了:
Slider colors

注意: 有的时候slider的背景色也会随着Min Tint color 的改变而改变。这是一个xcode的bug,咱们能够直接吧slider的背景色设置为默认的。

而后找到 ButtonViewController.m,在顶部加入下面的代码:

[objc]  view plain copy
  1. #import "ButtonView.h"  
  2. @interface  ButtonViewController ()  
  3. @property (weak, nonatomic) IBOutlet UISlider *blueSlider;  
  4. @property (weak, nonatomic) IBOutlet ButtonView *buttonView;  
  5. @property (weak, nonatomic) IBOutlet UISlider *greenSlider;  
  6. @property (weak, nonatomic) IBOutlet UISlider *redSlider;  
  7. @end  

把 buttonView 链接到咱们设置的那个 UIView 上,而后把3个 UISlider 和storyboard里面各自对应的链接上。若是你们还不知道怎么链接view和outlet,能够去看看咱们的 How To Create a Simple iPhone App 系列教程。
为了能让按钮的颜色随着slider的拖动而改变, 咱们的 ButtonView 须要随着slider 去更新。
找到 ButtonView.h 而后把下面3行加入 @interface 和 @end 之间:

[objc]  view plain copy
  1. @property (assign, nonatomic) CGFloat blueColor;  
  2. @property (assign, nonatomic) CGFloat greenColor;  
  3. @property (assign, nonatomic) CGFloat redColor;  

这些是储存按钮RGB值的变量。
而后切换到 ButtonView.m ,找到 drawRect:。咱们会注意到这段 Gradient Declarations 用的是旧的NSArray代码。为了保持良好的代码风格,把 Gradient Declarations 那行替换成以下:

[objc]  view plain copy
  1. NSArray *buttonGradientColors = @[(id)buttonColorLight.CGColor, (id)buttonColorDark.CGColor];  

而后,把全部带 “Color Declarations” 注释的代码替换成以下:

[objc]  view plain copy
  1. -(void)drawRect:(CGRect)rect {  
  2.     ...  
  3.     // 1  
  4.     UIColor *buttonColorLight = [UIColor colorWithRed:self.redColor green:self.greenColor blue:self.blueColor alpha: 1];  
  5.    
  6.     // 2  
  7.     if (self.state == UIControlStateHighlighted) {  
  8.         buttonColorLight = [UIColor colorWithRed:self.redColor green:self.greenColor blue:self.blueColor alpha:0.5];  
  9.     }  
  10.    
  11.     // 3  
  12.     CGFloat buttonColorLightRGBA[4];  
  13.     [buttonColorLight getRed:&buttonColorLightRGBA[0]  
  14.                        green:&buttonColorLightRGBA[1]  
  15.                         blue:&buttonColorLightRGBA[2]  
  16.                        alpha:&buttonColorLightRGBA[3]];  
  17.    
  18.     // 4  
  19.     UIColor *buttonColorDark = [UIColor colorWithRed:(buttonColorLightRGBA[0] * 0.5)  
  20.                                                green:(buttonColorLightRGBA[1] * 0.5)  
  21.                                                 blue:(buttonColorLightRGBA[2] * 0.5)  
  22.                                                alpha:(buttonColorLightRGBA[3] * 0.5 + 0.5)];  
  23.     // 5  
  24.     UIColor *innerGlowColor = [UIColor colorWithRed:1 green:1 blue:1 alpha:0.53];  
  25.     UIColor *shadowColor2 = [UIColor colorWithRed:1 green:1 blue:1 alpha:0.51];  
  26.    
  27.     ...  
  28. }  

咱们在这里具体作了:

  1. 申明一个局部 UIColor 变量做为按钮的浅色 (记住,咱们在渐变编辑器里设置的那个),可是如今咱们使用的是来自slider的RGB值。
  2. 若是用户安下了按钮,把按钮的颜色的alpha下降50%, 这时候按钮的状态是 UIControlStateHighlighted。这能在按下按钮时提供用户一些视觉上的反馈。
  3. 把按钮的rgb值储存到一个CGFloat的数组里。
  4. 基于浅色建立按钮的深色 (记住,咱们在渐变编辑器里设置的那个) 。
  5. 基于一些固定值建立内发光和阴影。

在这里咱们最好给按钮一个初始颜色。 由于咱们用的是Storyboard,因此咱们须要重载 initWithCoder: (在ButtonView.m) 来实现:

[objc]  view plain copy
  1. -(id)initWithCoder:(NSCoder *)coder {  
  2.     if (self = [super initWithCoder:coder]) {  
  3.         self.redColor = 1.0f;  
  4.         self.greenColor = 0.0f;  
  5.         self.blueColor = 0.0f;  
  6.         self.contentMode = UIViewContentModeRedraw;  
  7.     }  
  8.    
  9.     return self;  
  10. }  

这个设置把view的内容模式设置为了 UIViewContentModeRedraw,而且让按钮初始的时候是红色的。

注意: 若是你们好奇为何重载 initWithCoder: 而不是 initWithFrame:, 这是由于initWithFrame:是用来在代码里手动生成view的, 然而 initWithCoder: 是用来初始化一个从Nib或者Storyboard里面生成的view的。

在咱们开始测试以前,还有最后一件事作。找到 ButtonViewController.m 而后吧 viewDidLoad 替换成以下:

[objc]  view plain copy
  1. -(void)viewDidLoad {  
  2.     [super viewDidLoad];  
  3.    
  4.     [self.redSlider setValue:self.buttonView.redColor];  
  5.     [self.greenSlider setValue:self.buttonView.greenColor];  
  6.     [self.blueSlider setValue:self.buttonView.blueColor];  
  7. }  

上面的代码把每一个slider的颜色设置为按钮各个RGB通道的值。
编译运行, 试试滑动这些slider,以下所示:
Testing the sliders
等下!!为何没有反应!
咱们确实链接了slider, 可是如今在 ButtonViewController 没有任何方法去响应slider值的改变。咱们须要加一些 IBAction 代码来处理这些值。

响应事件

响应按钮和slider的事件其实很简单。
ButtonViewController.m里加入以下代码:

[objc]  view plain copy
  1. -(IBAction)sliderValueChanged:(UISlider *)slider {  
  2.     if (slider == self.redSlider) {  
  3.         self.buttonView.redColor = self.redSlider.value;  
  4.     } else if (slider == self.greenSlider) {  
  5.         self.buttonView.greenColor = self.greenSlider.value;  
  6.     } else if (slider == self.blueSlider) {  
  7.         self.buttonView.blueColor = self.blueSlider.value;  
  8.     }  
  9.    
  10.     [self.buttonView setNeedsDisplay];  
  11. }  

上面的能收到一个值改变了的slider的指针。 咱们经过和属性里声明的slider比较来肯定具体修改哪一个slider的值。
咱们能够注意到,在代码的最后咱们调用了setNeedsDisplay 来让按钮可以更新到最新的颜色。
如今回到Storyboard, 依次把slider的 Value Changed event 和ButtonViewController里的 sliderValueChanged: 链接起来,以下所示:
Connecting the sliders
Build and run your project again, and try once more to move the sliders around to change the button’s color, as below:
Working sliders
叼炫酷!如今咱们的按钮,不经能任意改变大小!还能随便的改变颜色了!
如今咱们来试试按钮按下有啥反应。
额~~~ 啥都没发生! 按钮并无高亮来表示按下,也没有任何提示你的信用卡刚被划掉了99.99$. (开个玩笑! :])
咱们尚未给按钮链接事件 — 接下来咱们就开始吧!

最后的点击

回到 ButtonView.m 而后加入下面的方法:

[objc]  view plain copy
  1. -(void)setEnabled:(BOOL)enabled {  
  2.     [super setEnabled:enabled];  
  3.     [self setNeedsDisplay];  
  4. }  
  5. -(void)setHighlighted:(BOOL)value {  
  6.     [super setHighlighted:value];  
  7.     [self setNeedsDisplay];  
  8. }  
  9. -(void)setSelected:(BOOL)value {  
  10.     [super setSelected:value];  
  11.     [self setNeedsDisplay];  
  12. }  

上面的代码是让按钮在 enabled 和 disabled,selected 和 unselected,highlighted 或者 unhighlighted 的时候可以从新绘制一次。 这是为了让咱们能看到具体的改变,当咱们按下按钮时候。
接着,把下面的代码加进ButtonViewController.m:

[objc]  view plain copy
  1. -(IBAction)buttonTapped:(UIButton *)button {  
  2.     ButtonView *buttonView = (ButtonView *)button;  
  3.    
  4.     NSString *messageString = [NSString stringWithFormat:@"Red: %fnGreen: %fnBlue: %fn Alpha: %f",  
  5.                                buttonView.redColor,  
  6.                                buttonView.greenColor,  
  7.                                buttonView.blueColor,  
  8.                                buttonView.alpha];  
  9.    
  10.     UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Button Colors"  
  11.                                                         message:messageString  
  12.                                                        delegate:nil  
  13.                                               cancelButtonTitle:@"Dismiss"  
  14.                                               otherButtonTitles:nil];  
  15.     [alertView show];  
  16. }  

这个方法的做用是在按钮按下之后,弹出一个提醒框,显示当前的RGB和Alpha值。
在Storyboard里,把 Touch Up Inside 和这个方法联系在一块儿。
最后在运行一次程序,按下按钮看看结果吧! 应该出现和下面同样的画面:
Final project
太棒了! -一切都正常工做。

何去何从?

你们能够在这里下载所需的PaintCode文件,和相关的Xcode项目。
恭喜你们如今已经掌握了大部分的PaintCode功能了。它能极大的缩短设计app调试UI的时间。
这个系列教程还剩下2部分;第二部分是教你们如何去建立一个自定义进度条,第三部分是使用贝塞尔曲线绘制箭头。
如今,咱们还能够再给这个项目增长一下功能让锦上添花:

  • 本身慢慢的熟悉 PaintCode 的其余功能和特性。
  • 增长字符串,阴影,以及更多的其余特效。
  • 重写ButtonView里的 initWithFrame: ,这样能让你使用代码生成动态按钮。
  • 给 ButtonView 建立本身的初始化方法,让咱们能初始按钮的颜色参数。

但愿你们能喜欢这个 PaintCode 教程,而且但愿你们能继续关注咱们接下来的2部。接下来的加成将会愈来愈深刻,而且会有一点的难度 — 可是我知道这对你们来讲是小菜一碟。


http://www.raywenderlich.com/36341/paintcode-tutorial-dynamic-buttons

相关文章
相关标签/搜索