【发布时间】:2022-12-19 02:03:35
【问题描述】:
我在 macOS 上的 SwiftUI 中有一个项目,我每秒在画布上绘制两次。
这是我的ContentView:
struct ContentView: view {
@State var score: Int = 0
var body: some View {
VStack {
Text("Score: \(self.score)")
.fixedSize(horizontal: true, vertical: true)
Canvas(renderer: { gc, size in
start(
gc: &gc,
size: size
onPoint: { newScore in
self.score = newScore
}
)
)
}
}
}
start 函数:
var renderer: Renderer
func start(
gc: inout GraphicsContext,
size: size,
onPoint: @escaping (Int) -> ()
) {
if renderer != nil {
renderer!.set(gc: &gc)
} else {
renderer = Renderer(
context: &gc,
canvasSize: size,
onPoint: onPoint
)
startGameLoop(renderer: renderer!)
}
renderer!.drawFrame()
}
var timer: Timer
func startGameLoop(renderer: Renderer) {
timer = Timer.scheduledTimer(withTimeInterval: 0.5, repeats: true, block: {
renderer!.handleNextFrame()
}
}
渲染器大致如下所示:
class Renderer {
var gc: GraphicsContext
var size: CGSize
var cellSize: CGFloat
let pointCallback: (Int) -> ()
var player: (Int, Int) = (0,0)
init(
context: inout GraphicsContext,
canvasSize: CGSize,
onPoint: (Int) -> ()
) {
self.gc = gc
self.size = canvasSize
self.pointCallback = onPoint
self.cellSize = min(self.size.width, self.size.height)
}
}
extension Renderer {
func handleNextFrame() {
self.player = (self.player.0 + 1, self.player.1 + 1)
self.drawFrame
}
func drawFrame() {
self.gc.fill(
Path(
x: CGFloat(self.player.0) * self.cellSize,
y: CGFloat(self.player.1) * self.cellSize,
width: self.cellSize,
height: self.cellSize
)
)
}
}
所以handleNextFrame方法每秒被调用两次,即调用drawFrame方法,将player的位置绘制到画布上。
但是,画布上没有绘制任何内容。
只绘制第一帧,来自start中的renderer!.drawFrame()。当得分时,画布也会重新绘制,因为 start 函数被再次调用。
问题是当从 handleNextFrame 调用 drawFrame 时,Canvas 没有绘制任何东西。
我的问题在哪里,我该如何解决这个问题?
提前致谢,
乔纳斯
【问题讨论】:
-
嘿,你能解决这个问题吗?如果你这样做了,你介意分享它作为答案吗?谢谢
标签: swift macos canvas swiftui