在 Swift/SwiftUI 中更改十进制数的字体大小
Posted
技术标签:
【中文标题】在 Swift/SwiftUI 中更改十进制数的字体大小【英文标题】:change the fontsize of the decimal number in Swift/ SwiftUI 【发布时间】:2021-08-26 09:10:34 【问题描述】:所以我需要使小数位小于实际数字,我将在下面告诉你我的意思。
这是我的代码:
import SwiftUI
struct BalanceDetailsView: View
//MARK: - PROPERTIES
var balance: Float
var balanceString: String
return balance.formattedWithSeparator
//MARK: - BODY
var body: some View
VStack
HStack
Text(balanceString)
.font(.custom(K.fonts.gilroyBold, size: 24))
.multilineTextAlignment(.center)
.padding(.top)
//:VSTACK
//:HSTACK
struct BalanceDetailsView_Previews: PreviewProvider
static var previews: some View
BalanceDetailsView(balance: 43678)
.previewLayout(.sizeThatFits)
//Formatter extension i used to get this code
extension Formatter
static let withSeparator: NumberFormatter =
let formatter = NumberFormatter()
formatter.numberStyle = .decimal
// minimum decimal digit, eg: to display 2 as 2.00
formatter.minimumFractionDigits = 2
// maximum decimal digit, eg: to display 2.5021 as 2.50
formatter.maximumFractionDigits = 2
return formatter
()
extension Numeric
var formattedWithSeparator: String Formatter.withSeparator.string(for: self) ?? ""
Result I get | Result I need |
---|---|
【问题讨论】:
【参考方案1】:当您知道字符串的确切格式时,例如在这种情况下最小字符串长度为 4("0.00") ,您可以安全地使用 dropLast
和 dropFirst
。
我建议将 2
移动到 priceFractionDigits
常量以减少代码中常量的使用。
然后你可以使用字符串连接,它会根据基线对齐Text
。
struct BalanceText: View
var balance: Float
var balanceString: String
return balance.formattedWithSeparator
var body: some View
Text(balanceString.dropLast(priceFractionDigits))
.font(.system(size: 24))
+
Text(balanceString.dropFirst(balanceString.count - priceFractionDigits))
.font(.system(size: 18))
private let priceFractionDigits = 2
extension Formatter
static let withSeparator: NumberFormatter =
let formatter = NumberFormatter()
formatter.numberStyle = .decimal
// minimum decimal digit, eg: to display 2 as 2.00
formatter.minimumFractionDigits = priceFractionDigits
// maximum decimal digit, eg: to display 2.5021 as 2.50
formatter.maximumFractionDigits = priceFractionDigits
return formatter
()
用法
BalanceText(balance: balance)
【讨论】:
【参考方案2】:这是在 SwiftUI 3(ios 15、macOS 12 等)中使用新 AttributedString
的示例
var balanceString: AttributedString
var attributedString = AttributedString(balance.formattedWithSeparator)
guard let separator = Formatter.withSeparator.decimalSeparator else return attributedString
if let range = attributedString.range(of: separator)
attributedString[attributedString.startIndex...attributedString.index(beforeCharacter: range.lowerBound)]
.font = Font.largeTitle
attributedString[attributedString.index(afterCharacter: range.lowerBound)..<attributedString.endIndex]
.font = Font.caption
return attributedString
我在这里使用了一些内置字体样式,但应该很容易替换。另请注意,由于我们在此处设置了.font
属性,因此应将其从Text
中删除
【讨论】:
【参考方案3】:您可以将Text
与+
运算符连接在一起。
我稍微改变了您使用 NumberFormatter
的方式,所以它被区域设置的正确十进制字符分割。
struct BalanceDetailsView: View
private let wholeNumberPart: String
private let decimalNumberPart: String
init(balance: Double)
(wholeNumberPart, decimalNumberPart) = balance.formattedSplittingBySeparator
var body: some View
Text(wholeNumberPart).font(.system(size: 24)) +
Text(decimalNumberPart).font(.system(size: 16))
extension Numeric
var formattedSplittingBySeparator: (whole: String, decimal: String)
let formatter = NumberFormatter()
formatter.numberStyle = .decimal
formatter.minimumFractionDigits = 2
formatter.maximumFractionDigits = 2
let str = formatter.string(for: self) ?? "0\(formatter.decimalSeparator!)00"
let split = str.components(separatedBy: formatter.decimalSeparator)
let whole = (split.first ?? "0") + formatter.decimalSeparator
let decimal = split.count == 2 ? split[1] : "00"
return (whole: whole, decimal: decimal)
用法:
BalanceDetailsView(balance: 43678)
结果:
【讨论】:
【参考方案4】:您可以用小数分隔符分割字符串,并以零间距 HStack
显示各个部分。
struct BalanceView : View
let balance : Float
var body: some View
let components = balance
.formattedWithSeparator
.components(separatedBy: Formatter.withSeparator.decimalSeparator)
HStack(alignment: .firstTextBaseline, spacing: 0)
Text(components[0])
if components.count > 1
Text(".")
Text(components[1])
.font(.title)
.font(.largeTitle)
.multilineTextAlignment(.center)
.padding(.top)
用您的自定义字体替换字体
在你的环境中你可以使用它
struct BalanceDetailsView: View
//MARK: - PROPERTIES
var balance: Float
//MARK: - BODY
var body: some View
VStack
BalanceView(balance: balance)
//:VSTACK
【讨论】:
以上是关于在 Swift/SwiftUI 中更改十进制数的字体大小的主要内容,如果未能解决你的问题,请参考以下文章
如何让 TextField 值更改触发 SwiftUI 中另一条数据的更新?
在 Swift 5/Swiftui 中重构 MapView(没有 Coordinators / UIViewRepresentables)