美文网首页iOS开发攻城狮的集散地
iOS 金融类游标尺选择数值 ZBRulerView

iOS 金融类游标尺选择数值 ZBRulerView

作者: biyuhuaping | 来源:发表于2018-06-28 14:47 被阅读12次

    最近产品看别的app有游标尺选金额,要我们也加上,好吧,开干!先看看效果:


    游标尺

    首先我要可以设置最大值、最小值、和默认指向的值:

    @property (nonatomic, assign) double minValue;      // 最小值,默认为0
    @property (nonatomic, assign) double maxValue;      // 最大值,必需设置
    @property (nonatomic, assign) double defaultValue;  // 默认值,默认为0
    

    初始化试图:

    - (instancetype)initWithFrame:(CGRect)frame {
        self = [super initWithFrame:frame];
        if (self) {
            _scrollWidth = kScreenWidth;
            self.backgroundColor = [UIColor whiteColor];
            [self addSubview:self.scrollView];
            [self addSubview:self.textField];
            [self addSubview:self.markLine];
            [self addSubview:self.bottomLine];
            _minValue = 0;     //设置默认初始值
        }
        return self;
    }
    

    难点是根据数值画刻度:

    - (void)createIndicator{
        for (NSUInteger i = self.minValue, j = 0; i <= self.maxValue; i+=kMinScale, j++) {
            _scrollWidth += kPadding;
            [self drawSegmentWithValue:i idx:j];
        }
        self.scrollView.contentSize = CGSizeMake(_scrollWidth-kPadding, CGRectGetHeight(self.frame));
    }
    
    - (void)drawSegmentWithValue:(NSUInteger)value idx:(NSUInteger)idx {
        UIBezierPath *path = [UIBezierPath bezierPath];
        CGFloat x = kScreenWidth*0.5 + kPadding*idx;
        [path moveToPoint:CGPointMake(x, CGRectGetHeight(self.frame)-5)];
        
        if (value % (kMinScale*10) == 0 || value == _minValue) { //每10个刻度,do something
            [path addLineToPoint:CGPointMake(x, CGRectGetHeight(self.frame)-10-5-10)];
            UILabel *numLabel = [[UILabel alloc] initWithFrame:CGRectMake(x-50*0.5, CGRectGetHeight(self.frame)-20-10-5-5, 50, 10)];
            numLabel.font = [UIFont systemFontOfSize:12];
            numLabel.textAlignment = NSTextAlignmentCenter;
            numLabel.textColor = [UIColor redColor];
            numLabel.text = [NSString stringWithFormat:@"%ld", value];
            [self.scrollView addSubview:numLabel];
        } else if (value % (kMinScale*2) != 0) {   //每2个刻度,do something
            [path addLineToPoint:CGPointMake(x, CGRectGetHeight(self.frame)-10)];
        } else{
            [path addLineToPoint:CGPointMake(x, CGRectGetHeight(self.frame)-10-5)];
        }
        
        CAShapeLayer *line = [[CAShapeLayer alloc] init];
        line.lineWidth = 1;
        line.strokeColor = [UIColor orangeColor].CGColor;
        line.path = path.CGPath;
        
        [self.scrollView.layer addSublayer:line];
    }
    
    

    通过执行UIScrollViewDelegate实时显示滚到的数值

    #pragma mark - UIScrollViewDelegate
    - (void)scrollViewDidScroll:(UIScrollView *)scrollView {
        CGFloat num = scrollView.contentOffset.x;
        double value = (num / kPadding) * kMinScale + self.minValue;
        if (value < self.minValue) {
            value = self.minValue;
        }else if (value > self.maxValue) {
            value = self.maxValue;
        }
        
        self.textField.text = [NSString stringWithFormat:@"%.f", value];
    }
    
    - (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView{
        CGFloat num = scrollView.contentOffset.x;
        NSInteger value = (num / kPadding) * kMinScale + self.minValue;
        value =  value - value % kMinScale;
        [self.scrollView setContentOffset:CGPointMake((value-_minValue)/kMinScale*kPadding, 0) animated:YES];
        self.textField.text = [NSString stringWithFormat:@"%ld", value];
    }
    
    - (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate{
        if(!decelerate){
            //OK,真正停止了,do something
            CGFloat num = scrollView.contentOffset.x;
            NSInteger value = (num / kPadding) * kMinScale + self.minValue;
            value =  value - value % kMinScale;
            [self.scrollView setContentOffset:CGPointMake((value-_minValue)/kMinScale*kPadding, 0) animated:YES];
            self.textField.text = [NSString stringWithFormat:@"%ld", value];
        }
    }
    

    通过实现UITextFieldDelegate代理方法实现数值修改,让游标尺滚动到对应的数值:

    #pragma mark - UITextFieldDelegate
    - (BOOL)textFieldShouldReturn:(UITextField *)textField {
        [self endEditing:YES];
        return YES;
    }
    
    - (void)textFieldDidEndEditing:(UITextField *)textField {
        if (textField.text.doubleValue > self.maxValue) {
            textField.text = [NSString stringWithFormat:@"%.f",self.maxValue];
        }
        
        [self.scrollView setContentOffset:CGPointMake((textField.text.doubleValue-_minValue)/kMinScale*kPadding, 0) animated:YES];
        self.textField.text = textField.text;
    }
    
    // 根据输入的数字变化
    - (void)textDidChanged:(NSNotification *)info {
        UITextField *textField = info.object;
        NSString *text = textField.text;
        if (textField.isEditing) {
            self.scrollView.contentOffset = CGPointMake((text.doubleValue-_minValue)/kMinScale*kPadding, 0);
            self.textField.text = text;
        }
    }
    

    细节处理:游标尺自动取整
    一个简洁的游标尺,就实现了。这里将Demo:ZBRulerView献上,朋友请多指教。

    相关文章

      网友评论

        本文标题:iOS 金融类游标尺选择数值 ZBRulerView

        本文链接:https://www.haomeiwen.com/subject/vpvgyftx.html