Swift AVAudioPlayer 不会停止播放歌曲,并且按钮不会在离开 UITable View 时消失

问题描述

过去 2 周我一直在为 2 个问题苦苦挣扎,但还没有找到解决方案,正在开发一个音频播放器,我想在单击 UItableview 单元格或单击里面的按钮播放时播放音频文件按钮 因此,我创建了一个包含音频详细信息的结构,稍后我计划从 mp3 文件提取该结构,例如歌曲名称、艺术家持续时间等。但现在我对这些详细信息进行了硬编码,以便我的主要重点是在单元格点击或按钮上播放歌曲

struct Audio {
    let id: Int
    let trackName: String
    let trackTitle: String
    let creationDate = Date()
    let album: String
    let uploadedBy: String
    let genre: String
    let lyricslang: String
    let artist: String
    let duration: Float
    var completed = false
 }

问题

  1. 如果用户只点击另一个单元格,我想隐藏播放按钮 播放当前歌曲将显示按钮(用于播放或停止)但问题 是按钮显示在单元格的每一行上,如果我点击,我也不想隐藏按钮 再次播放歌曲单元。

  2. 如果用户点击单元格,根据单元格编号,它将始终播放同一首歌曲,我想 根据单元格编号播放 0.mp3、1.mp3、2.mp3、3.mp3 等歌曲,然后停止 如果我在播放下一首歌曲之前尝试停止播放或尝试停止播放,则按钮不起作用 离开牢房 下面是我的全部代码

     class AudioListViewController: UIViewController {
          var selectedRowIndex = -1
          var songList: [Audio] = [
          Audio(id: 0,trackName: "Song 1",trackTitle: "ABbcd:",album: "Loreim loreim",uploadedBy: "A men",genre: "Romantic",lyricslang: "English",artist: "God",duration: 2.00),Audio(id: 1,trackName: "Song 2",Audio(id: 2,trackName: "Song 3",duration: 2.00)
          ]            
          @IBOutlet weak var songListTableView: UITableView!
          var isTapped: Bool = false
          @IBOutlet weak var close: UIButton!
    
          override func viewDidLoad() {
              super.viewDidLoad()
    
              songListTableView.dataSource = self
              songListTableView.delegate = self
              title = "Back"
              navigationItem.backButtonTitle = "Back be?"
    
              songListTableView.register(UINib(nibName:  "SongsListTableViewCell",bundle: 
             nil),forCellReuseIdentifier: "SongListCell")
         }
    
         @IBAction func closeSe(_ sender: Any) {
              self.dismiss(animated: true,completion: nil)
         }
    
      }
      extension AudioListViewController: UITableViewDataSource {
            func tableView(_ tableView: UITableView,numberOfRowsInSection section: Int) -> 
            Int {
                 return songList.count
             }
    
             func tableView(_ tableView: UITableView,cellForRowAt indexPath: IndexPath) -> 
               UITableViewCell {
                  let cell = tableView.dequeueReusableCell(withIdentifier: "SongListCell",for: indexPath) as! SongsListTableViewCell
    
             cell.songTitle?.text = songList[indexPath.row].trackName
             cell.songDuration?.text = String(songList[indexPath.row].duration)
             return cell
          }
        }
    
        extension AudioListViewController: UITableViewDelegate{
             func tableView(_ tableView: UITableView,didSelectRowAt indexPath: IndexPath) {
                  tableView.deselectRow(at: indexPath,animated: true)
                  let position = indexPath.row
    
                  print(indexPath.row)
                  let vc = tableView.dequeueReusableCell(withIdentifier: "SongListCell",for: 
          indexPath)
             as! SongsListTableViewCell
    
         vc.songs = songList
         vc.position = position
    
         let selectedFilterRow = songList[indexPath.section].id
         if selectedFilterRow == indexPath.row {
            return
         }
    
         if let prevIoUsCell = tableView.cellForRow(at: IndexPath(row: selectedFilterRow,section: indexPath.section)) {
               vc.useSong.isHidden = true
               vc.useSong.alpha = 0
               vc.stopSong()
         }
    
         if let cell = tableView.cellForRow(at: indexPath) {
               vc.useSong.isHidden = true
               vc.useSong.alpha = 0
               vc.stopSong()
               vc.configure(position: position)
          }
         }
       }
    

现在可以点击获取歌曲文件名,以及单元格的其他功能

     class SongsListTableViewCell: UITableViewCell {

        public var songs: [Audio] = [
            Audio(id: 0,artist: 
               "God",duration: 2.00) ]

            public var position: Int = 0
            public var isPlaying: Bool = false
            var cellsstate: Bool = false
            var songPlayer: AVAudioPlayer?

            @IBOutlet weak var singleViewCell: UIStackView!
            @IBOutlet weak var songCellView: UIView!
            @IBOutlet weak var songImage: UIImageView!
            @IBOutlet weak var songTitle: UILabel!
            @IBOutlet weak var songDuration: UILabel!
            @IBOutlet weak var makeFavorite: UIButton!
            @IBOutlet weak var useSong: UIButton!

            let songReoad: AudioListViewController! = nil

            override func awakeFromNib() {
               super.awakeFromNib()
               useSong.addTarget(self,action: 
                 #selector(SongsListTableViewCell.selectSong(_:)),for: .touchUpInside)
               makeFavorite.addTarget(self,action: 
                 #selector(SongsListTableViewCell.makeFavourite(_:)),for: .touchUpInside )
                useSong.isHidden = true
           }

           private let albumNameLabel: UILabel = {
               let label = UILabel()
               label.textAlignment = .center
               label.numberOfLines = 0 // line wrap
               return label
           }()

           private let artistNameLabel: UILabel = {
               let label = UILabel()
               label.textAlignment = .center
               label.numberOfLines = 0 // line wrap
               return label
           }()
           override func setSelected(_ selected: Bool,animated: Bool) {
               super.setSelected(selected,animated: animated)
               useSong.layer.cornerRadius = 6
               configure(position: self.position)
           }

           func configure(position:Int) {
  
              let song = songs[position]  
              let songId = String(song.id)
              let urlString = Bundle.main.path(forResource: songId,ofType: "mp3")
    
  
              do {
                 try AVAudioSession.sharedInstance().setMode(.default)
                 try AVAudioSession.sharedInstance().setActive(true,options: 
                   .notifyOthersOnDeactivation)
                 guard let urlString = urlString else {
                    return
                 }

                 songPlayer = try AVAudioPlayer(contentsOf: URL(string: urlString)!)
                 guard let player = songPlayer else {
                    return
                 }
                 player.volume = 0.5

                 player.play()
                 isPlaying = true
             }
              catch {
                  print("error occurred")
             }

             songTitle.text = song.trackName
             albumNameLabel.text = song.album

            
              // Frame
              let yPosition = artistNameLabel.frame.origin.y + 70 + 20
              let size: CGFloat = 70

               backButton.frame = CGRect(x: 20,y: yPosition,width: size,height: size)

               // Add actions
               makeFavorite.addTarget(self,action: #selector(didTapPlayPauseButton),for: 
                 .touchUpInside)
               
           }

           func stopSong(){
              if let player = songPlayer {
                 player.stop()
              }else{
                 songPlayer?.stop()
              }
           }

           @IBAction func selectSong(_ sender: UIButton) {
                cellsstate = !cellsstate
                songPlayer?.stop()
                if (cellsstate) {
                    useSong.isHidden = false
                    useSong.alpha = 1
                    UIView.animate(withDuration: 0.6,animations: {
                           self.useSong.transform = CGAffineTransform(scaleX: 0.6,y: 0.6)
                     },completion: { _ in
                         UIView.animate(withDuration: 0.6) {
                            self.useSong.transform = CGAffineTransform.identity
                      }
                  })
               } else {
                    useSong.isHidden = true
                    useSong.alpha = 0
             }
         }

          @IBAction func makeFavourite(_ sender: UIButton) {
              sender.isSelected = !sender.isSelected
              if sender.isSelected {
                  makeFavorite.setimage(UIImage(systemName: "star.fill"),for: .normal)
              } else {
                   makeFavorite.setimage(UIImage(systemName: "star"),for: .normal)
              }
           }

 
           @objc func didTapPlayPauseButton() {
                if songPlayer?.isPlaying == true {
                   // pause
                   songPlayer?.pause()
                }
                else {
                   // play
                  songPlayer?.play()
                }
             }
       }

这就是它现在的样子 SongList view

这是我的 Songlistview songlistview

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)