iOS 动画-波浪,这个东西早就想看看了。
今天花了点时间看了看。
要做出这个效果首先要懂得正弦函数
y =Asin(ωx+φ)+C
A 表示振幅,也就是使用这个变量来调整波浪的高度
ω表示周期,也就是使用这个变量来调整在屏幕内显示的波浪的数量
φ表示波浪横向的偏移,也就是使用这个变量来调整波浪的流动
C表示波浪纵向的位置,也就是使用这个变量来调整波浪在屏幕中竖直的位置。
@property (nonatomic, sng) CADisplayLink *waveDisplaylink;
@property (nonatomic, strong) CAShapeLayer *firstWaveLayer;
CADisplayLink的对象也是一个定时器。适用于UI的不停刷新,如自定义动画引擎或者视频的渲染。CADisplayLink 对象注册到Runloop之后。屏幕刷新的时候定时器就会被触发。iOS设备的刷新频率是60HZ也就是60帧也就是每秒刷新60次,也可以通过设置frameInterval属性为2那么两帧才会刷新一次。
CAShapeLayer 的对象是一个本身没有形状,他的形状来源于你给定的Path,它依附于path,所以必须给定path,即使path不完整也会自动收尾相接,strokeStart以及stroleEnd代表着这个path中所占的百分比(可以使用storkeStart和stroleEnd来做曲线进度的动画)。
基础变量
CGFloat waveA;//水纹振幅 表示上面的A
CGFloat waveW ;//水纹周期 表示上面的ω
CGFloat offsetX; //位移 表示上面的φ
CGFloat currentK; //当前波浪高度Y 表示上面的C
CGFloat waveSpeed;//水纹速度 表示波浪流动的速度
CGFloat waterWaveWidth; //水纹宽度
//设置波浪的宽度
waterWaveWidth = self.frame.size.width;
//设置波浪的颜色
_firstWaveColor = [UIColor colorWithRed:223/255.0 green:22/255.0 blue:64/255.0 alpha:1];
//设置波浪的速度
waveSpeed = 0.4/M_PI;
//初始化layer
if (_firstWaveLayer == nil) {
//初始化
_firstWaveLayer = [CAShapeLayer layer];
//设置闭环的颜色
_firstWaveLayer.fillColor = _firstWaveColor.CGColor;
//设置边缘线的颜色
// _firstWaveLayer.strokeColor = [UIColor blueColor].CGColor;
//设置边缘线的宽度
// _firstWaveLayer.lineWidth = 4.0;
[self.layer addSublayer:_firstWaveLayer];
}
//设置波浪流动速度
waveSpeed = 0.1;
//设置振幅
waveA = 10;
//设置周期
waveW = 1/30.0;
//设置波浪纵向位置
currentK = self.frame.size.height/2;//屏幕居中
//启动定时器
_waveDisplaylink = [CADisplayLink displayLinkWithTarget:self selector:@selector(getCurrentWave:)];
[_waveDisplaylink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
-(void)setCurrentFirstWaveLayerPath
{
//创建一个路径
CGMutablePathRef path = CGPathCreateMutable();
CGFloat y = currentK;
//将点移动到 x=0,y=currentK的位置
CGPathMoveToPoint(path, nil, 0, y);
for (NSInteger x = 0.0f; x<=waterWaveWidth; x++) {
//正玄波浪公式
y = waveA * sin(waveW * x+ offsetX)+currentK;
//将点连成线
CGPathAddLineToPoint(path, nil, x, y);
}
CGPathAddLineToPoint(path, nil, waterWaveWidth, self.frame.size.height);
CGPathAddLineToPoint(path, nil, 0, self.frame.size.height);
CGPathCloseSubpath(path);
_firstWaveLayer.path = path;
CGPathRelease(path);
}
Demo:http://download.youkuaiyun.com/detail/u010123208/9500406