Swift View中实现点击切换图标的Button技术咨询
SwiftUI按钮点击无法切换图标问题解决
问题描述
想在SwiftUI View中实现一个点击切换图标的Button,已确认点击按钮时my_player.isPlaying会在true和false之间切换,但当前代码始终显示pause图标。此前在ViewController中用IBOutlet实现过类似功能,首次编写SwiftUI代码遇到图标不更新的问题。
原代码片段:
struct myview: View { @EnvironmentObject var my_player: MusicPlayer var body: some View { let play_icon = UIImage(imageLiteralResourceName: "play.png") let pause_icon = UIImage(imageLiteralResourceName: "pause.png") let button_size : CGFloat = 60 VStack { Button(action: { my_player.play_pause_music() }) { HStack { Image(uiImage: my_player.isPlaying ? pause_icon : play_icon) .resizable() .scaledToFit() .frame(width: button_size) } } } } }
解决建议
确保
isPlaying是响应式属性:SwiftUI依赖ObservableObject的@Published标记来感知属性变化并触发View重绘。检查你的MusicPlayer类,必须将isPlaying标记为@Published,否则即使值变化,View也不会更新。示例:class MusicPlayer: ObservableObject { @Published var isPlaying = false func play_pause_music() { isPlaying.toggle() // 这里添加实际的播放/暂停逻辑 } }优化资源定义位置:将图片资源和按钮尺寸的定义移到
body外部,避免每次View重绘时重复创建对象,提升性能同时让代码更规范:struct MyView: View { // Swift类型名规范首字母大写 @EnvironmentObject var my_player: MusicPlayer private let playIcon = UIImage(imageLiteralResourceName: "play.png") private let pauseIcon = UIImage(imageLiteralResourceName: "pause.png") private let buttonSize: CGFloat = 60 var body: some View { VStack { Button(action: { my_player.play_pause_music() }) { Image(uiImage: my_player.isPlaying ? pauseIcon : playIcon) .resizable() .scaledToFit() .frame(width: buttonSize) } } } }确认环境对象已正确注入:确保你已经在View层级的根节点通过
.environmentObject(_:)注入了MusicPlayer的实例,比如:// 在SceneDelegate或App入口处 let player = MusicPlayer() let contentView = MyView().environmentObject(player)
内容的提问来源于stack exchange,提问作者UpNorth
相关产品推荐
相关产品推荐

