iOS 圓形水波浪效果實現
阿新 • • 發佈:2020-12-29
https://www.jianshu.com/p/1c947bb906cb?utm_campaign
水波浪效果如下
waterWave.gif最近專案中用到一個小的波浪動畫,查閱了一些資料如下:
網上參考的一些效果
CDNS上的原理
主要實現方法
- 水波動畫的關鍵點就是正餘弦函式
- 這個效果主要的思路是新增兩條曲線 一條正弦曲線、一條餘弦曲線 然後在曲線下新增深淺不同的背景顏色,從而達到波浪顯示的效果
正弦.png正弦型函式解析式:y=Asin(ωx+φ)+h
各常數值對函式影象的影響:
φ(初相位):決定波形與X軸位置關係或橫向移動距離(左加右減)
ω:決定週期(最小正週期T=2π/|ω|)
A:決定峰值(即縱向拉伸壓縮的倍數)
h:表示波形在Y軸的位置關係或縱向移動距離(上加下減)
我們想要繪製一條函式,這個曲線其實都是柵格的畫素點組成。可以沿著假想的曲線繪製許多個點,然後把點逐一用直線連在一起,如果點足夠多,就可以得到一條滿足需求的曲線,這也是一種微分的思想。而這些點的位置可以通過正弦函式的解析式求得。
如果要繪製上面這個曲線,可以觀察:波的峰值是1,週期是2π,初相位是0,h位移也是0。那麼計算各個點的座標公式就是y = sin(x);獲得各個點的座標之後,使用CGPathAddLineToPoint這個函式,把這些點逐一連成線,就可以得到最後的路徑。
另外一條波浪使用餘弦函式,同樣的原理,使得2條波浪錯開顯示。
//繪製的部分程式碼
CGFloat waterWaveWidth = self.bounds.size.width;
//初始化運動路徑
CGMutablePathRef path = CGPathCreateMutable();
CGMutablePathRef maskPath = CGPathCreateMutable();
//設定起始位置
CGPathMoveToPoint(path, nil, 0, _waveY);
//設定起始位置
CGPathMoveToPoint(maskPath, nil, 0, _waveY);
//初始化波浪其實Y為偏距
CGFloat y = _waveY;
//正弦曲線公式為: y=Asin(ωx+φ)+k;
for (float x = 0.0f; x <= waterWaveWidth ; x++) {
y = _waveAmplitude * sin(_wavePalstance * x + _waveX) + _waveY;
CGPathAddLineToPoint(path, nil, x, y);
}
現在 我們有了一條靜態的線,那怎麼讓他動起來呢?
平移後的影象我們可以讓他向左或者向右平移 每隔一段時間平移一次 使用CADisplayLink 使得平移看起來更加的流暢;
//以螢幕重新整理速度為週期刷新曲線的位置
_disPlayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(waveAnimation:)];
[_disPlayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
然後在利用CAShapeLayer繪製該波浪。
至此動畫的基本原理就搞清楚了,具體的程式碼實現在demo地址:)
作者:CoderSJun
連結:https://www.jianshu.com/p/1c947bb906cb
來源:簡書
著作權歸作者所有。商業轉載請聯絡作者獲得授權,非商業轉載請註明出處。