zoukankan      html  css  js  c++  java
  • CATextLayer与 CAShapeLayer(波浪)

    效果

    XYWaterWaveView.h文件

    #import <UIKit/UIKit.h>
    @interface XYWaterWaveView : UIView
    /**
    *  波纹振幅 默认30
    */
    @property (nonatomic ,assign) CGFloat waveAmplitude;
    /**
    *  振幅周期 默认200
    */
    @property (nonatomic ,assign) CGFloat waveCycle;
    /**
     *  波纹速度 默认 0.2
    */
    @property (nonatomic ,assign) CGFloat waveSpeed;
    /**
     *  波纹高度 默认为300
     */
    @property (nonatomic ,assign) CGFloat waterWaveHeight;
    /**
    *  波纹颜色 默认红色
    */
    @property (nonatomic, strong) UIColor* waveColor;
    /**
    *  开始
    */
    - (void)startWave;
    @end
    

    XYWaterWaveView.m文件

    #import "XYWaterWaveView.h"
    @interface XYWaterWaveView()
    {
        CGFloat _height;
        CGFloat _width;
    }
    /**
     *  波纹偏移
    */
    @property (nonatomic ,assign) CGFloat offsetX;
    /**
     *  波纹频率
     */
    @property (nonatomic ,assign) CGFloat waveRate;
    /**
     *  定时器
    */
    @property (nonatomic, strong) CADisplayLink *waveDisplaylink;
    /**
     *  波纹图层
     */
    @property (nonatomic, strong) CAShapeLayer *waveLayer;
    /**
     *  背景图层
     */
    @property (nonatomic, strong) CAShapeLayer *backLayer;
    /**
     *  介绍
     */
    @property (nonatomic, strong) CATextLayer *textLayer;
    @end
    @implementation XYWaterWaveView
    #pragma mark -- init
    - (instancetype)initWithFrame:(CGRect)frame{
    self = [super initWithFrame:frame];
    if (self) {
        [self initData];
    }
    return self;
    }
    - (void)initData{
    /**
     Asin(rt + x)
     A:waveAmplitude
     r:waveRate
     x:offsetX
     */
    //振幅
    self.waveAmplitude = 30.0f;
    //周期
    self.waveCycle = 200.0f;
    //频率
    self.waveRate = 2*M_PI/self.waveCycle;
    //偏移
    self.offsetX = 0.0f;
    //高度
    self.waterWaveHeight = 300.0f;
    //速度
    self.waveSpeed = 0.2f;
    //颜色
    self.waveColor = [UIColor redColor];
    _height = self.frame.size.height;
    _width = self.frame.size.width;
    }
    #pragma mark - set
    - (void)setWaveAmplitude:(CGFloat)waveAmplitude{
    _waveAmplitude = waveAmplitude;
    }
    - (void)setWaveCycle:(CGFloat)waveCycle{
    _waveCycle = waveCycle;
    _waveRate = 2*M_PI/_waveCycle;
    }
    - (void)setWaterWaveHeight:(CGFloat)waterWaveHeight{
    _waterWaveHeight = waterWaveHeight;
    NSString *text = [NSString stringWithFormat:@"%.2f%@",_waterWaveHeight/_height*100,@"%"];
    _textLayer.string = text;
    }
    - (void)setWaveSpeed:(CGFloat)waveSpeed{
    _waveSpeed = waveSpeed;
    }
    #pragma mark -- 开始
    - (void)startWave{
    if (_waveDisplaylink) {
        return;
    }
    if (self.waveLayer == nil) {
        // 创建第一个波浪Layer
        _waveLayer = [CAShapeLayer layer];
        _waveLayer.fillColor = self.waveColor.CGColor;
        [self.layer addSublayer:_waveLayer];
    }
    if (self.backLayer == nil) {
        _backLayer = [CAShapeLayer layer];
        _backLayer.frame = self.bounds;
        _backLayer.fillColor = [UIColor yellowColor].CGColor;
        _backLayer.backgroundColor = [UIColor blackColor].CGColor;
        [self.layer addSublayer:_backLayer];
    }
    if (self.textLayer == nil) {
        _textLayer = [CATextLayer layer];
        _textLayer.foregroundColor = [UIColor blackColor].CGColor;
        _textLayer.alignmentMode =kCAAlignmentJustified;
        _textLayer.wrapped =YES;
        _textLayer.frame = CGRectMake((_width - 150)/2, (_height - 40)/2, 150, 40);
        UIFont *font = [UIFont systemFontOfSize:40];
        CFStringRef fontName = (__bridge CFStringRef)font.fontName;
        CGFontRef fontRef =CGFontCreateWithFontName(fontName);
        _textLayer.font = fontRef;
        _textLayer.fontSize = font.pointSize;
        CGFontRelease(fontRef);
        NSString *text = [NSString stringWithFormat:@"%.2f%@",_waterWaveHeight/_height*100,@"%"];
        _textLayer.string = text;
        _textLayer.contentsScale = [UIScreen mainScreen].scale;
        [self.layer addSublayer:_textLayer];
        [_backLayer setMask:_textLayer];
    }
    // 启动定时调用
    _waveDisplaylink = [CADisplayLink displayLinkWithTarget:self selector:@selector(getCurrentWave:)];
    [_waveDisplaylink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
    }
    - (void)getCurrentWave:(CADisplayLink *)dicplayLink{
    // 波浪位移
    self.offsetX += self.waveSpeed;
    if (self.waterWaveHeight > _height - self.waveAmplitude) {
        self.waterWaveHeight = _height - self.waveAmplitude;
    }
    [self setCurrentWaveLayerPath];
    }
    - (void)setCurrentWaveLayerPath{
    CGMutablePathRef path = CGPathCreateMutable();
    CGFloat currentWavePointY = _height - self.waterWaveHeight;
    CGPathMoveToPoint(path, nil, 0, currentWavePointY);
    for (float x = 0.0f; x <= _width ; x++) {
        // 正弦波浪公式
        CGFloat y = self.waveAmplitude * sin(self.waveRate * x + self.offsetX) + currentWavePointY;
        CGPathAddLineToPoint(path, nil, x, y);
    }
    CGPathAddLineToPoint(path, nil, _width, _height);
    CGPathAddLineToPoint(path, nil, 0, _height);
    CGPathCloseSubpath(path);
    self.waveLayer.path = path;
    CGMutablePathRef backPath = CGPathCreateMutableCopy(path);
    self.backLayer.path = backPath;
    CGPathRelease(backPath);
    CGPathRelease(path);
    }
    #pragma mark -- 停止
    - (void)reset
    {
    [self stopWave];
    [_waveLayer removeFromSuperlayer];
    _waveLayer = nil;
    }
    - (void)stopWave{
    [_waveDisplaylink invalidate];
    _waveDisplaylink = nil;
    }
    - (void)dealloc{
    [self reset];
    }
    @end
    

    ViewController调用

    -(void)viewDidLoad {
    [super viewDidLoad];
    waterWaveView = [[XYWaterWaveView alloc]initWithFrame:self.view.bounds];
    waterWaveView.backgroundColor = [UIColor clearColor];
    [self.view addSubview:waterWaveView];
    [waterWaveView startWave];
    
    //振幅
    UILabel* label1 = [[UILabel alloc]initWithFrame:CGRectMake(0, 20, 60, 40)];
    label1.text = @"振幅";
    [self.view addSubview:label1];
    UISlider* slider1 = [[UISlider alloc]initWithFrame:CGRectMake(40, 20, 280, 40)];
    slider1.minimumValue = http://blog.csdn.net/xiaoxiaobukuang/article/details/20.0;
    slider1.maximumValue = 40.0;
    slider1.value = 30;
    [slider1 addTarget:self action:@selector(slider1:) forControlEvents:UIControlEventValueChanged];
    [self.view addSubview:slider1];
    //周期
    UILabel* label2 = [[UILabel alloc]initWithFrame:CGRectMake(0, 80, 60, 40)];
    label2.text = @"周期";
    [self.view addSubview:label2];
    UISlider* slider2 = [[UISlider alloc]initWithFrame:CGRectMake(40, 80, 280, 40)];
    slider2.minimumValue = http://blog.csdn.net/xiaoxiaobukuang/article/details/100.0;
    slider2.maximumValue = 300.0;
    slider2.value = 200;
    [slider2 addTarget:self action:@selector(slider2:) forControlEvents:UIControlEventValueChanged];
    [self.view addSubview:slider2];
    //速度
    UILabel* label3 = [[UILabel alloc]initWithFrame:CGRectMake(0, 140, 60, 40)];
    label3.text = @"速度";
    [self.view addSubview:label3];
    UISlider* slider3 = [[UISlider alloc]initWithFrame:CGRectMake(40, 140, 280, 40)];
    slider3.minimumValue = http://blog.csdn.net/xiaoxiaobukuang/article/details/0.1f;
    slider3.maximumValue = 0.3f;
    slider3.value = 0.2f;
    [slider3 addTarget:self action:@selector(slider3:) forControlEvents:UIControlEventValueChanged];
    [self.view addSubview:slider3];
    //高度
    UILabel* label4 = [[UILabel alloc]initWithFrame:CGRectMake(0, 200, 60, 40)];
    label4.text = @"高度";
    [self.view addSubview:label4];
    UISlider* slider4 = [[UISlider alloc]initWithFrame:CGRectMake(40, 200, 280, 40)];
    slider4.minimumValue = http://blog.csdn.net/xiaoxiaobukuang/article/details/0;
    slider4.maximumValue = self.view.frame.size.height;
    slider4.value = 300;
    [slider4 addTarget:self action:@selector(slider4:) forControlEvents:UIControlEventValueChanged];
    [self.view addSubview:slider4];
    }
    - (void)slider1:(UISlider *)slider{
    waterWaveView.waveAmplitude = slider.value;
    }
    - (void)slider2:(UISlider *)slider{
    waterWaveView.waveCycle = slider.value;
    }
    - (void)slider3:(UISlider *)slider{
    waterWaveView.waveSpeed = slider.value;
    }
    - (void)slider4:(UISlider *)slider{
    waterWaveView.waterWaveHeight = slider.value;
    }
  • 相关阅读:
    Codeforces Global Round 11
    2018-2019 ICPC, Asia Najing
    Codeforces Round #675 (Div. 2) ABCDE
    AtCoder Regular Contest 104 D(卡常)
    Navigator History Location
    键盘移动div
    键盘事件
    事件的传播
    事件的绑定
    事件的委派
  • 原文地址:https://www.cnblogs.com/sunyanyan/p/5360234.html
Copyright © 2011-2022 走看看