iOS可复用控件之滚动按钮组

本文介绍了如何在iOS中创建一个可复用的滚动按钮组,该组件基于ScrollView,详细讲解了实现原理和具体步骤,同时提供了GitHub项目链接供参考。

GitHub地址:https://github.com/runThor/HTScrollButton

效果:


控件内部有一个ScrollView,按钮都加在ScrollView上。

实现:

ScrollView类:

//  HTButtonScrollView.h

#import <UIKit/UIKit.h>

@interface HTButtonScrollView : UIScrollView

// 在ScrollView中配置按钮
- (void)configButtons:(NSArray *)buttons;

@end


//  HTButtonScrollView.m

#import "HTButtonScrollView.h"

@interface HTButtonScrollView ()

@property (nonatomic, strong) NSMutableArray *buttonArr;  // 按钮组

@end

@implementation HTButtonScrollView

- (instancetype)initWithFrame:(CGRect)frame {
    if (self = [super initWithFrame:frame]) {
        self.pagingEnabled = YES;  // 翻页效果
        self.showsHorizontalScrollIndicator = NO;  
        self.buttonArr = [[NSMutableArray alloc] init];
    }
    
    return self;
}

// 配置按钮
- (void)configButtons:(NSArray *)buttons {
    
    [self.subviews makeObjectsPerformSelector:@selector(removeFromSuperview)];
    
    [self.buttonArr removeAllObjects];
    
    if (buttons.count == 0) {
        return;
    }
    
    // 默认一页5个按钮
    NSInteger pageCount = (buttons.count - 1)/5 + 1;
    CGFloat eachWidth;
    
    if (buttons.count < 5) {
        eachWidth = self.frame.size.width/buttons.count;
        self.contentSize = CGSizeMake(self.frame.size.width, self.frame.size.height);
    } else if (buttons.count%5 == 0){
        eachWidth = self.frame.size.width/5;
        self.contentSize = CGSizeMake(self.frame.size.width * pageCount, self.frame.size.height);
    } else {
        eachWidth = self.frame.size.width/5;
        self.contentSize = CGSizeMake(self.frame.size.width * (pageCount - 1) + eachWidth * (buttons.count%5), self.frame.size.height);
    }
    
    for (int i = 0; i < buttons.count; i++) {
        CGFloat centerX = self.frame.size.width * (i/5) + i%5 * eachWidth + eachWidth/2;
        CGFloat centerY = self.frame.size.height/2;
        
        UIButton *btn = buttons[i];
        [btn setCenter:CGPointMake(centerX, centerY)];
        [self addSubview:btn];
    }
}



@end

ScrollButton类:

//  HTScrollButton.h

#import <UIKit/UIKit.h>

@interface HTScrollButton : UIView

// 配置按钮组
- (void)configButtons:(NSArray *)buttons;

@end

//  HTScrollButton.m

#import "HTScrollButton.h"
#import "HTButtonScrollView.h"

@interface HTScrollButton ()<UIScrollViewDelegate>

@property (nonatomic, strong) HTButtonScrollView *scrollView;
@property (nonatomic, strong) UIButton *leftArrowBtn;  // 左箭头
@property (nonatomic, strong) UIButton *rightArrowBtn;  // 右箭头

@end

@implementation HTScrollButton

- (instancetype)initWithFrame:(CGRect)frame {
    if (self = [super initWithFrame:frame]) {
        self.scrollView = [[HTButtonScrollView alloc] initWithFrame:CGRectMake(25, 0, self.bounds.size.width - 50, self.bounds.size.height)];
        self.scrollView.delegate = self;
        [self addSubview:self.scrollView];
        
        // 左箭头
        self.leftArrowBtn = [[UIButton alloc] initWithFrame:CGRectMake(5, self.frame.size.height/2 - 7.5, 10, 15)];
        [self.leftArrowBtn setBackgroundImage:[UIImage imageNamed:@"leftArrow"] forState:UIControlStateNormal];
        [self.leftArrowBtn addTarget:self action:@selector(leftArrowBtnClicked:) forControlEvents:UIControlEventTouchUpInside];
        [self addSubview:self.leftArrowBtn];
        self.leftArrowBtn.hidden = YES;
        
        // 右箭头
        self.rightArrowBtn = [[UIButton alloc] initWithFrame:CGRectMake(self.frame.size.width - 15, self.frame.size.height/2 - 7.5, 10, 15)];
        [self.rightArrowBtn setBackgroundImage:[UIImage imageNamed:@"rightArrow"] forState:UIControlStateNormal];
        [self.rightArrowBtn addTarget:self action:@selector(rightArrowBtnClicked:) forControlEvents:UIControlEventTouchUpInside];
        [self addSubview:self.rightArrowBtn];
        self.rightArrowBtn.hidden = YES;
    }
    
    return self;
}


// 配置按钮组
- (void)configButtons:(NSArray *)buttons {
    if (buttons.count == 0) {
        return;
    } else if (buttons.count > 5) {
        // 如按钮个数超过一页,则显示右箭头
        self.rightArrowBtn.hidden = NO;
    }
    
    // 将按钮组配置到ScrollView上
    [self.scrollView configButtons:buttons];
}

// 点击左箭头向左翻页
- (void)leftArrowBtnClicked:(UIButton *)btn {
    if (self.scrollView.contentOffset.x < self.scrollView.frame.size.width) {
        [self.scrollView setContentOffset:CGPointMake(0, 0) animated:YES];
    } else {
        [self.scrollView setContentOffset:CGPointMake(self.scrollView.contentOffset.x - self.scrollView.frame.size.width, 0) animated:YES];
    }
}

// 点击右箭头向右翻页
- (void)rightArrowBtnClicked:(UIButton *)btn {
    if ((self.scrollView.contentOffset.x + self.scrollView.frame.size.width) > (self.scrollView.contentSize.width - self.scrollView.frame.size.width)) {
        [self.scrollView setContentOffset:CGPointMake(self.scrollView.contentSize.width - self.scrollView.frame.size.width, 0) animated:YES];
    } else {
        [self.scrollView setContentOffset:CGPointMake(self.scrollView.contentOffset.x + self.scrollView.frame.size.width, 0) animated:YES];
    }
}


#pragma mark - UIScrollViewDelegate

// 点击箭头滚动完成后调用
- (void)scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView {
    // 如滚动到最左侧,隐藏左箭头
    if (scrollView.contentOffset.x > 0) {
        self.leftArrowBtn.hidden = NO;
    } else {
        self.leftArrowBtn.hidden = YES;
    }
    
    // 如滚动到最右侧,隐藏右箭头
    if ((scrollView.contentSize.width - scrollView.frame.size.width) > scrollView.contentOffset.x) {
        self.rightArrowBtn.hidden = NO;
    } else {
        self.rightArrowBtn.hidden = YES;
    }
}

// 拖拽滚动完成后调用
- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView {
    // 如滚动到最左侧,隐藏左箭头
    if (scrollView.contentOffset.x > 0) {
        self.leftArrowBtn.hidden = NO;
    } else {
        self.leftArrowBtn.hidden = YES;
    }
    
    // 如滚动到最右侧,隐藏右箭头
    if ((scrollView.contentSize.width - scrollView.frame.size.width) > scrollView.contentOffset.x) {
        self.rightArrowBtn.hidden = NO;
    } else {
        self.rightArrowBtn.hidden = YES;
    }
}


@end

使用:

//  ViewController.m

#import "ViewController.h"
#import "HTScrollButton.h"

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    
    HTScrollButton *HTView = [[HTScrollButton alloc] initWithFrame:CGRectMake(0, 0, [UIScreen mainScreen].bounds.size.width, 50)];
    [HTView setCenter:CGPointMake([UIScreen mainScreen].bounds.size.width/2, [UIScreen mainScreen].bounds.size.height/2)];
    HTView.backgroundColor = [UIColor grayColor];
    [self.view addSubview:HTView];
    
    NSMutableArray *buttonArr = [[NSMutableArray alloc] init];
    // 模拟按钮组
    for (int i = 0; i < 13; i++) {
        UIButton *btn = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, 40, 40)];
        [btn setTitle:[NSString stringWithFormat:@"%d", i + 1] forState:UIControlStateNormal];
        [btn setBackgroundColor:[UIColor colorWithRed:1/255.0 green:174/255.0 blue:202/255.0 alpha:1]];
        [buttonArr addObject:btn];
    }
    
    // 传入按钮组
    [HTView configButtons:buttonArr];
}


- (void)didReceiveMemoryWarning {
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}


@end

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值