Android下载并解析Lrc歌词文件

大多数歌词文件都是.lrc文件,我们看一下lrc文件里面的内容
在这里插入图片描述
可以看到中括号里面的就是该行歌词所对应的时间,后面则是歌词,所以提取起来还是很简单的,就是对字符串的操作而已。
代码如下:

private static Lyric parseLine(String line) {
    // LRC歌词通常是这样的格式:[mm:ss]歌词内容
    // 或者是 [mm:ss.ff]歌词内容
    if (line.startsWith("[") && line.contains("]")) {
        String[] parts = line.split("]");
        String timeStr = parts[0].substring(1); // 去掉开头的[
        String[] timeParts = timeStr.split(":");
        int minutes = Integer.parseInt(timeParts[0]);
        String[] timeParts2 = timeParts[1].split("\\.");
        int seconds = Integer.parseInt(timeParts2[0]);
        int milliseconds = Integer.parseInt(timeParts2[1]);
        milliseconds = milliseconds % 1000;//避免有些歌词文件的毫秒太长

        int time = (int) ((minutes * 60 + seconds) * 1000 + milliseconds);

        String lrcText="";
        if (parts.length>=2){
            lrcText = parts[1].trim();
        }

        Lyric lrcContent = new Lyric();
        lrcContent.setMinutes(minutes);
        lrcContent.setSeconds((int) seconds);
        lrcContent.setMilliseconds(milliseconds);
        lrcContent.setTime(time);
        lrcContent.setLyric(lrcText);
        return lrcContent;
    }
    return null; // 如果行不是有效的LRC格式,返回null
}

这里我只是解析一行的而已。
这里面有一个Lyric(歌词)类


public class Lyric {
    private int Time; // 时间戳
    private String Lyric; // 歌词内容
    private int Minutes;
    private int Seconds;
    private int Milliseconds;

    public int getTime() {
        return Time;
    }

    public void setTime(int time) {
        Time = time;
    }

    public String getLyric() {
        return Lyric;
    }

    public void setLyric(String lyric) {
        Lyric = lyric;
    }

    public int getMinutes() {
        return Minutes;
    }

    public void setMinutes(int minutes) {
        Minutes = minutes;
    }

    public int getSeconds() {
        return Seconds;
    }

    public void setSeconds(int seconds) {
        Seconds = seconds;
    }

    public int getMilliseconds() {
        return Milliseconds;
    }

    public void setMilliseconds(int milliseconds) {
        Milliseconds = milliseconds;
    }
}

这样解析后呢我们就可以得到一行歌词的成分了,因为最终我们加载lrc文件的时候是一行一行读取得,所以就可以每加载一行就解析存进集合里(arraylist,linkedList之类的)
如果有lrc文件的下载链接呢,就可以用以下代码下载并解析歌词文件啦。


import android.util.Log;

import com.example.utils.Lyric;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;


public class LyricParser {

    public LyricParser() {
    }


    public static void  parseLrc(String lrcUrl,LyricCallback callback) {

        new Thread(){
            @Override
            public void run() {
                super.run();
                InputStream is = null;
                try {
                    URL url = new URL(lrcUrl);
                    HttpURLConnection connection = (HttpURLConnection) url.openConnection();
                    connection.setRequestMethod("GET");
                    connection.setRequestProperty("Content-Type", "text/plain");
                    connection.connect();

                    is = connection.getInputStream();

                    BufferedReader reader = new BufferedReader(new InputStreamReader(is));
                    List<Lyric> lrcList = new ArrayList<>();

                    String line;
                    while ((line = reader.readLine()) != null) {
                        // 解析每一行歌词
//                        Log.e("LrcParser",line);
                        Lyric lrcContent = parseLine(line);
                        if (lrcContent != null) {
                            lrcList.add(lrcContent);
                        }
                    }
                    callback.onBack(lrcList);
                    connection.disconnect();


                } catch (IOException e) {
                    Log.e("LrcParser", "Error reading lrc file", e);
                } finally {
                    try {
                        if (is != null) {
                            is.close();
                        }
                    } catch (IOException e) {
                        Log.e("LrcParser", "Error closing stream", e);
                    }
                }
            }
        }.start();
    }

    private static Lyric parseLine(String line) {
        // LRC歌词通常是这样的格式:[mm:ss]歌词内容
        // 或者是 [mm:ss.ff]歌词内容
        if (line.startsWith("[") && line.contains("]")) {
            String[] parts = line.split("]");
            String timeStr = parts[0].substring(1); // 去掉开头的[
            String[] timeParts = timeStr.split(":");
            int minutes = Integer.parseInt(timeParts[0]);
            String[] timeParts2 = timeParts[1].split("\\.");
            int seconds = Integer.parseInt(timeParts2[0]);
            int milliseconds = Integer.parseInt(timeParts2[1]);
            milliseconds = milliseconds % 1000;//避免有些歌词文件的毫秒太长

            int time = (int) ((minutes * 60 + seconds) * 1000 + milliseconds);

            String lrcText="";
            if (parts.length>=2){
                lrcText = parts[1].trim();
            }

            Lyric lrcContent = new Lyric();
            lrcContent.setMinutes(minutes);
            lrcContent.setSeconds((int) seconds);
            lrcContent.setMilliseconds(milliseconds);
            lrcContent.setTime(time);
            lrcContent.setLyric(lrcText);
            return lrcContent;
        }
        return null; // 如果行不是有效的LRC格式,返回null
    }

    public interface LyricCallback{
        public abstract void onBack(List<Lyric> list);
    }

}

要在Android Studio中显示LRC歌词文件,可以按照以下步骤进行操作: 1.在布局文件中添加一个TextView,用于显示歌词。 2.在Java代码中读取LRC文件并将其解析为Map,其中键为时间戳,值为歌词文本。 3.在MediaPlayer的OnPreparedListener中启动一个线程,该线程将定期更新TextView以显示当前播放时间的歌词。 下面是一个简单的示例代码,可以帮助你实现这个功能: ```java // 在布局文件中添加一个TextView,用于显示歌词 TextView lrcTextView = findViewById(R.id.lrcTextView); // 在Java代码中读取LRC文件并将其解析为Map Map<Long, String> lrcMap = new HashMap<>(); try { BufferedReader br = new BufferedReader(new FileReader(lrcFile)); String line; while ((line = br.readLine()) ! null) { Matcher matcher = Pattern.compile("\\[(\\d{2}):(\\d{2})\\.(\\d{2})\\](.*)").matcher(line); if (matcher.find()) { long time = Long.parseLong(matcher.group(1)) * 60 * 1000 + Long.parseLong(matcher.group(2)) * 1000 + Long.parseLong(matcher.group(3)) * 10; String text = matcher.group(4); lrcMap.put(time, text); } } br.close(); } catch (IOException e) { e.printStackTrace(); } // 在MediaPlayer的OnPreparedListener中启动一个线程,该线程将定期更新TextView以显示当前播放时间的歌词 MediaPlayer mediaPlayer = new MediaPlayer(); mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() { @Override public void onPrepared(MediaPlayer mp) { new Thread(new Runnable() { @Override public void run() { while (mediaPlayer.isPlaying()) { long time = mediaPlayer.getCurrentPosition(); if (lrcMap.containsKey(time)) { runOnUiThread(new Runnable() { @Override public void run() { lrcTextView.setText(lrcMap.get(time)); } }); } try { Thread.sleep(100); } catch (InterruptedException e) { e.printStackTrace(); } } } }).start(); } }); // 播放音乐 mediaPlayer.setDataSource(audioFile); mediaPlayer.prepare(); mediaPlayer.start(); ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Dear Mr. Ma

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值