【问题标题】:swift: audio slider controlswift:音频滑块控件
【发布时间】:2016-01-24 01:47:38
【问题描述】:

问题:

当我转到包含按钮和滑块的视图控制器时,它会使应用程序崩溃并在 slider.maximumValue = Float(audioPlayer.duration) 的行上给我 Thread 1:EXC_BAD_ACCESS (code=1, address=0x38)。在视图控制器中,我有一个播放/暂停按钮、一个停止按钮和一个控制音频播放位置的滑块。

代码:

import UIKit
import AVFoundation

class AgnesAudioViewController: UIViewController {

var audioPlayer = AVAudioPlayer()
var toggleState = 1
@IBOutlet var slider: UISlider!

@IBAction func done(sender: AnyObject) {
    dismissViewControllerAnimated(true, completion: nil)
}

@IBAction func play(sender: AnyObject) {
    audioPlayer.play()
}

@IBAction func pause(sender: AnyObject) {
    audioPlayer.pause()
}

@IBAction func stop(sender: AnyObject) {
    audioPlayer.stop()
}

@IBAction func scrubAudio(sender: AnyObject) {
    audioPlayer.stop()
    audioPlayer.currentTime = NSTimeInterval(slider.value)
    audioPlayer.prepareToPlay()
    audioPlayer.play()
}

@IBAction func playPauseButton(sender: AnyObject) {
    var playBtn = sender as! UIButton
    if toggleState == 1 {
        audioPlayer.play()
        toggleState = 2
        playBtn.setImage(UIImage(named:"pause.png"),forState:UIControlState.Normal)
    } else {
        audioPlayer.pause()
        toggleState = 1
        playBtn.setImage(UIImage(named:"play.png"),forState:UIControlState.Normal)
    }
}

override func viewDidLoad() {
    super.viewDidLoad()

    var timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: Selector("updateSlider"), userInfo: nil, repeats: true)

    slider.maximumValue = Float(audioPlayer.duration)

    let pathString = NSBundle.mainBundle().pathForResource("agnes", ofType: "mp2")

    if let pathString = pathString {

        let pathURL = NSURL(fileURLWithPath: pathString)

        do {

            try audioPlayer = AVAudioPlayer(contentsOfURL: pathURL)

        } catch {

            print("error")
        }


    }

}

func updateSlider() {
    slider.value = Float(audioPlayer.currentTime)
}
}

【问题讨论】:

    标签: swift avaudioplayer uislider


    【解决方案1】:

    这解决了问题:

    import UIKit
    import AVFoundation
    
    class AgnesAudioViewController: UIViewController {
    
    var audioPlayer = AVAudioPlayer()
    var toggleState = 1
    @IBOutlet var slider: UISlider!
    @IBOutlet var playedTime: UILabel!
    
    @IBAction func done(sender: AnyObject) {
        dismissViewControllerAnimated(true, completion: nil)
        audioPlayer.stop()
    }
    
    @IBAction func play(sender: AnyObject) {
        audioPlayer.play()
        updateTime()
    }
    
    @IBAction func pause(sender: AnyObject) {
        audioPlayer.pause()
        updateTime()
    }
    
    @IBAction func stop(sender: AnyObject) {
        audioPlayer.stop()
        updateTime()
    }
    
    @IBAction func scrubAudio(sender: AnyObject) {
        audioPlayer.stop()
        audioPlayer.currentTime = NSTimeInterval(slider.value)
        audioPlayer.prepareToPlay()
        audioPlayer.play()
    }
    
    func updateTime() {
        var currentTime = Int(audioPlayer.currentTime)
        var duration = Int(audioPlayer.duration)
        var total = currentTime - duration
        var totalString = String(total)
    
        var minutes = currentTime/60
        var seconds = currentTime - minutes / 60
    
        playedTime.text = NSString(format: "%02d:%02d", minutes,seconds) as String
    }
    
    @IBAction func playPauseButton(sender: AnyObject) {
        //1 = play
        //2 = pausw
        var playBtn = sender as! UIButton
        if toggleState == 1 {
            audioPlayer.play()
            toggleState = 2
            playBtn.setImage(UIImage(named:"pause2.png"),forState:UIControlState.Normal)
        } else {
            audioPlayer.pause()
            toggleState = 1
            playBtn.setImage(UIImage(named:"play2.png"),forState:UIControlState.Normal)
        }
    }
    
    override func viewDidLoad() {
        super.viewDidLoad()
    
        var updateTimer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: Selector("updateTime"), userInfo: nil, repeats: true)
        var timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: Selector("updateSlider"), userInfo: nil, repeats: true)
    
        let pathString = NSBundle.mainBundle().pathForResource("agnes", ofType: "mp3")
    
        if let pathString = pathString {
    
            let pathURL = NSURL(fileURLWithPath: pathString)
    
            do {
    
                try audioPlayer = AVAudioPlayer(contentsOfURL: pathURL)
    
            } catch {
    
                print("error")
            }
    
    
        }
    
        slider.maximumValue = Float(audioPlayer.duration)
    }
    
    func updateSlider() {
        slider.value = Float(audioPlayer.currentTime)
        }
    }
    

    【讨论】:

    • 那么总数是多少?
    • var seconds = currentTime - minutes / 60 是错误的。应该是 var currentTime - 分钟 * 60
    【解决方案2】:

    对于Hunter回答,没关系,但我会在updateTime 函数中添加一些行。因为这样它不会在标签中显示像 1:61 这样的时间。

        func updateTime() {
        var currentTime = Int(audioPlayer.currentTime)
        var duration = Int(audioPlayer.duration)
        var total = currentTime - duration
        var totalString = String(total)
    
        var minutes = currentTime/60
        var seconds = currentTime - minutes / 60
        if minutes > 0 {
           seconds = seconds - 60 * minutes
        }
    
        playedTime.text = NSString(format: "%02d:%02d", minutes,seconds) as String
    }
    

    【讨论】:

    • 那么总数是多少?
    • @iosMentalist 如果我现在看它可能什么都没有。这段代码可能会更简洁,并且还有一些不必要的计算,对此感到抱歉。写这篇文章后我学到了很多:)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-09
    相关资源
    最近更新 更多