• 使用带粒子效果的 CAEmitterLayer


    下雪 下雨 等粒子动画效果

    CAEmitterLayer用GPU渲染 不占用CPU

    极客学院视频地址 http://www.jikexueyuan.com/course/1302_1.html?ss=2

    ViewController.h

    #import "ViewController.h"
    #import "CAEmitterLayerView.h"
    #import "SnowView.h"
    #import "RainView.h"
    
    @interface ViewController ()
    
    @end
    
    @implementation ViewController
    
    - (void)viewDidLoad {
        [super viewDidLoad];
        // Do any additional setup after loading the view, typically from a nib.
        
        
        //MARK: 1.用 CAEmitterLayer 产生粒子效果
        [self mark1];
        
        //MARK: 2.封装 CAEmitterLayer
        
        CAEmitterLayerView *layerView = [[CAEmitterLayerView alloc]initWithFrame:CGRectZero];
        NSLog(@"%@",layerView.layer);
        
        //MARK: 3.封装下雪、下雨的粒子效果控件
        // 优化效果 添加alpha图层 模糊边界效果
        UIImageView *alphaView1       = [[UIImageView alloc]initWithFrame:CGRectMake(0, 0, 100, 100)];
        alphaView1.image              = [UIImage imageNamed:@"alpha"];
        UIImageView *alphaView2       = [[UIImageView alloc]initWithFrame:CGRectMake(0, 0, 100, 100)];
        alphaView2.image              = [UIImage imageNamed:@"alpha"];
        
        // 添加下雪效果  (在这里复习一下多态 用父类指针指向子类创建出来的对象)
        CAEmitterLayerView *snowView  = [[SnowView alloc]initWithFrame:CGRectMake(100, 220, 100, 100)];
        snowView.maskView             = alphaView1;
        [self.view addSubview:snowView];
        [snowView show];
        
        // 添加下雨效果
        CAEmitterLayerView *rainView  = [[RainView alloc]initWithFrame:CGRectMake(220, 220, 100, 100)];
        rainView.maskView             = alphaView2;
        [self.view addSubview:rainView];
        [rainView show];
    }
    
    - (void)mark1 {
        //第一步 创建出Layer
        CAEmitterLayer *emitterLayer = [CAEmitterLayer layer];
        
        // 设置基本信息
        emitterLayer.borderWidth     = 1.f;
        
        // 给定尺寸
        emitterLayer.frame           = CGRectMake(100, 100, 100, 100);
        // 不让粒子超出layer的范围
        emitterLayer.masksToBounds   = YES;
        // 粒子发射点坐标
        emitterLayer.emitterPosition = CGPointMake(0, 0);
        // 发射模式
        emitterLayer.emitterMode     = kCAEmitterLayerSurface;
        // 发射形状
        emitterLayer.emitterShape    = kCAEmitterLayerLine;
        
        // 添加layer
        [self.view.layer addSublayer:emitterLayer];
        
        //第二步 创建粒子
        CAEmitterCell * cell         = [CAEmitterCell emitterCell];
        
        // 粒子产生率
        cell.birthRate               = 1.f;
        // 粒子生命周期 设置成120秒
        cell.lifetime                = 120.f;
        // 粒子运动的速度值(10) 以及加减的范围(7~13)
        cell.velocity                = 10.f;
        cell.velocityRange           = 3.f;
        // y轴加速度
        cell.yAcceleration           = 2.f;
        // 粒子发射范围的角度
        cell.emissionRange           = 4 * M_1_PI;
        // 设置粒子颜色
        cell.color                   = [UIColor blackColor].CGColor;
        // 设置粒子图片
        cell.contents                = (__bridge id)[UIImage imageNamed:@"snow"].CGImage;
        
        
        //第三步 让CAEmitterLayer和CAEmitterCell产生关联
        emitterLayer.emitterCells    = @[cell];
    }
    

     
    模拟一个抽象的父类CAEmitterLayerView

    CAEmitterLayerView.h

    @interface CAEmitterLayerView : UIView
    
    
    //模拟一个抽象的父类
    
    /*
     模仿setter,getter方法 用.语法解决设置有很多参数的问题
     */
    - (void)setEmitterLayer:(CAEmitterLayer *)layer;
    - (CAEmitterLayer *)emitterLayer;
    
    //显示出当前View
    - (void)show;
    //隐藏当前View
    - (void)hide;
    

     CAEmitterLayerView.m

    @interface CAEmitterLayerView () {
        
        CAEmitterLayer * _emitterLayer;
        
    }
    
    @end
    
    
    @implementation CAEmitterLayerView
    
    //创建layer的过程中把CALayer替换成CAEmitterLayer
    + (Class)layerClass {
        return [CAEmitterLayer class];
    }
    
    - (instancetype)initWithFrame:(CGRect)frame
    {
        self = [super initWithFrame:frame];
        if (self) {
            
            _emitterLayer = (CAEmitterLayer *)self.layer;
            
        }
        return self;
    }
    
    - (void)setEmitterLayer:(CAEmitterLayer *)layer {
        _emitterLayer = layer;
    }
    
    - (CAEmitterLayer *)emitterLayer {
        return _emitterLayer;
    }
    
    - (void)show {
        //这里可以说是 里氏代换原则 每个继承了CAEmitterLayerView的子类都有show的方法 但是都可以重写 实现不同的功能(只有当衍生类可以替换掉基类,软件单位的功能不受到影响时,基类才能真正被复用,而衍生类也能够在基类的基础上增加新的行为)
    }
    
    - (void)hide {
        
    }
    

    继承了CAEmitterLayerView的SnowView和RainView

    SnowView.m

    - (instancetype)initWithFrame:(CGRect)frame
    {
        self = [super initWithFrame:frame];
        if (self) {
            
            [self initEmitterLayerProperties];
            
        }
        return self;
    }
    
    - (void)initEmitterLayerProperties {
        //初始化一些参数
        self.emitterLayer.masksToBounds   = YES;
        self.emitterLayer.emitterShape    = kCAEmitterLayerLine;
        self.emitterLayer.emitterMode     = kCAEmitterLayerSurface;
        self.emitterLayer.emitterSize     = self.frame.size;
        self.emitterLayer.emitterPosition = CGPointMake(self.bounds.size.width / 2.f, - 20);
    }
    
    
    - (void)show {
        //添加 CAEmitterCell
        CAEmitterCell *snowflake  = [CAEmitterCell emitterCell];
        snowflake.birthRate       = 1.f;
        snowflake.speed           = 10.f;
        snowflake.velocity        = 2.f;
        snowflake.velocityRange   = 10.f;
        snowflake.yAcceleration   = 10.f;
        snowflake.emissionRange   = 0.5 * M_PI;
        snowflake.spinRange       = 0.25 * M_PI;
        snowflake.contents        = (__bridge id)([UIImage imageNamed:@"snow"].CGImage);
        snowflake.color           = [UIColor redColor].CGColor;
        snowflake.lifetime        = 60.f;
        snowflake.scale           = 0.5;
        snowflake.scaleRange      = 0.3;
        
        // 添加动画
        self.emitterLayer.emitterCells = @[snowflake];
    }
    

     RainView.m

    - (instancetype)initWithFrame:(CGRect)frame {
        self = [super initWithFrame:frame];
        if (self) {
            // 初始化设置
            [self setup];
        }
        return self;
    }
    
    - (void)setup {
        self.emitterLayer.masksToBounds   = YES;
        self.emitterLayer.emitterShape    = kCAEmitterLayerLine;
        self.emitterLayer.emitterMode     = kCAEmitterLayerSurface;
        self.emitterLayer.emitterSize     = self.frame.size;
        self.emitterLayer.emitterPosition = CGPointMake(self.bounds.size.width / 2.f, - 20);
    }
    
    - (void)show {
        // 配置
        CAEmitterCell *rainflake  = [CAEmitterCell emitterCell];
        rainflake.birthRate       = 25.f;
        rainflake.speed           = 10.f;
        rainflake.velocity        = 10.f;
        rainflake.velocityRange   = 10.f;
        rainflake.yAcceleration   = 1000.f;
        rainflake.contents        = (__bridge id)([UIImage imageNamed:@"rain"].CGImage);
        rainflake.color           = [UIColor blackColor].CGColor;
        rainflake.lifetime        = 7.f;
        rainflake.scale           = 0.2f;
        rainflake.scaleRange      = 0.f;
        
        // 添加动画
        self.emitterLayer.emitterCells = @[rainflake];
    }
    
     
  • 相关阅读:
    (转)编写高质量高效率的SharePoint应用程序
    转:我眼中的Visual Studio 2010架构工具
    Windows 7 x64/Windows 2008 : The ‘Microsoft.Jet.OLEDB.4.0′ provider is not registered on the local machine.
    转:构建高性能ASP.NET站点之一 剖析页面的处理过程(前端)
    HTML5 到底是什么?
    使用eval()解析JSON格式字符串应注意的问题
    使用HTML5进行地理位置定位。误差在+500m
    LAST DAY
    javacript获取obj的长度
    通过 JSON 字符串来创建对象
  • 原文地址:https://www.cnblogs.com/lxllanou/p/4708503.html
Copyright © 2020-2023  润新知