「静听」是我独立开发的一款 iOS 本地音乐播放器,主打无损格式支持、WiFi 传歌、无广告体验。开发一年多了,一直在持续优化。
问题出现在 AVPlayer 的 timeObserver 回调时机处理上。原逻辑在歌曲即将结束时就开始准备循环,导致只播放最后几秒。
解决方案:
// 修复后的逻辑
player.addPeriodicTimeObserver(forInterval: CMTime(seconds: 0.5, preferredTimescale: CMTimeScale(NSEC_PER_SEC)), queue: .main) { [weak self] time in
guard let self = self else { return }
let currentTime = CMTimeGetSeconds(time)
let duration = CMTimeGetSeconds(self.player.currentItem?.duration ?? CMTime.zero)
// 在歌曲结束前 0.1 秒开始准备循环
if duration - currentTime < 0.1 && self.playMode == .singleLoop {
self.seek(to: 0)
self.play()
}
}
iOS 的音频会话管理比较 tricky ,特别是蓝牙设备连接/断开时的状态恢复。
关键代码:
// 监听蓝牙状态变化
NotificationCenter.default.addObserver(
self,
selector: #selector(handleAudioRouteChange),
name: AVAudioSession.routeChangeNotification,
object: nil
)
@objc func handleAudioRouteChange(notification: Notification) {
guard let userInfo = notification.userInfo,
let reasonValue = userInfo[AVAudioSessionRouteChangeReasonKey] as? UInt,
let reason = AVAudioSession.RouteChangeReason(rawValue: reasonValue) else {
return
}
switch reason {
case .newDeviceAvailable: // 新设备可用(如连接蓝牙)
if shouldResumePlayback {
resumePlayback()
}
case .oldDeviceUnavailable: // 旧设备不可用(如断开蓝牙)
pausePlayback()
savePlaybackPosition()
default:
break
}
}
使用 UserDefaults + NotificationCenter 实现状态同步:
// 设置播放模式时
UserDefaults.standard.set(playMode.rawValue, forKey: "currentPlayMode")
NotificationCenter.default.post(name: .playModeChanged, object: playMode)
// 各处监听
NotificationCenter.default.addObserver(
self,
selector: #selector(updatePlayModeUI),
name: .playModeChanged,
object: nil
)
问题:原算法使用了 Array.shuffled(),但在每次切歌时都重新 shuffle ,导致随机性不够。
解决:改为一次性 shuffle 整个播放队列,然后顺序播放。
问题:AVPlayer 的 timeObserver 在某些情况下(如后台播放、网络波动)会停止回调。
解决:增加保活机制,定期检查播放状态,必要时重新添加 observer 。
问题:用户不选择封面时,系统会保存一个占位图,导致不必要的存储。
解决:判断用户是否真的选择了新封面,如果没有,保持原封面或使用默认 App logo 。
做独立开发最有趣的地方就是这些「小修小补」。每个 bug 的修复、每个体验的优化,都能让产品更接近「完美」。
今天修复的这些问题,大多都是用户反馈或自己使用中发现的。有时候一个看似简单的「继续播放」逻辑,背后涉及音频会话管理、状态恢复、用户体验等多个方面。
静听 - 无损音乐播放器 & 本地传歌 App Store: [搜索「静听」即可下载] GitHub: [暂未开源,考虑中]
欢迎交流讨论!
1
huangqihong 7 天前
可以车载吗
|
2
kfj92 OP @huangqihong 暂时不可以,后边会做
|
3
afirefish 7 天前
|
4
ttsh 7 天前
先顺序播放,然后在播放页设置为随机播放,不会变随机,还是顺序
|
6
igofreely 7 天前
网易云音乐有个新功能,一首歌还没放完,下一首歌的声音就开始混进来播放了,「静听」音乐播放器可以加上这个功能。
|
7
bugsnail 7 天前
这么纯粹的嘛,连个链接都不放一个?
|
8
toan 7 天前
👍 这么纯粹的 当今很少见!
|
13
kfj92 OP |
14
kfj92 OP |
15
heziqiang 7 天前
是开源的吗,
发出来大家给你一起修 issue 吧 |
17
tangshanliu 6 天前
刚刚下载了。
如果能直接读取文件,替换现在的文件导入就好了。 我刚刚尝试通过 ios 的文件管理把本地的音乐文档移动到对应的文件夹下没有自动识别。 只能通过首页的文件导入识别。导入后又形成了新的副本,文件名也重新命名了。 文件管理我现在用的是“documents”,各种文件直接通过 ios 的文件移动就可以自动识别管理和打开。 |
18
tangshanliu 6 天前
@kfj92 我倒是觉得静听挺好的。即有致敬“千千静听”感觉,又有一种自己安静的欣赏的感觉,意境非常好。
|
19
kfj92 OP @tangshanliu 后者大致就是我取这个名的本意
|
20
kfj92 OP @tangshanliu documents 很少用,只是下载过,可以加 APP 里边的微信,详聊。
|
21
tangshanliu 5 天前
@huangqihong 车载需要特殊的功能吗?早上试过了,我手机蓝牙连接车载蓝牙音频输入,目前是可用的,播放信息也能同.
|
22
huangqihong 5 天前
@tangshanliu #21 我用的 carplay ,方便看导航还有听歌
|