美文网首页
iOS-带图片的跑马灯,可自定义view

iOS-带图片的跑马灯,可自定义view

作者: 加拉隆的深渊之核 | 来源:发表于2019-10-30 18:05 被阅读0次

    网上有很多跑马灯的demo,但是都是没有带图片的,所以只能自己写一个了

    我的思路就是直接用scrollView,上面放view,让他一直滚
    (可以把scrollView换成tableView的)

    主要用到了setContentOffset这个方法

    但是使用

    
    [self.scrollView setContentOffset:CGPointMake(0,0) animated:YES];
    
    

    返回到最初时却出现了一个bug,就是视图往回滚了

    所以我就想要不多写一个视图,让他代替CGPointMake(0,0) 的动画,到时关掉动画效果就行了,说干就干

    
    #import "HorseRaceLampView.h"
    
    #import "UIView+Extionsiton.h"
    
    #import "HorseRaceLampCell.h"
    
    @interface HorseRaceLampView ()<UIScrollViewDelegate>
    
    /**
    
     定时器
    
     */
    
    @property (nonatomic, strong) NSTimer *timer;
    
    /**
    
     滚动视图
    
     */
    
    @property (nonatomic, strong) UIScrollView *scrollView;
    
    /**
    
     记录已经加载的视图
    
     */
    
    @property (nonatomic, strong) NSMutableArray *viewList;
    
    /**
    
     当前滑动第几个界面 1开始
    
     */
    
    @property (nonatomic, assign) NSInteger currentIndex;
    
    /**
    
     处理的数组,因为要避免回退动画,就是最后一个回到第一个
    
     */
    
    @property (nonatomic, strong) NSMutableArray *tempArr;
    
    @end
    
    @implementationHorseRaceLampView
    
    -(instancetype)initWithFrame:(CGRect)frame{
    
    
    
        if(self= [superinitWithFrame:frame]) {
    
            [selfinitialize];
    
            [selfcreateUI];
    
        }
    
        return self;
    
    }
    
    #pragma mark - 生命周期
    
    -(void)dealloc{
    
        [self.timer invalidate];
    
        self.timer=nil;
    
    }
    
    #pragma mark - 初始化
    
    -(void)initialize{
    
        self.currentIndex = 1;
    
    }
    
    #pragma mark - 创建UI
    
    -(void)createUI{
    
        self.scrollView = [[UIScrollView alloc] initWithFrame:self.bounds];
    
        self.scrollView.backgroundColor = UIColor.grayColor;
    
        self.scrollView.scrollEnabled = NO;
    
        self.scrollView.showsVerticalScrollIndicator = NO;
    
        self.scrollView.showsHorizontalScrollIndicator = NO;
    
        self.scrollView.delegate = self;
    
        [self addSubview:self.scrollView];
    
    }
    
    #pragma mark - 私用方法
    
    #pragma mark - 公共方法
    
    - (void)startAnimation {
    
        if (!self.timer.isValid) {
    
            [self.timerfire];
    
        }
    
    }
    
    -(void) stopAnimation{  //结束动画
    
        if (self.timer.isValid) {
    
            [self.timer invalidate];
    
            self.timer=nil;
    
        }
    
    }
    
    #pragma mark - 通知方法
    
    #pragma mark - 监听代理
    
    -(void)refreshProgress{
    
        CGFloat y = self.currentIndex * self.scrollView.height;
    
        self.currentIndex++;
    
        [self.scrollView setContentOffset:CGPointMake(0,y) animated:YES];
    
    }
    
    #pragma mark - 点击事件
    
    #pragma mark - 代理协议
    
    // 当滚动视图动画完成后,调用该方法,如果没有动画,那么该方法将不被调用
    
    - (void)scrollViewDidEndScrollingAnimation:(UIScrollView*)scrollView{
    
        if (self.currentIndex == self.tempArr.count) {
    
            self.currentIndex=1;
    
            [self.scrollView setContentOffset:CGPointMake(0,0) animated:NO];
    
        }
    
    }
    
    #pragma mark - 网络请求
    
    #pragma mark - 懒加载
    
    - (NSMutableArray*)viewList{
    
        if(!_viewList) {
    
            _viewList = [[NSMutableArray alloc] init];
    
        }
    
        return _viewList;
    
    }
    
    -(NSTimer*)timer{
    
        if(!_timer) {
    
            _timer = [NSTimer timerWithTimeInterval: 1.0f target:self selector:@selector(refreshProgress) userInfo:nil repeats:YES];
    
            [[NSRunLoop currentRunLoop] addTimer:_timer forMode:NSRunLoopCommonModes];
    
        }
    
        return _timer;
    
    }
    
    -(NSMutableArray *)tempArr{
    
        if(!_tempArr) {
    
            _tempArr= [[NSMutableArrayalloc]init];
    
        }
    
        return _tempArr;
    
    }
    
    #pragma mark - getset方法
    
    -(void)setModels:(NSArray*)models{
    
        _models= models;
    
    
    
        //移除动画
    
        [self.scrollView.layer removeAllAnimations];
    
    
    
        //先移除之前的item
    
            for(UIView*vinself.scrollView.subviews) {
    
                if([visKindOfClass:[HorseRaceLampCellclass]]) {
    
                    [vremoveFromSuperview];
    
                }
    
            }
    
            [self.viewList removeAllObjects];
    
    
    
    
    
        //    为了解决闪一下,所以要加多加一个view用来替代动画
    
        self.tempArr = [NSMutableArray arrayWithArray:models];
    
        // 数据要加第一个
    
        [self.tempArr addObject:models.firstObject];
    
    
    
        for(inti =0; i
    
            NSDictionary*dic =self.tempArr[i];
    
    
    
            HorseRaceLampCell *nb = [HorseRaceLampCell initView];
    
            nb.backgroundColor = [UIColor purpleColor];
    
            nb.frame = CGRectMake(0, (i*self.scrollView.height), self.scrollView.width, self.scrollView.height);
    
            nb.tag= i;
    
            nb.titleLB.text= dic[@"title"];
    
            nb.iconImgV.image= [UIImageimageNamed:dic[@"icon"]];
    
    
    
            [self.scrollView addSubview:nb];
    
            [self.viewList addObject:nb];
    
        }
    
    
    
        self.scrollView.contentSize = CGSizeMake(0, self.tempArr.count * self.scrollView.height);
    
        self.clipsToBounds = YES;
    
    
    
    }
    
    
    
    HorseRaceLampView *marqueeView = [[HorseRaceLampView alloc] initWithFrame:CGRectMake(0,100,self.view.bounds.size.width,44)];
    
        [self.view addSubview:marqueeView];
    
        [marqueeView setModels:@[@{@"title":@"你好吗",@"icon":@"login-password"},@{@"title":@"我很好",@"icon":@"login-phone"}]];
    
        //开始动画
    
        [marqueeView startAnimation];
    
    

    当然也有很多可以优化的地方
    以上就是全部代码了,HorseRaceLampCell这个自定义替换成需求样式就好了

    代码是在http://www.cnblogs.com/qqcc1388/p/8664280.html的基础上改的
    转载:http://www.cnblogs.com/qqcc1388/p/8664280.html

    在分享一个swift版的,也是自定义视图的
    用collectionView做的 复制一下代码就可以直接用

    import UIKit
    
    enum Roll {
        case ver    /// 垂直
        case hor    /// 水平
    }
    
    class HorseRunningLightsView: UIView {
    
        deinit {
            if timer.isValid {
                timer.invalidate()
            }
        }
        
        /// 定时器
        private lazy var timer : Timer = {
            let timer = Timer(timeInterval: 2.0, target: self, selector: #selector(startToMove), userInfo: nil, repeats: true)
            RunLoop.current.add(timer, forMode: .common)
            return timer
        }()
        
        
        /// 创建布局对象
        let flowLayout = UICollectionViewFlowLayout()
        
        /// collectionView
        private lazy var collectionView : UICollectionView = {
            let collectionView = UICollectionView(frame: self.bounds, collectionViewLayout: flowLayout)
            collectionView.delegate = self
            collectionView.dataSource = self
            collectionView.register(UICollectionViewCell.self, forCellWithReuseIdentifier: "cell")
            return collectionView
        }()
        
        /// 滚动方向
        private var rollType : Roll?
        
        /// 当前滑动第几个cell
        private var currentIndex : Int?
        
        /// 处理的数组,因为要避免回退动画,就是最后一个回到第一个
        private var tempList : Array<Any>?
        
        /// 数据源
        var models : Array<Any>? {
            didSet {
                guard models != nil && (models?.count)! > 0 else {
                    return
                }
                tempList = Array(models!)
                /// 添加多一个数据源用来作过渡
                tempList?.append(models?.first as Any)
                
                /// 延迟2秒
                timer.fireDate = Date(timeIntervalSinceNow: 2)
            }
        }
        
        
        override init(frame: CGRect) {
            super.init(frame: frame)
            initialize()
            createUI()
        }
        
        required init?(coder aDecoder: NSCoder) {
            fatalError("init(coder:) has not been implemented")
        }
        
        /// 出现构造方法
        convenience init(frame: CGRect,type: Roll) {
            self.init(frame: frame)
            rollType = type
            if type == Roll.ver {
                flowLayout.scrollDirection = .vertical
            }else{
                flowLayout.scrollDirection = .horizontal
            }
        }
        
        
        
    }
    
    extension HorseRunningLightsView: UICollectionViewDelegate,UICollectionViewDataSource {
        
        func numberOfSections(in collectionView: UICollectionView) -> Int {
            return 1
        }
        
        func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
            return tempList?.count ?? 0
        }
        
        func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
            let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath)
            if indexPath.row == 0 {
                cell.backgroundColor = UIColor.red
            }else if indexPath.row == 1 {
                cell.backgroundColor = UIColor.yellow
            }else if indexPath.row == 2 {
                cell.backgroundColor = UIColor.green
            }else if indexPath.row == 3 {
                cell.backgroundColor = UIColor.blue
            }else if indexPath.row == 4 {
                cell.backgroundColor = UIColor.purple
            }
            return cell
        }
    }
    
    extension HorseRunningLightsView: UICollectionViewDelegateFlowLayout {
        /// cell尺寸
        func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
            return CGSize(width: self.collectionView.width, height: self.collectionView.height)
        }
        
        /// 这个是两行cell之间的间距(上下行cell的间距)
        func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
            return 0
        }
        
        /// 定义每个Section的四边间距
        func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets {
            return UIEdgeInsets(top: 0, left: 0, bottom: 0, right: 0)
        }
        
    }
    
    extension HorseRunningLightsView: UIScrollViewDelegate {
        /// scrollView的动画结束后会进入此方法
        /// 当滚动到最后一个的处理
        func scrollViewDidEndScrollingAnimation(_ scrollView: UIScrollView) {
            if self.currentIndex == self.tempList?.count {
                self.currentIndex = 1
                self.collectionView.setContentOffset(CGPoint(x: 0, y: 0), animated: false)
            }
        }
    }
    
    extension HorseRunningLightsView {
        func initialize() {
            currentIndex = 1
        }
        
        func createUI() {
            addSubview(collectionView)
        }
    }
    
    extension HorseRunningLightsView {
        @objc private func startToMove(){
            if rollType == Roll.ver {
                let y = CGFloat(self.currentIndex!) * self.collectionView.height
                self.currentIndex = self.currentIndex! + 1
                self.collectionView.setContentOffset(CGPoint(x: 0, y: y), animated: true)
            }else{
                let x = CGFloat(self.currentIndex!) * self.collectionView.width
                self.currentIndex = self.currentIndex! + 1
                self.collectionView.setContentOffset(CGPoint(x: x, y: 0), animated: true)
            }
        }
    }
    
        override func viewDidLoad() {
            super.viewDidLoad()
            // Do any additional setup after loading the view, typically from a nib.
            let v = HorseRunningLightsView(frame: CGRect(x: 0, y: 100, width: self.view.width, height: 44), type: Roll.hor)
            v.models = ["你好吗","呵呵呵","你还好意思问我","我这不是在关心你嘛"]
            view.addSubview(v)
        }
    

    相关文章

      网友评论

          本文标题:iOS-带图片的跑马灯,可自定义view

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