///|
///|
fn format_index(labels : Array[String], value : Double) -> String {
if labels.length() == 0 || value.is_nan() || value.is_inf() {
return ""
}
let index = value.round().to_int()
if Double::abs(value - Double::from_int(index)) > 1.0e-10 ||
index < 0 ||
index >= labels.length() {
""
} else {
labels[index]
}
}
///|
fn format_str_method(format : String, value : Double) -> String {
format_str_method_at(format, value, 0)
}
///|
fn format_str_method_at(
format : String,
value : Double,
position : Int32,
) -> String {
let chars = format.to_array()
let result = StringBuilder()
let mut index = 0
while index < chars.length() {
if chars[index] == '{' &&
index + 1 < chars.length() &&
chars[index + 1] == '{' {
result.write_char('{')
index += 2
continue
}
if chars[index] == '}' &&
index + 1 < chars.length() &&
chars[index + 1] == '}' {
result.write_char('}')
index += 2
continue
}
if chars[index] != '{' {
result.write_char(chars[index])
index += 1
continue
}
let start = index + 1
let mut close : Int32? = None
let mut cursor = start
while cursor < chars.length() {
if chars[cursor] == '}' {
close = Some(cursor)
break
}
cursor += 1
}
match close {
None => {
result.write_char('{')
index += 1
}
Some(end) => {
let token = String::from_array(chars[start:end])
let rendered = format_method_token(token, value, position)
if rendered == "" && token != "x" && token != "value" && token != "pos" {
for original in (start - 1)..<=end {
result.write_char(chars[original])
}
} else {
result.write_string(rendered)
}
index = end + 1
}
}
}
result.to_string()
}
///|
fn format_method_token(
token : String,
value : Double,
position : Int32,
) -> String {
if token == "x" || token == "value" {
return format_general(value, None, false)
}
if token == "pos" {
return position.to_string()
}
if token.has_prefix("x:") || token.has_prefix("value:") {
let spec_start = if token.has_prefix("x:") { 2 } else { 6 }
let spec = String::unsafe_substring(
token,
start=spec_start,
end=token.length(),
)
return format_method_spec(spec, value)
}
if token.has_prefix("pos:") {
let spec = String::unsafe_substring(token, start=4, end=token.length())
return format_method_spec(spec, Double::from_int(position))
}
""
}
///|
fn format_method_spec(spec : String, value : Double) -> String {
if spec == "" {
return format_general(value, None, false)
}
if spec.has_prefix("%") {
format_printf(spec, value)
} else {
format_printf("%" + spec, value)
}
}