JavaFX: Java音乐播放读取歌词

  • 1、lrc歌词文件
  • 2、解析lrc歌词
    • 2.1 读取每行歌词
    • 2.2 解析歌词时间标签Time-tag
    • 2.3 解析歌词标识标签ID-tags
    • 2.4 创建对象包含歌词相关信息
  • 3、播放显示歌词
  • ** 相关文献

JavaFX: Java音乐播放

1、lrc歌词文件

lrc歌词文件的扩展名

  • 1、标准格式: [分钟:秒.毫秒] 歌词
    注释:(如图1所示)中括号、冒号、点号全都要求英文输入状态;
  • 2、其他格式①:[分钟:秒] 歌词
  • 3、其他格式②:[分钟:秒:毫秒] 歌词,与标准格式相比,秒后边的点号被改成了冒号。

lrc歌词文本中含有两类标签:

  • 一是标识标签,其格式为“[标识名:值]”主要包含以下预定义的标签:
    [ar:歌手名]、[ti:歌曲名]、[al:专辑名]、[by:编辑者(指lrc歌词的制作人)]、[offset:时间补偿值] (其单位是毫秒,正值表示整体提前,负值相反。这是用于总体调整显示快慢的,但多数的MP3可能不会支持这种标签)。
  • 二是时间标签,形式为“[mm:ss]”或“[mm:ss.ff]”(分钟数:秒数.百分之一秒数),时间标签需位于某行歌词中的句首部分,一行歌词可以包含多个时间标签(比如歌词中的迭句部分)。当歌曲播放到达某一时间点时,MP3就会寻找对应的时间标签并显示标签后面的歌词文本,这样就完成了“歌词同步”的功能。

■ 时间标签(Time-tag)
形式为"[mm:ss]"(分钟数:秒数)或"[mm:ss.ff]"。数字须为非负整数, 比如"[12:34.50]"是有效的,而"[0x0C:-34.50]"无效(但也有不太规范的歌词采用[00:-0.12]的方式表示负值以显示歌曲名,部分播放器是支持的)。 它可以位于某行歌词中的任意位置。一行歌词可以包含多个时间标签(比如歌词中的迭句部分)。根据这些时间标签,用户端程序会按顺序依次高亮显示歌词,从而实现卡拉OK功能。另外,标签无须排序。

■ 标识标签(ID-tags)
其格式为"[标识名:值]"。大小写等价。以下是预定义的标签。
[ar:艺人名]
[ti:曲名]
[al:专辑名]
[by:编者(指编辑LRC歌词的人)]
[offset:时间补偿值] 其单位是毫秒,正值表示整体提前,负值相反。这是用于总体调整显示快慢的。

2、解析lrc歌词

[by:天空的星空_SJ5q]
[ti:黄昏]
[ar:周传雄]
[al:忘记]
[by:]
[offset:0]
[00:31.86]
[00:35.19]过完整个夏天忧伤并没有好一些
[00:38.43]
[00:41.29]开车行驶在公路无际无边
[00:47.38]有离开自己的感觉
[00:50.91]
[00:53.64]唱不完一首歌
[00:57.07]
[00:59.75]疲倦还剩下黑眼圈
[01:03.12]
[01:05.92]感情的世界伤害在所难免
[01:12.03]黄昏再美终要黑夜
[01:15.65]
[01:18.64]依然记得从你口中
[01:21.69]说出再见坚决如铁
[01:25.16]昏暗中有种烈日灼身的错觉
[01:30.48]黄昏的地平线
[01:33.53]划出一句离别
[01:36.65]爱情进入永夜
[01:40.30]
[01:43.23]依然记得从你眼中
[01:46.22]滑落的泪伤心欲绝
[01:49.67]混乱中有种热泪烧伤的错觉
[01:55.10]黄昏的地平线
[01:58.17]割断幸福喜悦
[02:01.34]相爱已经幻灭
[02:05.48]
[02:19.87]唱不完一首歌
[02:22.96]
[02:25.89]疲倦还剩下黑眼圈
[02:29.39]
[02:32.11]感情的世界伤害在所难免
[02:38.14]黄昏再美终要黑夜
[02:42.39]
[02:44.73]依然记得从你口中
[02:47.79]说出再见坚决如铁
[02:51.26]昏暗中有种烈日灼身的错觉
[02:56.65]黄昏的地平线
[02:59.72]划出一句离别
[03:02.79]爱情进入永夜
[03:06.38]
[03:09.46]依然记得从你眼中
[03:12.38]滑落的泪伤心欲绝
[03:15.83]混乱中有种热泪烧伤的错觉
[03:21.26]黄昏的地平线
[03:24.34]割断幸福喜悦
[03:27.42]相爱已经幻灭
[03:31.49]
[03:58.73]依然记得从你口中
[04:01.60]说出再见坚决如铁
[04:05.18]昏暗中有种烈日灼身的错觉
[04:10.49]黄昏的地平线
[04:13.56]划出一句离别
[04:16.64]爱情进入永夜
[04:20.10]
[04:23.44]依然记得从你眼中
[04:26.26]滑落的泪伤心欲绝
[04:29.71]混乱中有种热泪烧伤的错觉
[04:35.10]黄昏的地平线
[04:38.17]割断幸福喜悦
[04:41.23]相爱已经幻灭

2.1 读取每行歌词

这里使用commons-ioorg.apache.commons.io.FileUtils

lineList = FileUtils.readLines(file, Charset.defaultCharset());

当然也可以自己实现:

InputStreamReader read = new InputStreamReader(new FileInputStream(file), encoding);
BufferedReader bufferedReader = new BufferedReader(read);
String lineStr = null;
while ((lineStr = bufferedReader.readLine()) != null) {// ... ...
}
read.close();

2.2 解析歌词时间标签Time-tag

private static Map<Long, String> parseLongTime(String line) {String regex = "\\[(\\d{1,2}):(\\d{1,2}).(\\d{1,2})\\]";Pattern pattern = Pattern.compile(regex);Matcher matcher = pattern.matcher(line);Map<Long, String> map = null;while (matcher.find()) {map = new HashMap<Long, String>();// [00:35.19] ----对应---> [分钟:秒.毫秒]String min = matcher.group(1);String sec = matcher.group(2);String mill = matcher.group(3);long time = getLongTime(min, sec, mill + "0");String text = line.substring(matcher.end());map.put(time, text);}return map;}private static long getLongTime(String min, String sec, String mill) {int m = Integer.parseInt(min);int s = Integer.parseInt(sec);int ms = Integer.parseInt(mill);long time = m * 60 * 1000 + s * 1000 + ms;return time;}

2.3 解析歌词标识标签ID-tags

/*** [ar:艺人名]* [ti:曲名]* [al:专辑名]* [by:编者(指编辑LRC歌词的人)]* [offset:时间补偿值] 其单位是毫秒,正值表示整体提前,负值相反。这是用于总体调整显示快慢的。*/private static Map<String, String> parseIdTags(String line) {String regex = "\\[(ar|ti|al|by|offset):(.*)\\]";Pattern pattern = Pattern.compile(regex);Matcher matcher = pattern.matcher(line);Map<String, String> map = null;while (matcher.find()) {map = new HashMap<String, String>();String idTag = matcher.group(1);String idStr = matcher.group(2);XLog.i("matcher.groupCount() = " + matcher.groupCount() + "; idTag = " + idTag + "; idStr = " + idStr);map.put(idTag, idStr);}return map;}

2.4 创建对象包含歌词相关信息

重写toString()方法输出信息:

public class Lyric {/*** [ar:艺人名]* [ti:曲名]* [al:专辑名]* [by:编者(指编辑LRC歌词的人)]* [offset:时间补偿值] 其单位是毫秒,正值表示整体提前,负值相反。这是用于总体调整显示快慢的。*/private enum idTag {ar, ti, al, by, offset;}private String artist;private String title;private String album;private String bySomebody;private int offset;// [00:35.19] ----对应---> [分钟:秒.毫秒]private List<Map.Entry<Long, String>> lrcList;public Lyric() {lrcList = new ArrayList<>();}public String getArtist() {return artist;}public void setArtist(String artist) {this.artist = artist;}public String getTitle() {return title;}public void setTitle(String title) {this.title = title;}public String getAlbum() {return album;}public void setAlbum(String album) {this.album = album;}public String getBySomebody() {return bySomebody;}public void setBySomebody(String bySomebody) {this.bySomebody = bySomebody;}public int getOffset() {return offset;}public void setOffset(int offset) {this.offset = offset;}public List<Map.Entry<Long, String>> getLrcList() {return lrcList;}public void setLrcList(List<Map.Entry<Long, String>> lrcList) {this.lrcList = lrcList;}public void addLrcMap(Map.Entry<Long, String> map) {lrcList.add(map);}public void set(Map.Entry<String, String> entry) {XLog.i(entry.getKey() + " : " + entry.getValue());String value = entry.getValue();if (value == null || value.trim().length() <= 0) {return;}String key = entry.getKey();if (idTag.ar.toString().equals(key)) {artist = value;} else if (idTag.ti.toString().equals(key)) {title = value;} else if (idTag.al.toString().equals(key)) {album = value;} else if (idTag.by.toString().equals(key)) {bySomebody = value;} else if (idTag.offset.toString().equals(key)) {offset = Integer.parseInt(value);}}@Overridepublic String toString() {String str = "Lyric {" +"artist='" + artist + '\'' +", title='" + title + '\'' +", album='" + album + '\'' +", bySomebody='" + bySomebody + '\'' +", offset=" + offset +", lrcList= {\n";StringBuffer sb = new StringBuffer(str);for (Map.Entry<Long, String> entry : lrcList) {sb.append("\t" + entry.toString() + "\n");}sb.append("\t}\n");return sb + "}";}
}

3、播放显示歌词

JavaFx中监听Service<Lyric>设置text控件

public static class LyricService extends Service<Lyric> {private static LyricService mInstance;private String mPath;private LyricService() {}public static LyricService getInstance() {if (mInstance == null) {synchronized (LyricService.class) {if (mInstance == null) {mInstance = new LyricService();}}}return mInstance;}@Overrideprotected Task<Lyric> createTask() {return new Task<>() {private Lyric mLyric;@Overrideprotected Lyric call() {mLyric = LrcParser.parse(mPath);return mLyric;}};}public void startFindLyricService(AudioFile audioFile) {String ext = audioFile.getExt();String path = audioFile.getFile().getAbsolutePath();path = path.substring(0, path.length() - ext.length()) + "lrc";XLog.i(path);this.startFindLyricService(path);}public void startFindLyricService(String path) {mPath = path;reset();start();}
}

** 相关文献

Java使用正则表达式解析LRC歌词文件 https://www.cnblogs.com/wuqianling/p/5656761.html
lrc歌词文件格式 https://blog.51cto.com/u_13488278/3209754

JavaFX: Java音乐播放读取歌词相关推荐

  1. android音乐播放器之歌词下载、处理、开始、同步

    android音乐播放器之歌词下载.处理.开始.同步 ** 程序源代码在底部 ** 先来看看效果 下载 /*** 自定义下载方法,调用系统DownloadManager下载* * @param myU ...

  2. java播放器使用教程_[Java教程]Java音乐播放器

    [Java教程]Java音乐播放器 0 2016-01-07 12:00:09 乐乐音乐目前是基于musique开发的一个java音乐播放器,之前开发了一个android版本的音乐播放器,现在把and ...

  3. java课程设计-音乐播放器_java课程设计---java音乐播放器.doc

    java课程设计---java音乐播放器 Java程序设计课程设计 题 目 java音乐播放器 学 号: 姓 名: 指导教师: 完成时间: 目 录 第一章 系统概述3 1.需求分析3 1.1任务目的: ...

  4. MoMoPlayer,纯java音乐播放器

    # MoMoPlayer,纯java音乐播放器 # 致我最爱得人 # github源码  :https://github.com/junehappylove/MoMoPlayer # 修改自千里冰封的 ...

  5. javafx音乐播放器----歌词同步实时显示(包含获取酷我歌词方式,歌词同步方法)

    首先我是爬虫获取的酷我的音源,因此歌词也是通过爬虫获取的,下面这个方法可以获取到歌曲对应的歌词信息.简单说下,在搜索歌曲之后会返回一个歌曲列表,查看源代码是包含在li标签里面的,这个li标签里面就有请 ...

  6. java制作音乐播放器教程_教你轻松制作java音乐播放器

    一.音乐播放器的实现原理 Javase的多媒体功能很弱,所以有一个专门处理多媒体的插件叫JMF,JMF提供的模型可大致分为七类 * 数据源(Data source) * 截取设备(Capture De ...

  7. 安卓java音乐播放器下一曲_Android实现简单音乐播放器(MediaPlayer)

    Android实现简单音乐播放器(MediaPlayer),供大家参考,具体内容如下 开发工具:Andorid Studio 1.3 运行环境:Android 4.4 KitKat 工程内容 实现一个 ...

  8. android 音乐播放器-------歌词同步 lrc

    lrc格式 : [al:这首歌所在的唱片集 ] [ar:歌词作者 ] [by:本LRC文件的创建者 ] [offset:+/- 以毫秒为单位整体时间戳调整,+增加,-减小 ] [re:创建此LRC文件 ...

  9. Java音乐播放器设计

    如何使用Java进行音乐播放器的设计? 大三上老师的结课作业,由室友共同合作完成 可以设置背景(动态).歌词(逐行高亮).按照时间进行.上一首.下一首.暂停,选择歌曲等内容均以实现(背景图片和歌曲未放 ...

最新文章

  1. 设计模式之抽象工厂模式(Abstract Factory)摘录
  2. 评审关上了你CVPR的门?这还有Rebuttal的窗,7个小技巧送上
  3. Sratch-gui 中文文档
  4. 终章 | 机器学习笔试题精选
  5. 1.今日标签:视频价值一千字
  6. 程序员上班都在做什么?
  7. Java Stream API进阶篇
  8. win32开发(绘制bitmap)
  9. jsoup教程_1 简介
  10. [置顶]C++求平面最近点对
  11. Openlayer:学习笔记之Source和Layer
  12. 核心Element对象
  13. 两个pv挂一个vg_王者荣耀2020世冠杯小组赛全部结束,TS和AG、QG和E星一个半区
  14. Thinkpad T400 解决PCI 内存控制器设备黄色感叹号问题
  15. typedef用法详解
  16. 软件工程:软件开发生命周期 (SDLC)
  17. Word修改标题样式缩进不起作用原因
  18. 微信引流黑科技:手机浏览器直接唤起微信方案调研
  19. CCF NOI 2022获奖名单
  20. r导入txt乱码_R中导入excel乱码的解决办法

热门文章

  1. 数学建模:图论模型-Floyd算法
  2. excel——宏表函数
  3. 浪叫兽的自我介绍 (完整版) 讲述一段如何进入大数据行业
  4. Python网络编程(06)----MySQL8.0介绍--01(使用command命令创建数据库以及数据表)
  5. wps中最后一页删除方法比较神奇哦!!!
  6. 会声会影2019序列号激活码安装教程
  7. Android Bluetooth杂记
  8. 字符串相似度计算工具和算法
  9. matlab画三维实心圆柱体,怎样用matlab画水平实心圆柱体,已知圆柱体的半径和高度(悬? 爱问知识人...
  10. 黑马程序员——JAVA笔记——单例设计模式