2018正版葡京赌侠诗干货!老司机工作面临因故到的自定义控件,总有一个契合你的(一)

今天总结了转平常工作遭到呢那些奇葩的UI设计从定义的控件,下面一个个享给大家。


一样、第一只凡是tableView的透明度渐变效果

1、效果:

广大app用到了这种效果,比如歌词显示、直播中聊天记录等。
约莫效果如下:

2018正版葡京赌侠诗 1

WZBGradualTableView

2018正版葡京赌侠诗 2

背景图片截取自新浪直播,侵立删

2、使用方式:
/*
 * frame:tableView的frame
 * direction:透明渐进的方向
 * gradualValue:透明范围值,如果只有一个方向,此值传一个NSNumber、NSString即可,值的范围0—1。如果是两个方向,则需要传一个数组,数组里边传两个NSNumber或者NSString
 ***/
+ (instancetype)gradualTableViewWithFrame:(CGRect)frame direction:(WZBTableViewGradualDirection)direction gradualValue:(id)gradualValue;

参数值说明一下,direction代表方向,是一个号移枚举,如果想让tableView顶部渐变,则此值为WZBTableViewGradualDirectionTop,如果也底渐变,则此值为WZBTableViewGradualDirectionBottom,如果前后都要渐变,则用WZBTableViewGradualDirectionTop
|
WZBTableViewGradualDirectionBottom。gradualValue代表渐变范围值,值的限也0-1,如果想吃顶部20%渐变,此值为@(0.2)。如果想顶部底部都生20%渐变,此值为@[@(0.2),
@(0.2)]。

如下:

WZBGradualTableView *tableView = [WZBGradualTableView gradualTableViewWithFrame:self.view.bounds direction:(WZBTableViewGradualDirectionTop | WZBTableViewGradualDirectionBottom)  gradualValue:@[@(.3), @0.3]];

虽然显示效果啊:

2018正版葡京赌侠诗 3

WZBGradualTableView

假设这样描绘

[WZBGradualTableView gradualTableViewWithFrame:CGRectMake(0, self.view.frame.size.height - 180, self.view.frame.size.width, 140) direction:WZBTableViewGradualDirectionTop  gradualValue:@.3f]

效果如下:

2018正版葡京赌侠诗 4

背景图片截取自新浪直播,侵立删

3、实现大致原理:

这种渐变效果主要用到tableView的mask属性,我们先是使开创一个CAGradientLayer,此类的用网上介绍来诸多,在这里不再赘言,不了解私聊我,或者参加我之技术群。

上代码:

if (!self.layer.mask) {
      CAGradientLayer *maskLayer = [CAGradientLayer layer];
      maskLayer.locations = @[@0.0, topValue, @(1-bottomValue.doubleValue), @1.0f];
      maskLayer.bounds = CGRectMake(0, 0, self.frame.size.width, self.frame.size.height);
      maskLayer.anchorPoint = CGPointZero;
      self.layer.mask = maskLayer;
 }
[self addObserver:self forKeyPath:@"contentOffset" options:NSKeyValueObservingOptionNew context:nil];

鉴于tableView可以滑动,滑动的当儿即便需要实时的作出变动,因此我这边用KVO监听“contentOffset”属性,每当contentOffset发生变更,证明用户滑动了tableView,这时候需要调用的代码为:

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSKeyValueChangeKey,id> *)change context:(void *)context {
    if ([keyPath isEqualToString:@"contentOffset"]) {
        [self change];
    }
}
- (void)change {
    UIScrollView *scrollView = (UIScrollView *)self;
    CGColorRef outerColor = [UIColor colorWithWhite:1.0 alpha:0.0].CGColor;
    CGColorRef innerColor = [UIColor colorWithWhite:1.0 alpha:1.0].CGColor;
    NSArray *colors;

    if (scrollView.contentOffset.y + scrollView.contentInset.top <= 0) {
        //Top of scrollView
        colors = @[(__bridge id) innerColor, (__bridge id) innerColor,
                   (__bridge id) innerColor, (__bridge id) outerColor];
    } else if (scrollView.contentOffset.y + scrollView.frame.size.height
               >= scrollView.contentSize.height) {
        //Bottom of tableView
        colors = @[(__bridge id) outerColor, (__bridge id) innerColor,
                   (__bridge id) innerColor, (__bridge id) innerColor];
    } else {
        //Middle
        colors = @[(__bridge id) outerColor, (__bridge id) innerColor,
                   (__bridge id) innerColor, (__bridge id) outerColor];
    }
    ((CAGradientLayer *) scrollView.layer.mask).colors = colors;

    [CATransaction begin];
    [CATransaction setDisableActions:YES];
    scrollView.layer.mask.position = CGPointMake(0, scrollView.contentOffset.y);
    [CATransaction commit];
}

转移忘了移除观察者:

- (void)dealloc {
    [self removeObserver:self forKeyPath:@"contentOffset"];
}
4、GitHub源码地址:WZBGradualTableView

老二、自定义的开关控件

1、效果:

2018正版葡京赌侠诗 5

WZBSwitch

2、使用方法:

拿WZBSwitch.h和WZBSwitch.m拖入工程

每当急需用的地方调用

    /** 初始化方法
     *  switchValueChange: 开关状态改变回调block
     */
    WZBSwitch *switchView = [[WZBSwitch alloc] initWithFrame:CGRectMake(100, 100, 50, 25) switchValueChanged:^(WZBSwitch *swith, BOOL on)     {
        // do someing
    }];
    [self.view addSubview:switchView];

对于开关状态的监听或者您还足以经过代办:

   WZBSwitch *switchView = [[WZBSwitch alloc] initWithFrame:CGRectMake(100, 100, 50, 25)];
   [self.view addSubview:switchView];
   // delegate
   switchView.delegate = self;

接下来实现代理方即可

   #pragma mark - WZBSwitchDelegate
   - (void)switchValueChange:(WZBSwitch *)swith on:(BOOL)on {
        // do someing
   }

只要您想打定义开关颜色,代码如下:

//设置所有颜色
    [switchView setUpAllColors:^NSDictionary *(UIColor *__autoreleasing *onTintColor, UIColor *__autoreleasing *onBackgroundColor,                UIColor *__autoreleasing *offTintColor, UIColor *__autoreleasing *offBackgroundColor, UIColor *__autoreleasing *tintColor) {
        // 可以通过这种方法设置需要设置的颜色
        *onTintColor = [UIColor redColor];
        *onBackgroundColor = [UIColor blueColor];
        *offTintColor = [UIColor greenColor];
        *offBackgroundColor = [UIColor grayColor];
        *tintColor = [UIColor blackColor];
        return nil;
    }];

要这样

  [switchView setUpAllColors:^NSDictionary *(UIColor *__autoreleasing *onTintColor, UIColor *__autoreleasing *onBackgroundColor, UIColor    *__autoreleasing *offTintColor, UIColor *__autoreleasing *offBackgroundColor, UIColor *__autoreleasing *tintColor) {
        // 也可以通过这种方法设置需要设置的颜色
        return @{OnTintColor : WZBColor(234, 67, 53), OnBackgroundColor : WZBColor(244, 161, 154), OffTintColor : WZBColor(255, 255,              255), OffBackgroundColor : WZBColor(214, 214, 214), TintColor : [UIColor colorWithRed:0.8252 green:0.8252 blue:0.8252                   alpha:1.0]};
    }];
3、实现大致原理:

其一控件由少有的组成,顶部View和底View

@property (nonatomic, strong) UIView *topView;
@property (nonatomic, strong) UIView *bottomView;

/** 一个方法设置所有颜色 && block回调
 *  switchValueChange: 开关状态改变回调block
 */
- (void)setUpAllColors:(NSDictionary *(^)(UIColor **onTintColor,UIColor **onBackgroundColor, UIColor **offTintColor, UIColor **offBackgroundColor, UIColor **tintColor))allColorBlock switchValueChanged:(SwitchValueChangeBlock)switchValueChange;;

斯主意有有限只block参数,第一个好装您所用安装的有所颜色值,第二单block是当开关状态来变动之下回调

/** 设置开关状态, animated : 是否有动画 */
- (void)setOn:(BOOL)newOn animated:(BOOL)animated;

本条方式用于安装开关状态

@protocol WZBSwitchDelegate <NSObject>
@optional
- (void)switchValueChange:(WZBSwitch *)swith on:(BOOL)on;
@end

假如您不爱下block,我还提供了代理方监听开关状态的转移

- (void)setOn:(BOOL)newOn animated:(BOOL)animated {
//    if (_on == newOn) return;
    __block CGRect frame = self.topView.frame;
    CGFloat newX = newOn ? self.frame.size.width - self.topView.frame.size.width : 0;
    [UIView animateWithDuration:animated ? 0.2 : 0.0 animations:^{
        frame.origin.x = newX;
        self.topView.frame = frame;
        [self setSwitchColorWithStatus:newOn];
    }                completion:^(BOOL finished) {
        if (finished) {
            // delegate
            if ([self.delegate respondsToSelector:@selector(switchValueChange:on:)]) {
                [self.delegate switchValueChange:self on:newOn];
            }
            // block
            if (self.switchValueChange) {
                self.switchValueChange(self, newOn);
            }
        }
    }];
    _on = newOn;
}

当外界调用方法改变开关状态时,动画/非动画,改变上层View的frame即可

4、GitHub源码地址:WZBSwitch

老三、一个仿网易的Segment

1、效果:

2018正版葡京赌侠诗 6

WZBSegmentedControl

2、使用方法:

将WZBSegmentedControl.h和WZBSegmentedControl.m拖入工程

当待采用的地方调用

  /** 初始化方法
   *  titles: 所有标题
   *  titleClick: 点击标题的block回调
   */
  WZBSegmentedControl *segmentedControl = [WZBSegmentedControl segmentWithFrame:(CGRect){0, 0, 170, 25} titles:[self titles] titleClick:^(NSInteger index) {
        // do soming
  }];
  self.navigationItem.titleView = segmentedControl;
3、实现大致原理:

其一控件还免是甚完美,目前就供一个初始化方法:

/* 初始化方法
 * frame:控件frame
 * titleClick:点击title的时候block回调
 **/
+ (instancetype)segmentWithFrame:(CGRect)frame titles:(NSArray *)titles titleClick:(void(^)(NSInteger index))titleClick;

- (void)setContentOffset:(CGPoint)contentOffset {
    CGRect frame = self.backgroundView.frame;
    frame.origin.x = contentOffset.x;
    self.backgroundView.frame = frame;

    // 找出要操作的两个button设置颜色(目前先这样写,后续改进)
    for (UIView *v in self.subviews) {
        if ([v isKindOfClass:[UIButton class]]) {
            UIButton *button = (UIButton *)v;
            CGFloat overLapWidth = CGRectIntersection(button.frame, self.backgroundView.frame).size.width;
            NSInteger gb = 255 - overLapWidth * (255 / (self.frame.size.width / self.titles.count));
            [button setTitleColor:WZBColor(255, gb, gb) forState:UIControlStateNormal];
        }
    }
}

基本措施:改变底部白色滑块的位置,但是要是留意观察,有只注意点是,在滑行的时节title的仿吗会趁着渐变,目前预试用这个办法临时解决,后续会提供方设置文字颜色、选中文字颜色、背景颜色和滑块颜色等。

4、GitHub源码地址:WZBSegmentedControl

———————————-难道我是分割线—————————–

11月13日更新:

本篇文章最后一个情由当下最匆忙写的非完全,今天补给一下。
加了几乎只方式设置中控件颜色

/* 设置文字颜色
 * normalColor:未选中的按钮文字颜色
 * selectColor:选中的按钮文字颜色
 */
- (void)setNormalColor:(UIColor *)normalColor selectColor:(UIColor *)selectColor;
/* 设置部分颜色
 * normalColor:未选中的按钮文字颜色
 * selectColor:选中的按钮文字颜色
 * edgingColor:边框颜色
 */
- (void)setNormalColor:(UIColor *)normalColor selectColor:(UIColor *)selectColor edgingColor:(UIColor *)edgingColor;
/* 设置所有颜色
 * normalColor:未选中的按钮文字颜色
 * selectColor:选中的按钮文字颜色
 * sliderColor:滑块背景颜色
 * edgingColor:边框颜色
 */
- (void)setNormalColor:(UIColor *)normalColor selectColor:(UIColor *)selectColor sliderColor:(UIColor *)sliderColor edgingColor:(UIColor *)edgingColor;
/* 设置所有属性
 * normalColor:未选中的按钮文字颜色
 * selectColor:选中的按钮文字颜色
 * sliderColor:滑块背景颜色
 * edgingColor:边框颜色
 * edgingWidth:边框宽度
 */
- (void)setNormalColor:(UIColor *)normalColor selectColor:(UIColor *)selectColor sliderColor:(UIColor *)sliderColor edgingColor:(UIColor *)edgingColor edgingWidth:(CGFloat)edgingWidth;

产生矣这些主意你便可以开心的所以层出不穷的颜色了

技术交流群:413050745

除去还当.h放出了这些性

// 所有title
@property (nonatomic, strong, readonly) NSArray *titles;
// 底部的滑块
@property (nonatomic, strong, readonly) UIView *backgroundView;
// 辅助属性,当前选中的Button
@property (nonatomic, strong, readonly) UIButton *selectButton;
// 为选中的button颜色
@property (nonatomic, strong) UIColor *normalColor;
// 选中的button颜色
@property (nonatomic, strong) UIColor *selectColor;
// 滑块颜色
@property (nonatomic, strong) UIColor *sliderColor;
// 边框颜色
@property (nonatomic, strong) UIColor *edgingColor;
// 边框颜色
@property (nonatomic, assign) CGFloat edgingWidth;

以便使用者可以独自设置有颜色

// 点击title的block回调
@property (nonatomic, copy) void(^tClick)(NSInteger index);
// 点击title的block回调,selectButton:选中的button
@property (nonatomic, copy) void(^titleClick)(NSInteger index, UIButton *selectButton);

再有这半个block,一个block只出入选下标参数,另外一个产生入选下标和当选的button两独参数

哼吧!我肯定很多总人口爱不释手用代理要不是block,为什么未提供摄方为?OK,Here!

@protocol WZBSegmentedControlDelegate <NSObject>
@optional
// segmented点击的时候调用,selectIndex:选中的index
- (void)segmentedValueDidChange:(WZBSegmentedControl *)segment selectIndex:(NSInteger)selectIndex;
// segmented点击的时候调用,selectIndex:选中的index,fromeIndex:从哪个index点过来的
- (void)segmentedValueDidChange:(WZBSegmentedControl *)segment selectIndex:(NSInteger)selectIndex fromeIndex:(NSInteger)fromeIndex;
// segmented点击的时候调用,selectIndex:选中的index,fromeIndex:从哪个index点过来的,selectButton:选中的button
- (void)segmentedValueDidChange:(WZBSegmentedControl *)segment selectIndex:(NSInteger)selectIndex fromeIndex:(NSInteger)fromeIndex selectButton:(UIButton *)selectButton;
// segmented点击的时候调用,selectIndex:选中的index,fromeIndex:从哪个index点过来的,selectButton:选中的button,allButtons:所有的button
- (void)segmentedValueDidChange:(WZBSegmentedControl *)segment selectIndex:(NSInteger)selectIndex fromeIndex:(NSInteger)fromeIndex selectButton:(UIButton *)selectButton allButtons:(NSArray *)allButtons;
@end

诠释很清楚

简单易行吃大家讲下拖动的时光颜色渐变的实现,直接上代码

// 根据颜色拿到RGB数值
void getRGBValue(CGFloat colorArr[3], UIColor *color) {
    unsigned char data[4];
    // 宽,高,内存中像素的每个组件的位数(RGB应该为32),bitmap的每一行在内存所占的比特数
    size_t width = 1, height = 1, bitsPerComponent = 8, bytesPerRow = 4;
    // bitmap上下文使用的颜色空间
    CGColorSpaceRef space = CGColorSpaceCreateDeviceRGB();
    // 指定bitmap是否包含alpha通道
    uint32_t bitmapInfo = 1;
    // 创建一个位图上下文。当你向上下文中绘制信息时,Quartz把你要绘制的信息作为位图数据绘制到指定的内存块。一个新的位图上下文的像素格式由三个参数决定:每个组件的位数,颜色空间,alpha选项。alpha值决定了绘制像素的透明性
    CGContextRef context = CGBitmapContextCreate(&data, width, height, bitsPerComponent, bytesPerRow, space, bitmapInfo);
    // 设置当前上下文中填充颜色
    CGContextSetFillColorWithColor(context, [color CGColor]);
    // 在此区域内填入当前填充颜色
    CGContextFillRect(context, CGRectMake(0, 0, 1, 1));
    CGContextRelease(context);
    CGColorSpaceRelease(space);
    for (NSInteger i = 0; i < 3; i++) {
        colorArr[i] = data[i];
    }
}

即是描摹的一个c语言函数,每句基本还发生注释,说白了不畏是把RGB颜色拆分开,R是稍微,G是稍稍,B是有点,然后放数组里。

// 找出要操作的两个button设置颜色
    NSMutableArray *buttonArr = [NSMutableArray array];
    for (UIButton *button in self.allButtons) {
        CGFloat overLapWidth = CGRectIntersection(button.frame, self.backgroundView.frame).size.width;
        if (overLapWidth > 0) {
            [buttonArr addObject:button];
        }
    }

    // 切换的时候
    if (buttonArr.count > 1) {
        UIButton *leftButton = buttonArr.firstObject;
        UIButton *rightButton = buttonArr.lastObject;
        // 设置要渐变的两个button颜色
        [rightButton setTitleColor:WZBColor([self getRGBValueWithIndex:0 button:rightButton], [self getRGBValueWithIndex:1 button:rightButton], [self getRGBValueWithIndex:2 button:rightButton]) forState:UIControlStateNormal];
        [leftButton setTitleColor:WZBColor([self getRGBValueWithIndex:0 button:leftButton], [self getRGBValueWithIndex:1 button:leftButton], [self getRGBValueWithIndex:2 button:leftButton]) forState:UIControlStateNormal];
    }

先行找到两独需要改颜色的button,按照button和脚滑块交叉区域之大幅度比例,切换每个R、G、B的价值,具体大家好下载风行的源码

产生未掌握或者其他疑问的地方还可于凡评论,或者随时沟通我,您还足以为此QQ扫描底部的第二维码加入我们的技术交流群,我以那边当正在你!

怀念看还多,请点击:干货!老车手工作备受因故到之自定义控件,总有一个可你的(二)

哪,这些你学会怎么用了邪?

吁不要吝惜,随手点个爱或关注一下咔嚓!您的支撑是自无比充分之动力!
是系列文章频频创新,您得关心自己以便就查阅自己之风靡篇章或你还可入我们的洋洋,大家庭期待你的投入!

2018正版葡京赌侠诗 7

咱俩2018正版葡京赌侠诗的社区

发表评论

电子邮件地址不会被公开。 必填项已用*标注