You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift如何将JSON API解析的图片URL加载到UIImageView并实现数据更新

问题原因分析
  • 原有错误代码存在两个核心问题:
    1. 你直接用拉取电台API返回的JSON数据来初始化UIImage,这个data是JSON格式的接口返回值,不是图片的二进制数据,自然无法生成有效图片
    2. 你新建的UIImageView没有添加到当前视图的层级中,也没有设置布局约束和展示属性,就算生成了图片也不会显示
  • 额外你还需要解决定时拉取API更新播放信息的需求,避免重启应用才能刷新数据

实现步骤

1. 提前配置专辑封面UIImageView

首先在你的ViewController中添加专辑封面的IBOutlet(用Storyboard/XIB的话直接拖线关联,纯代码就手动创建),同时新增定时刷新用的计时器属性:

//  MARK: - 界面元素
@IBOutlet weak var albumArtImageView: UIImageView!
// 定时刷新用的计时器
var refreshTimer: Timer?

然后在viewDidLoad中配置UIImageView的展示模式,同时启动定时刷新逻辑:

override func viewDidLoad() {
    super.viewDidLoad()
    // 保留你的原有配置
    overrideUserInterfaceStyle = .light
    setupRemoteCommandCenter()
    
    // 配置图片展示模式为Aspect Fill,且裁剪超出边界的内容
    albumArtImageView.contentMode = .scaleAspectFill
    albumArtImageView.clipsToBounds = true
    
    // 启动定时刷新,间隔可以自己调整,单位是秒,这里设30秒拉一次
    refreshTimer = Timer.scheduledTimer(timeInterval: 30, target: self, selector: #selector(fetchNowPlayingData), userInfo: nil, repeats: true)
    // 启动后先主动拉一次初始数据
    fetchNowPlayingData()
}

2. 封装拉取播放数据的方法

把原来写在viewDidLoad里的网络请求封装成独立方法,方便定时器重复调用:

// MARK: - 数据拉取
@objc func fetchNowPlayingData() {
    let urlString = "https://radioapp.com/api/nowplaying/radioapp"
    guard let url = URL(string: urlString) else { return }
    URLSession.shared.dataTask(with: url) { [weak self] data, response, error in
        guard let self = self, error == nil, let data = data else {
            print(error ?? "返回数据为空")
            return
        }
        do {
            let radio = try JSONDecoder().decode(RadioAPI.self, from: data)
            DispatchQueue.main.async {
                self.songtitle.text = radio.nowPlaying.song.title
                self.artist.text = radio.nowPlaying.song.artist
                // 加载对应专辑封面
                self.loadAlbumArt(urlString: radio.nowPlaying.song.art)
            }
        } catch {
            print("JSON解析错误: \(error)")
        }
    }.resume()
}

3. 实现专辑封面加载方法

单独处理图片的网络请求,避免阻塞主线程:

// MARK: - 图片加载
func loadAlbumArt(urlString: String) {
    guard let artUrl = URL(string: urlString) else { return }
    // 后台线程拉取图片数据
    DispatchQueue.global().async { [weak self] in
        if let imageData = try? Data(contentsOf: artUrl), let albumImage = UIImage(data: imageData) {
            DispatchQueue.main.async {
                // 回到主线程赋值展示图片
                self?.albumArtImageView.image = albumImage
            }
        }
    }
}

可选优化

如果需要图片缓存、加载失败占位图、加载进度提示等功能,也可以引入成熟的第三方图片加载库,调用对应API即可实现更稳定的图片加载效果。

内容的提问来源于stack exchange,提问作者LewTrocki

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.03 22:48:02