如何在值更改时防止SwiftUI Text抖动并在小数点两侧格式化双精度值?
How to prevent SwiftUI Text from shaking when value changes and format double value both sides of the decimal point?
我有一个倒数计时器。当数字不断变化时,文字水平移动,感觉晃动太多了,因为我每 0.1 秒更新一次计时器。
如何防止文字抖动?这是完整的代码:
struct CountDownTimerView: View {
@ObservedObject var timer = CountdownTimer(seconds: 15)
var body: some View {
Text(String(format: "%.1f", timer.time))
.font(Font.system(size: 144).weight(.light))
}
}
class CountdownTimer: ObservableObject {
@Published var time: Double
/// time interval in seconds
let interval = 0.1
lazy var timer = Timer.scheduledTimer(withTimeInterval: interval, repeats: true) { _ in
self.update()
}
init(seconds: Double) {
time = seconds
timer.fire()
}
func update() {
if self.time-interval <= 0 {
self.time = 0
timer.invalidate()
} else {
self.time -= interval
}
}
}
我想将时间显示为双精度值 7.329523 和 07.3。我可以使用 String(format: "%02d", Int(timer.time))
实现小数点前的格式化,如“07”,或使用 (String(format: "%.1f", timer.time)
的小数点后,如“7.3”。如何格式化小数点两边?
您应该尝试使用每个字符间距相等的字体,通常称为等宽字体。
我找到了两种使用 SwiftUI 实现此目的的方法:
等宽字体
将字体的设计更改为等宽。这将影响文本的外观,因为它使用了不同的字体设计。
.font(Font.system(size: 144, design: .monospaced).weight(.light))
自适应字体
另一种更好的方法是将您当前的字体调整为等宽数字。您可以这样做:
.font(Font.monospacedDigit(Font.system(size: 144).weight(.light))())
就是这样(你必须给出前缀为 0 的输出的全宽度,所以 [0 7 . 3] 是四个字符,因此:
let value: CGFloat = 7.329523
Text(String(format: "%04.1f", value))
输出
测试 Xcode 12
我有一个倒数计时器。当数字不断变化时,文字水平移动,感觉晃动太多了,因为我每 0.1 秒更新一次计时器。
如何防止文字抖动?这是完整的代码:
struct CountDownTimerView: View {
@ObservedObject var timer = CountdownTimer(seconds: 15)
var body: some View {
Text(String(format: "%.1f", timer.time))
.font(Font.system(size: 144).weight(.light))
}
}
class CountdownTimer: ObservableObject {
@Published var time: Double
/// time interval in seconds
let interval = 0.1
lazy var timer = Timer.scheduledTimer(withTimeInterval: interval, repeats: true) { _ in
self.update()
}
init(seconds: Double) {
time = seconds
timer.fire()
}
func update() {
if self.time-interval <= 0 {
self.time = 0
timer.invalidate()
} else {
self.time -= interval
}
}
}
我想将时间显示为双精度值 7.329523 和 07.3。我可以使用 String(format: "%02d", Int(timer.time))
实现小数点前的格式化,如“07”,或使用 (String(format: "%.1f", timer.time)
的小数点后,如“7.3”。如何格式化小数点两边?
您应该尝试使用每个字符间距相等的字体,通常称为等宽字体。
我找到了两种使用 SwiftUI 实现此目的的方法:
等宽字体
将字体的设计更改为等宽。这将影响文本的外观,因为它使用了不同的字体设计。
.font(Font.system(size: 144, design: .monospaced).weight(.light))
自适应字体
另一种更好的方法是将您当前的字体调整为等宽数字。您可以这样做:
.font(Font.monospacedDigit(Font.system(size: 144).weight(.light))())
就是这样(你必须给出前缀为 0 的输出的全宽度,所以 [0 7 . 3] 是四个字符,因此:
let value: CGFloat = 7.329523
Text(String(format: "%04.1f", value))
输出
测试 Xcode 12