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

为何ResolvedSymbol的size始终与Canvas视图尺寸一致?

为什么GraphicsContext.ResolvedSymbol.size返回Canvas尺寸而非符号自身尺寸?

当在SwiftUI的Canvas中尝试通过GraphicsContext.ResolvedSymbol.size获取已解析符号的边界框尺寸时,会发现返回值始终等于Canvas自身的尺寸,而非符号本身的实际大小。比如示例中符号是300x300的椭圆路径,但size却跟着Canvas的400x350/500x450变化。

原因说明

ResolvedSymbol.size的设计意图并非返回符号的原始边界框,而是返回符号被解析时所处的容器尺寸(即Canvas的当前尺寸)。SwiftUI在解析Canvas的symbols闭包内容时,会默认将符号布局填充到整个Canvas空间,因此该属性会同步Canvas的尺寸。如果需要获取符号自身的原始尺寸,不能依赖这个属性,而是需要在定义符号时手动记录(比如把尺寸存在变量中),或者通过计算路径的boundingRect来获取。

复现输出

canvas size: (400.0, 350.0); symbol size: (400.0, 350.0)
toggled
canvas size: (500.0, 450.0); symbol size: (500.0, 450.0)
toggled
canvas size: (400.0, 350.0); symbol size: (400.0, 350.0)

复现代码

struct ContentView: View {
  @State private var large = false
  var body: some View {
    VStack {
      Button {
        large.toggle()
        print("toggled")
      } label: {
        Text("Toggle Size")
      }
      Spacer()
      Canvas { context, size in
        let s0 = context.resolveSymbol(id: 0)!
        print("canvas size: \(size); symbol size: \(s0.size)")
        context.draw(s0, in: CGRect(origin: .zero, size: size))
      } symbols: {
        Path(ellipseIn: CGRect(origin: .zero, size: CGSize(width: 300, height: 300)))
          .stroke(.green, lineWidth: 10)
          .border(.blue)
          .tag(0)
      }
      .frame(width: large ? 500 : 400, height: large ? 450 : 350)
    }.padding()
  }
}

内容的提问来源于stack exchange,提问作者g i i k

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.24 06:52:12