网易云歌词解析
网易云歌词接口 解析类 如何用
网易云歌词接口
// /lyric?id=447926071
{
"sgc": false,
"sfy": false,
"qfy": false,
"lrc": {
"version": 7,
"lyric": "[00:00.000] 作曲 : 赵雷\n[00:01.000] 作词 : 赵雷\n[00:04.75]编曲:赵雷 / 喜子\n[00:05.75]\n[00:06.75]BASS:张岭\n[00:07.75]鼓:贝贝\n[00:08.75]钢琴:柳森\n[00:09.75]箱琴:赵雷 / 喜子\n[00:10.75]笛子:祝子\n[00:11.75]弦乐编写:柳森\n[00:12.75]弦乐:亚洲爱乐国际乐团\n[00:13.75]和声:朱奇迹 / 赵雷 / 旭东\n[00:16.75]让我掉下眼泪的 不止昨夜的酒\n[00:25.91]让我依依不舍的 不止你的温柔\n[00:33.91]余路还要走多久 你攥着我的手\n[00:41.70]让我感到为难的 是挣扎的自由\n[00:52.10]分别总是在九月 回忆是思念的愁\n[00:59.63]深秋嫩绿的垂柳 亲吻着我额头\n[01:07.53]在那座阴雨的小城里 我从未忘记你\n[01:15.41]成都 带不走的 只有你\n[01:23.69]和我在成都的街头走一走\n[01:31.08]直到所有的灯都熄灭了也不停留\n[01:39.69]你会挽着我的衣袖 我会把手揣进裤兜\n[01:47.08]走到玉林路的尽头 坐在(走过)小酒馆的门口\n[02:30.37]分别总是在九月 回忆是思念的愁\n[02:38.10]深秋嫩绿的垂柳 亲吻着我额头\n[02:46.13]在那座阴雨的小城里 我从未忘记你\n[02:54.02]成都 带不走的 只有你\n[03:02.34]和我在成都的街头走一走\n[03:10.41]直到所有的灯都熄灭了也不停留\n[03:18.34]你会挽着我的衣袖 我会把手揣进裤兜\n[03:25.51]走到玉林路的尽头 坐在(走过)小酒馆的门口\n[04:35.96][03:35.40]和我在成都的街头走一走\n[04:42.76][03:45.39]直到所有的灯都熄灭了也不停留\n[03:53.62]和我在成都的街头走一走\n[04:01.35]直到所有的灯都熄灭了也不停留\n[04:08.95]你会挽着我的衣袖 我会把手揣进裤兜\n[04:17.27]走到玉林路的尽头 坐在(走过)小酒馆的门口\n"
},
"klyric": {
"version": 0,
"lyric": null
},
"tlyric": {
"version": 0,
"lyric": null
},
"code": 200
}
解析类
export class Lyric {
constructor(data) {
this.data = data;
this.lrc = data["lrc"]["lyric"];
this.tlyric = data["tlyric"]["lyric"];
this.lrcMap = this.getLyricMap(this.lrc);
this.finalLrcMap = this.convertProp(Object.assign({}, this.lrcMap));
this.tlyricMap = this.getLyricMap(this.tlyric);
this.finalTlyricMap = this.convertProp(Object.assign({}, this.tlyricMap));
}
// 以对象形式格式化歌词,{[00:12.570]: "歌词"}
getLyricMap(lrc) {
let key, value, sIdx, eIdx, nsIdx;
let ret = {};
if (!lrc || typeof lrc !== "string") return ret;
while (lrc) {
sIdx = lrc.indexOf("[");
eIdx = lrc.indexOf("]") + 1;
if (sIdx !== -1 && eIdx !== -1) {
key = lrc.slice(sIdx, eIdx);
advance(eIdx);
nsIdx = lrc.indexOf("[");
value = lrc.slice(0, nsIdx);
ret[key] = value.trim();
advance(nsIdx);
} else {
break;
}
}
function advance(n) {
lrc = lrc.substring(n);
}
return ret;
}
// 再次格式化歌词,{12570: "歌词"},过滤了空串
convertProp(obj) {
Object.keys(obj).forEach((str) => {
if (!obj[str]) {
delete obj[str];
} else {
let prop = f(str);
obj[prop] = obj[str];
delete obj[str];
}
});
function f(str) {
str = str.match(/^\[(\d+):(\d+)\.(\d+)/);
return Number(str[1]) * 60 * 1000 + Number(str[2]) * 1000 + Number(str[3]);
}
return obj;
}
// 获取当前歌词
getCurPlayLyric(audioCurTime) {
let audioCurTimeMs = audioCurTime * 1000;
let arrTime = Object.keys(this.finalLrcMap);
let i = 0,
len = arrTime.length,
idx;
let hasTranslate = Object.keys(this.finalTlyricMap).length > 0;
if (audioCurTimeMs === 0) {
return g.call(this, arrTime[0]);
}
if (audioCurTimeMs >= Number(arrTime[len - 1])) {
return g.call(this, arrTime[len - 1]);
}
for (; i < len; i++) {
if (audioCurTimeMs >= Number(arrTime[i - 1]) && audioCurTimeMs < Number(arrTime[i])) {
idx = i - 1;
break;
}
}
return g.call(this, arrTime[idx]);
function g(prop) {
return hasTranslate ? v(this.finalLrcMap[prop]) + "\n" + v(this.finalTlyricMap[prop]) : v(this.finalLrcMap[prop]);
}
function v(val) {
return typeof val === "undefined" ? "" : val;
}
}
}
如何用
// init lyricData是歌词接口返回的数据
lyric = new Lyric(lyricData);
// 监听播放 $audio是audio标签,如果使用vue,内置timeupdate钩子
$audio.addEventListener(
"timeupdate",
() => {
// 当前时间的歌词
let lyric = getCurPlayLyric($audio.currentTime);
},
false
);
即可发布评论!
暂无评论
确认评论邮箱
邀请制评论