UIKit
ViewController
UIViewController
{
//显示歌曲标题
@IBOutlet
weak
titleLabel:
UILabel
!
//暂停按钮
pauseBtn:
UIButton
!
//可拖动的进度条
playbackSlider:
UISlider
!
//当前播放时间标签
playTime:
UILabel
!
//更新进度条定时器
timer:
Timer
!
//音频播放器
audioPlayer:
STKAudioPlayer
!
//播放列表
queue = [
Music
(name:
"歌曲1"
url:
URL
(string:
"http://mxd.766.com/sdo/music/data/3/m10.mp3"
)!),
"歌曲2"
"http://mxd.766.com/sdo/music/data/3/m12.mp3"
"歌曲3"
"http://mxd.766.com/sdo/music/data/3/m13.mp3"
)!)]
//当前播放音乐索引
currentIndex:
Int
= -1
//是否循环播放
loop:
Bool
=
false
//当前播放状态
state:
STKAudioPlayerState
= []
override
viewDidLoad() {
super
.viewDidLoad()
//设置进度条相关属性
playbackSlider!.minimumValue = 0
playbackSlider!.isContinuous =
false
//重置播放器
resetAudioPlayer()
//开始播放歌曲列表
playWithQueue(queue: queue)
//设置一个定时器,每三秒钟滚动一次
timer =
.scheduledTimer(timeInterval: 0.1,target:
self
selector: #selector(tick),userInfo:
nil
)
}
//重置播放器
resetAudioPlayer() {
options =
STKAudioPlayerOptions
()
options.flushQueueOnSeek =
true
options.enableVolumeMixer =
true
audioPlayer =
(options: options)
audioPlayer.meteringEnabled =
true
audioPlayer.volume = 1
audioPlayer.delegate =
self
}
//开始播放歌曲列表(默认从第一首歌曲开始播放)
playWithQueue(queue: [
],index:
Int
= 0) {
guard index >= 0 && index < queue.count
else
{
return
}
.queue = queue
audioPlayer.clearQueue()
url = queue[index].url
audioPlayer.play(url)
for
i
in
1 ..< queue.count {
audioPlayer.queue(queue[
((index + i) % queue.count)].url)
}
currentIndex = index
loop =
false
}
//停止播放
stop() {
audioPlayer.stop()
queue = []
currentIndex = -1
}
//单独播放某个歌曲
play(file:
) {
audioPlayer.play(file.url)
}
//下一曲
next() {
guard queue.count > 0
{
return
}
currentIndex = (currentIndex + 1) % queue.count
playWithQueue(queue: queue,index: currentIndex)
}
//上一曲
prev() {
currentIndex =
max
(0,currentIndex - 1)
}
//下一曲按钮点击
@IBAction
nextBtnTapped(_ sender:
) {
next()
}
//上一曲按钮点击
prevBtnTapped(_ sender:
) {
prev()
}
//暂停继续按钮点击
pauseBtnTapped(_ sender:
) {
//在暂停和继续两个状态间切换
if
.state == .paused {
audioPlayer.resume()
}
{
audioPlayer.pause()
}
}
//结束按钮点击
stopBtnTapped(_ sender:
) {
stop()
}
//定时器响应,更新进度条和时间
tick() {
if
state == .playing {
//更新进度条进度值
.playbackSlider!.value =
Float
(audioPlayer.progress)
//一个小算法,来实现00:00这种格式的播放时间
all:
=
(audioPlayer.progress)
m:
=all % 60
f:
(all/60)
time:
String
=
""
f<10{
time=
"0(f):"
{
"(f)"
}
m<10{
time+=
"0(m)"
{
"(m)"
}
//更新播放时间
.playTime!.text=time
}
}
//拖动进度条改变值时触发
playbackSliderValueChanged(_ sender:
) {
//播放器定位到对应的位置
audioPlayer.seek(toTime:
Double
(playbackSlider.value))
//如果当前时暂停状态,则继续播放
state == .paused
{
audioPlayer.resume()
}
}
didReceiveMemoryWarning() {
.didReceiveMemoryWarning()
}
}
extension
STKAudioPlayerDelegate
{
//开始播放歌曲
audioPlayer(_ audioPlayer:
didStartPlayingQueueItemId queueItemId:
NSObject
) {
index = (queue.index { $0.url == queueItemId
as
!
}) {
currentIndex = index
}
}
//缓冲完毕
didFinishBufferingSourceWithQueueItemId queueItemId:
) {
updateNowPlayingInfoCenter()
}
//播放状态变化
stateChanged state:
previousState:
) {
.state = state
state != .stopped && state != .error && state != .disposed {
}
updateNowPlayingInfoCenter()
}
//播放结束
didFinishPlayingQueueItemId queueItemId:
with stopReason:
STKAudioPlayerStopReason
andProgress progress:
Double
) {
index = (queue.index {
$0.url == audioPlayer.currentlyPlayingQueueItemId()
URL
}) {
currentIndex = index
}
//自动播放下一曲
stopReason == .eof {
next()
else
stopReason == .error {
stop()
resetAudioPlayer()
}
}
//发生错误
unexpectedError errorCode:
STKAudioPlayerErrorCode
) {
(
"Error when playing music (errorCode)"
)
resetAudioPlayer()
}
//更新当前播放信息
updateNowPlayingInfoCenter() {
currentIndex >= 0 {
music = queue[currentIndex]
//更新标题
titleLabel.text =
"当前播放:(music.name)"
//更新暂停按钮名字
pauseBtnTitle =
.state == .playing ?
"暂停"
:
"继续"
pauseBtn.setTitle(pauseBtnTitle,
: .normal)
//设置进度条相关属性
playbackSlider!.maximumValue =
Float
(audioPlayer.duration)
{
//停止播放
"播放停止!"
//更新进度条和时间标签
playbackSlider.value = 0
playTime.text =
"--:--"
}
}
}
//歌曲类
{
name:
String
URL
//类构造函数
init
(name:
){
.name = name
.url = url
}
}
|