iOS開發--QQ音樂練習,歌詞的展示,歌詞的滾動,歌詞的顏色變化


一.歌詞的展示 -- 首先歌詞是在scrollView上,scrollView的大小是兩個屏幕的寬度

  • scrollView滾動修改透明度的代碼                                                            
  • 自定義展示歌詞的view,繼承自UIScrollView,向外界提供一個歌詞文件名的屬性

    /** 歌詞文件的名字 */

    @property(nonatomic,copy) NSString *lrcFileName;

    重寫setter,解析歌詞,通過歌詞的工具類獲得模型集合

  • 歌詞工具類的實現
     1 #import "ChaosLrcTool.h"
     2 #import "ChaosLrc.h"
     3 
     4 @implementation ChaosLrcTool
     5 + (NSArray *)lrcToolWithLrcName:(NSString *)lrcname
     6 {
     7     // 1.獲取文件路徑
     8     NSString *lrcPath = [[NSBundle mainBundle] pathForResource:lrcname ofType:nil];
     9     // 2.加載文件內容
    10     NSString *lrcString = [NSString stringWithContentsOfFile:lrcPath encoding:NSUTF8StringEncoding error:nil];
    11     // 3.切割字符串
    12     NSArray *lrcLines = [lrcString componentsSeparatedByString:@"\n"];
    13     // 4.遍歷集合,轉換成歌詞模型
    14     NSMutableArray *arr = [NSMutableArray array];
    15     for (NSString *lrcLineString in lrcLines) {
    16         /*
    17          [ti:簡單愛]
    18          [ar:周傑倫]
    19          [al:范特西]
    20          */
    21         // 5.跳過指定行
    22         if ([lrcLineString hasPrefix:@"[ti"] || [lrcLineString hasPrefix:@"[ar"] || [lrcLineString hasPrefix:@"[al"] || ![lrcLineString hasPrefix:@"["]) {
    23             continue;
    24         }
    25         ChaosLrc *lrc = [ChaosLrc lrcWithLrcLine:lrcLineString];
    26         [arr addObject:lrc];
    27     }
    28     return arr;
    29 }
    30 @end

     

  • 歌詞解析完畢后,根據歌詞模型集合來實現tableView(歌詞用tableView來顯示)的數據源方法

二.歌詞的滾動

  • 歌詞的滾動由每一句的時間來決定,自定義的歌詞的view需要外界不停的提供歌曲播放的時間,自己來判斷並滾動顯示對應的歌詞.所以自定義的歌詞View需要向外界提供一個時間屬性,重寫時間屬性來實現歌詞滾動
     1 #pragma mark - 歌詞滾動
     2 // 重寫time的setter
     3 - (void)setCurrentTime:(NSTimeInterval)currentTime
     4 {
     5     _currentTime = currentTime;
     6     // 遍歷歌詞,找到對應時間應該顯示的歌詞模型
     7     for (int i = 0; i < self.lrcList.count; i++) {
     8         // 當前的歌詞
     9         ChaosLrc *lrc = self.lrcList[i];
    10         NSInteger next = i + 1;
    11         // 下一句歌詞
    12         ChaosLrc *nextLrc;
    13         if (next < self.lrcList.count) {
    14             nextLrc = self.lrcList[next];
    15         }
    16         if (self.currentLrcIndex != i && currentTime >= lrc.time && currentTime < nextLrc.time) {
    17             
    18             NSIndexPath *indexPath = [NSIndexPath indexPathForRow:i inSection:0];
    19             NSIndexPath *previousIndexPath = [NSIndexPath indexPathForRow:self.currentLrcIndex inSection:0];
    20             // 記錄當前行
    21             self.currentLrcIndex = i;
    22             // 滿足條件,tableview滾動
    23             [self.lrcView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionTop animated:YES];
    24             // 刷新上一行,字體還原
    25             [self.lrcView reloadRowsAtIndexPaths:@[previousIndexPath] withRowAnimation:UITableViewRowAnimationNone];
    26             // 刷新當前行,字體變大
    27             [self.lrcView reloadRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationNone];
    28         }
    29         // 當前歌詞的label的進度
    30         if (self.currentLrcIndex == i) {
    31             
    32             // 獲取當前的cell
    33             NSIndexPath *currentIndexPath = [NSIndexPath indexPathForRow:i inSection:0];
    34             ChaosLrcCell *currentCell = [self.lrcView cellForRowAtIndexPath:currentIndexPath];
    35             CGFloat totalTime = nextLrc.time - lrc.time; // 當前歌詞總時間
    36             CGFloat progressTime = currentTime - lrc.time; // 當前歌詞已經走過了多長時間
    37             currentCell.lrcLabel.progress = progressTime / totalTime;
    38             
    39             // 主頁的label
    40             self.mainLabel.text = lrc.text;
    41             self.mainLabel.progress = currentCell.lrcLabel.progress;
    42         }
    43     }
    44 }

     

  • 外界給歌詞的View提供時間就不是每一秒提供一次那么簡單了,外界需要更牛逼的定時器                                     
    • 播放的時候添加定時器                              
    • 定時器的方法中實現給歌詞的view提供的時間屬性賦值

三.歌詞的顏色變化 -- 畫上去的(自定義cell中的顯示歌詞的label,label需要外界提供一個進度值,自己內部根據進度值來畫)

  • 自定義label的實現
     1 #import "ChaosLabel.h"
     2 
     3 @implementation ChaosLabel
     4 
     5 - (void)setProgress:(CGFloat)progress
     6 {
     7     _progress = progress;
     8     // 重繪
     9     [self setNeedsDisplay];
    10 }
    11 
    12 - (void)drawRect:(CGRect)rect {
    13     
    14     [super drawRect:rect];
    15     
    16     // 1.獲取需要畫的區域
    17     CGRect fillRect = CGRectMake(0, 0, self.bounds.size.width * self.progress, self.bounds.size.height);
    18     // 2.選擇顏色
    19     [[UIColor yellowColor] set];
    20     // 3.添加區域開始畫圖
    21 //    UIRectFill(fillRect);
    22     UIRectFillUsingBlendMode(fillRect, kCGBlendModeSourceIn);
    23 }
    24 
    25 @end

     

  • 外部進度值的計算

                 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM