rui_orig/propertySet.go

885 lines
23 KiB
Go
Raw Permalink Normal View History

2021-09-07 17:36:50 +03:00
package rui
import (
"math"
"strconv"
"strings"
)
2024-11-13 12:56:39 +03:00
var colorProperties = []PropertyName{
ColorTag,
2021-09-07 17:36:50 +03:00
BackgroundColor,
TextColor,
CaretColor,
2021-09-07 17:36:50 +03:00
BorderColor,
BorderLeftColor,
BorderRightColor,
BorderTopColor,
BorderBottomColor,
OutlineColor,
TextLineColor,
ColorPickerValue,
AccentColor,
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func isPropertyInList(tag PropertyName, list []PropertyName) bool {
2021-09-07 17:36:50 +03:00
for _, prop := range list {
if prop == tag {
return true
}
}
return false
}
2024-11-13 12:56:39 +03:00
var angleProperties = []PropertyName{
2022-04-30 12:13:16 +03:00
From,
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
var boolProperties = []PropertyName{
2021-09-07 17:36:50 +03:00
Disabled,
Focusable,
2021-09-07 17:36:50 +03:00
Inset,
BackfaceVisible,
ReadOnly,
EditWrap,
2021-09-07 17:36:50 +03:00
Spellcheck,
CloseButton,
OutsideClose,
Italic,
SmallCaps,
Strikethrough,
Overline,
Underline,
Expanded,
AvoidBreak,
NotTranslate,
Controls,
Loop,
Muted,
AnimationPaused,
2021-11-04 14:59:25 +03:00
Multiple,
2021-11-17 12:32:37 +03:00
TabCloseButton,
2022-04-30 12:13:16 +03:00
Repeating,
UserSelect,
2023-01-03 14:56:57 +03:00
ColumnSpanAll,
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
var intProperties = []PropertyName{
2021-09-07 17:36:50 +03:00
ZIndex,
2022-08-20 20:05:56 +03:00
TabSize,
2021-09-07 17:36:50 +03:00
HeadHeight,
FootHeight,
RowSpan,
ColumnSpan,
ColumnCount,
2022-12-18 18:37:36 +03:00
Order,
2022-12-20 18:38:39 +03:00
TabIndex,
2024-11-13 12:56:39 +03:00
MaxLength,
NumberPickerPrecision,
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
var floatProperties = map[PropertyName]struct{ min, max float64 }{
2022-04-21 18:22:17 +03:00
Opacity: {min: 0, max: 1},
2021-09-07 17:36:50 +03:00
NumberPickerMax: {min: -math.MaxFloat64, max: math.MaxFloat64},
NumberPickerMin: {min: -math.MaxFloat64, max: math.MaxFloat64},
NumberPickerStep: {min: -math.MaxFloat64, max: math.MaxFloat64},
NumberPickerValue: {min: -math.MaxFloat64, max: math.MaxFloat64},
ProgressBarMax: {min: 0, max: math.MaxFloat64},
ProgressBarValue: {min: 0, max: math.MaxFloat64},
VideoWidth: {min: 0, max: 10000},
VideoHeight: {min: 0, max: 10000},
}
2024-11-13 12:56:39 +03:00
var sizeProperties = map[PropertyName]string{
Width: string(Width),
Height: string(Height),
MinWidth: string(MinWidth),
MinHeight: string(MinHeight),
MaxWidth: string(MaxWidth),
MaxHeight: string(MaxHeight),
Left: string(Left),
Right: string(Right),
Top: string(Top),
Bottom: string(Bottom),
2021-09-07 17:36:50 +03:00
TextSize: "font-size",
2024-11-13 12:56:39 +03:00
TextIndent: string(TextIndent),
LetterSpacing: string(LetterSpacing),
WordSpacing: string(WordSpacing),
LineHeight: string(LineHeight),
2021-09-07 17:36:50 +03:00
TextLineThickness: "text-decoration-thickness",
ListRowGap: "row-gap",
ListColumnGap: "column-gap",
2024-11-13 12:56:39 +03:00
GridRowGap: string(GridRowGap),
GridColumnGap: string(GridColumnGap),
ColumnWidth: string(ColumnWidth),
ColumnGap: string(ColumnGap),
Gap: string(Gap),
Margin: string(Margin),
MarginLeft: string(MarginLeft),
MarginRight: string(MarginRight),
MarginTop: string(MarginTop),
MarginBottom: string(MarginBottom),
Padding: string(Padding),
PaddingLeft: string(PaddingLeft),
PaddingRight: string(PaddingRight),
PaddingTop: string(PaddingTop),
PaddingBottom: string(PaddingBottom),
BorderWidth: string(BorderWidth),
BorderLeftWidth: string(BorderLeftWidth),
BorderRightWidth: string(BorderRightWidth),
BorderTopWidth: string(BorderTopWidth),
BorderBottomWidth: string(BorderBottomWidth),
OutlineWidth: string(OutlineWidth),
OutlineOffset: string(OutlineOffset),
XOffset: string(XOffset),
YOffset: string(YOffset),
BlurRadius: string(BlurRadius),
SpreadRadius: string(SpreadRadius),
Perspective: string(Perspective),
PerspectiveOriginX: string(PerspectiveOriginX),
PerspectiveOriginY: string(PerspectiveOriginY),
TransformOriginX: string(TransformOriginX),
TransformOriginY: string(TransformOriginY),
TransformOriginZ: string(TransformOriginZ),
2024-11-13 12:56:39 +03:00
Radius: string(Radius),
RadiusX: string(RadiusX),
RadiusY: string(RadiusY),
RadiusTopLeft: string(RadiusTopLeft),
RadiusTopLeftX: string(RadiusTopLeftX),
RadiusTopLeftY: string(RadiusTopLeftY),
RadiusTopRight: string(RadiusTopRight),
RadiusTopRightX: string(RadiusTopRightX),
RadiusTopRightY: string(RadiusTopRightY),
RadiusBottomLeft: string(RadiusBottomLeft),
RadiusBottomLeftX: string(RadiusBottomLeftX),
RadiusBottomLeftY: string(RadiusBottomLeftY),
RadiusBottomRight: string(RadiusBottomRight),
RadiusBottomRightX: string(RadiusBottomRightX),
RadiusBottomRightY: string(RadiusBottomRightY),
ItemWidth: string(ItemWidth),
ItemHeight: string(ItemHeight),
CenterX: string(CenterX),
CenterY: string(CenterX),
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
var enumProperties = map[PropertyName]struct {
2021-09-07 17:36:50 +03:00
values []string
cssTag string
cssValues []string
}{
Semantics: {
[]string{"default", "article", "section", "aside", "header", "main", "footer", "navigation", "figure", "figure-caption", "button", "p", "h1", "h2", "h3", "h4", "h5", "h6", "blockquote", "code"},
"",
[]string{"div", "article", "section", "aside", "header", "main", "footer", "nav", "figure", "figcaption", "button", "p", "h1", "h2", "h3", "h4", "h5", "h6", "blockquote", "code"},
},
Visibility: {
[]string{"visible", "invisible", "gone"},
2022-03-31 19:59:10 +03:00
"",
2021-09-07 17:36:50 +03:00
[]string{"visible", "invisible", "gone"},
},
2022-07-27 13:26:36 +03:00
Overflow: {
[]string{"hidden", "visible", "scroll", "auto"},
2024-11-13 12:56:39 +03:00
string(Overflow),
2022-07-27 13:26:36 +03:00
[]string{"hidden", "visible", "scroll", "auto"},
},
2021-09-07 17:36:50 +03:00
TextAlign: {
[]string{"left", "right", "center", "justify"},
2024-11-13 12:56:39 +03:00
string(TextAlign),
2021-09-07 17:36:50 +03:00
[]string{"left", "right", "center", "justify"},
},
TextTransform: {
[]string{"none", "capitalize", "lowercase", "uppercase"},
2024-11-13 12:56:39 +03:00
string(TextTransform),
2021-09-07 17:36:50 +03:00
[]string{"none", "capitalize", "lowercase", "uppercase"},
},
TextWeight: {
[]string{"inherit", "thin", "extra-light", "light", "normal", "medium", "semi-bold", "bold", "extra-bold", "black"},
"font-weight",
[]string{"inherit", "100", "200", "300", "normal", "500", "600", "bold", "800", "900"},
},
WhiteSpace: {
[]string{"normal", "nowrap", "pre", "pre-wrap", "pre-line", "break-spaces"},
2024-11-13 12:56:39 +03:00
string(WhiteSpace),
2021-09-07 17:36:50 +03:00
[]string{"normal", "nowrap", "pre", "pre-wrap", "pre-line", "break-spaces"},
},
WordBreak: {
[]string{"normal", "break-all", "keep-all", "break-word"},
2024-11-13 12:56:39 +03:00
string(WordBreak),
2021-09-07 17:36:50 +03:00
[]string{"normal", "break-all", "keep-all", "break-word"},
},
TextOverflow: {
[]string{"clip", "ellipsis"},
2024-11-13 12:56:39 +03:00
string(TextOverflow),
2021-09-07 17:36:50 +03:00
[]string{"clip", "ellipsis"},
},
2024-06-06 17:33:55 +03:00
TextWrap: {
[]string{"wrap", "nowrap", "balance"},
2024-11-13 12:56:39 +03:00
string(TextWrap),
2024-06-06 17:33:55 +03:00
[]string{"wrap", "nowrap", "balance"},
},
2021-09-07 17:36:50 +03:00
WritingMode: {
[]string{"horizontal-top-to-bottom", "horizontal-bottom-to-top", "vertical-right-to-left", "vertical-left-to-right"},
2024-11-13 12:56:39 +03:00
string(WritingMode),
2021-09-07 17:36:50 +03:00
[]string{"horizontal-tb", "horizontal-bt", "vertical-rl", "vertical-lr"},
},
TextDirection: {
[]string{"system", "left-to-right", "right-to-left"},
"direction",
[]string{"", "ltr", "rtl"},
},
VerticalTextOrientation: {
[]string{"mixed", "upright"},
"text-orientation",
[]string{"mixed", "upright"},
},
TextLineStyle: {
[]string{"inherit", "solid", "dashed", "dotted", "double", "wavy"},
"text-decoration-style",
[]string{"inherit", "solid", "dashed", "dotted", "double", "wavy"},
},
BorderStyle: {
[]string{"none", "solid", "dashed", "dotted", "double"},
2024-11-13 12:56:39 +03:00
string(BorderStyle),
2021-09-07 17:36:50 +03:00
[]string{"none", "solid", "dashed", "dotted", "double"},
},
TopStyle: {
[]string{"none", "solid", "dashed", "dotted", "double"},
"",
[]string{"none", "solid", "dashed", "dotted", "double"},
},
RightStyle: {
[]string{"none", "solid", "dashed", "dotted", "double"},
"",
[]string{"none", "solid", "dashed", "dotted", "double"},
},
BottomStyle: {
[]string{"none", "solid", "dashed", "dotted", "double"},
"",
[]string{"none", "solid", "dashed", "dotted", "double"},
},
LeftStyle: {
[]string{"none", "solid", "dashed", "dotted", "double"},
"",
[]string{"none", "solid", "dashed", "dotted", "double"},
},
OutlineStyle: {
[]string{"none", "solid", "dashed", "dotted", "double"},
2024-11-13 12:56:39 +03:00
string(OutlineStyle),
2021-09-07 17:36:50 +03:00
[]string{"none", "solid", "dashed", "dotted", "double"},
},
Tabs: {
2021-11-17 12:32:37 +03:00
[]string{"top", "bottom", "left", "right", "left-list", "right-list", "hidden"},
2021-09-07 17:36:50 +03:00
"",
2021-11-17 12:32:37 +03:00
[]string{"top", "bottom", "left", "right", "left-list", "right-list", "hidden"},
2021-09-07 17:36:50 +03:00
},
NumberPickerType: {
[]string{"editor", "slider"},
"",
[]string{"editor", "slider"},
},
EditViewType: {
[]string{"text", "password", "email", "emails", "url", "phone", "multiline"},
"",
[]string{"text", "password", "email", "emails", "url", "phone", "multiline"},
},
Orientation: {
[]string{"up-down", "start-to-end", "bottom-up", "end-to-start"},
"",
[]string{"column", "row", "column-reverse", "row-reverse"},
},
ListWrap: {
2021-09-07 17:36:50 +03:00
[]string{"off", "on", "reverse"},
"",
[]string{"nowrap", "wrap", "wrap-reverse"},
},
"list-orientation": {
[]string{"vertical", "horizontal"},
"",
[]string{"vertical", "horizontal"},
},
VerticalAlign: {
[]string{"top", "bottom", "center", "stretch"},
"",
[]string{"top", "bottom", "center", "stretch"},
},
HorizontalAlign: {
[]string{"left", "right", "center", "stretch"},
"",
[]string{"left", "right", "center", "stretch"},
},
ButtonsAlign: {
[]string{"left", "right", "center", "stretch"},
"",
[]string{"left", "right", "center", "stretch"},
},
2022-07-31 15:37:26 +03:00
ArrowAlign: {
[]string{"left", "right", "center"},
"",
[]string{"left", "right", "center"},
},
2021-09-07 17:36:50 +03:00
CellVerticalAlign: {
[]string{"top", "bottom", "center", "stretch"},
"align-items",
[]string{"start", "end", "center", "stretch"},
},
CellHorizontalAlign: {
[]string{"left", "right", "center", "stretch"},
"justify-items",
[]string{"start", "end", "center", "stretch"},
},
CellVerticalSelfAlign: {
[]string{"top", "bottom", "center", "stretch"},
"align-self",
[]string{"start", "end", "center", "stretch"},
},
CellHorizontalSelfAlign: {
[]string{"left", "right", "center", "stretch"},
"justify-self",
[]string{"start", "end", "center", "stretch"},
},
GridAutoFlow: {
[]string{"row", "column", "row-dense", "column-dense"},
2024-11-13 12:56:39 +03:00
string(GridAutoFlow),
[]string{"row", "column", "row dense", "column dense"},
},
2021-09-07 17:36:50 +03:00
ImageVerticalAlign: {
[]string{"top", "bottom", "center"},
"",
[]string{"top", "bottom", "center"},
},
ImageHorizontalAlign: {
[]string{"left", "right", "center"},
"",
[]string{"left", "right", "center"},
},
ItemVerticalAlign: {
[]string{"top", "bottom", "center", "stretch"},
"",
[]string{"start", "end", "center", "stretch"},
},
ItemHorizontalAlign: {
[]string{"left", "right", "center", "stretch"},
"",
[]string{"start", "end", "center", "stretch"},
},
CheckboxVerticalAlign: {
[]string{"top", "bottom", "center"},
"",
[]string{"start", "end", "center"},
},
CheckboxHorizontalAlign: {
[]string{"left", "right", "center"},
"",
[]string{"start", "end", "center"},
},
TableVerticalAlign: {
[]string{"top", "bottom", "center", "stretch", "baseline"},
"vertical-align",
[]string{"top", "bottom", "middle", "baseline", "baseline"},
},
Cursor: {
[]string{"auto", "default", "none", "context-menu", "help", "pointer", "progress", "wait", "cell", "crosshair", "text", "vertical-text", "alias", "copy", "move", "no-drop", "not-allowed", "e-resize", "n-resize", "ne-resize", "nw-resize", "s-resize", "se-resize", "sw-resize", "w-resize", "ew-resize", "ns-resize", "nesw-resize", "nwse-resize", "col-resize", "row-resize", "all-scroll", "zoom-in", "zoom-out", "grab", "grabbing"},
2024-11-13 12:56:39 +03:00
string(Cursor),
2021-09-07 17:36:50 +03:00
[]string{"auto", "default", "none", "context-menu", "help", "pointer", "progress", "wait", "cell", "crosshair", "text", "vertical-text", "alias", "copy", "move", "no-drop", "not-allowed", "e-resize", "n-resize", "ne-resize", "nw-resize", "s-resize", "se-resize", "sw-resize", "w-resize", "ew-resize", "ns-resize", "nesw-resize", "nwse-resize", "col-resize", "row-resize", "all-scroll", "zoom-in", "zoom-out", "grab", "grabbing"},
},
Fit: {
[]string{"none", "contain", "cover", "fill", "scale-down"},
"object-fit",
[]string{"none", "contain", "cover", "fill", "scale-down"},
},
backgroundFit: {
[]string{"none", "contain", "cover"},
"",
[]string{"none", "contain", "cover"},
},
Repeat: {
[]string{"no-repeat", "repeat", "repeat-x", "repeat-y", "round", "space"},
"",
[]string{"no-repeat", "repeat", "repeat-x", "repeat-y", "round", "space"},
},
Attachment: {
[]string{"scroll", "fixed", "local"},
"",
[]string{"scroll", "fixed", "local"},
},
BackgroundClip: {
[]string{"border-box", "padding-box", "content-box"}, // "text"},
"background-clip",
[]string{"border-box", "padding-box", "content-box"}, // "text"},
},
Direction: {
[]string{"to-top", "to-right-top", "to-right", "to-right-bottom", "to-bottom", "to-left-bottom", "to-left", "to-left-top"},
"",
[]string{"to top", "to right top", "to right", "to right bottom", "to bottom", "to left bottom", "to left", "to left top"},
},
AnimationDirection: {
[]string{"normal", "reverse", "alternate", "alternate-reverse"},
"",
[]string{"normal", "reverse", "alternate", "alternate-reverse"},
},
2021-09-07 17:36:50 +03:00
RadialGradientShape: {
[]string{"ellipse", "circle"},
"",
[]string{"ellipse", "circle"},
},
RadialGradientRadius: {
[]string{"closest-side", "closest-corner", "farthest-side", "farthest-corner"},
"",
[]string{"closest-side", "closest-corner", "farthest-side", "farthest-corner"},
},
ItemCheckbox: {
[]string{"none", "single", "multiple"},
"",
[]string{"none", "single", "multiple"},
},
Float: {
[]string{"none", "left", "right"},
"float",
[]string{"none", "left", "right"},
},
Preload: {
[]string{"none", "metadata", "auto"},
"",
[]string{"none", "metadata", "auto"},
},
2022-01-05 18:33:18 +03:00
SelectionMode: {
[]string{"none", "cell", "row"},
"",
[]string{"none", "cell", "row"},
},
Resize: {
[]string{"none", "both", "horizontal", "vertical"},
"resize",
[]string{"none", "both", "horizontal", "vertical"},
},
2022-07-31 15:37:26 +03:00
Arrow: {
[]string{"none", "top", "right", "bottom", "left"},
"",
[]string{"none", "top", "right", "bottom", "left"},
},
MixBlendMode: {
[]string{"normal", "multiply", "screen", "overlay", "darken", "lighten", "color-dodge", "color-burn", "hard-light", "soft-light", "difference", "exclusion", "hue", "saturation", "color", "luminosity"},
2024-11-13 12:56:39 +03:00
string(MixBlendMode),
[]string{"normal", "multiply", "screen", "overlay", "darken", "lighten", "color-dodge", "color-burn", "hard-light", "soft-light", "difference", "exclusion", "hue", "saturation", "color", "luminosity"},
},
BackgroundBlendMode: {
[]string{"normal", "multiply", "screen", "overlay", "darken", "lighten", "color-dodge", "color-burn", "hard-light", "soft-light", "difference", "exclusion", "hue", "saturation", "color", "luminosity"},
2024-11-13 12:56:39 +03:00
string(BackgroundBlendMode),
[]string{"normal", "multiply", "screen", "overlay", "darken", "lighten", "color-dodge", "color-burn", "hard-light", "soft-light", "difference", "exclusion", "hue", "saturation", "color", "luminosity"},
},
2022-12-23 17:27:14 +03:00
ColumnFill: {
[]string{"balance", "auto"},
2024-11-13 12:56:39 +03:00
string(ColumnFill),
2022-12-23 17:27:14 +03:00
[]string{"balance", "auto"},
},
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func notCompatibleType(tag PropertyName, value any) {
ErrorLogF(`"%T" type not compatible with "%s" property`, value, string(tag))
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func invalidPropertyValue(tag PropertyName, value any) {
ErrorLogF(`Invalid value "%v" of "%s" property`, value, string(tag))
2021-09-07 17:36:50 +03:00
}
func isConstantName(text string) bool {
len := len(text)
if len <= 1 || text[0] != '@' {
return false
}
if len > 2 {
last := len - 1
if (text[1] == '`' && text[last] == '`') ||
(text[1] == '"' && text[last] == '"') ||
(text[1] == '\'' && text[last] == '\'') {
return true
}
}
return !strings.ContainsAny(text, ",;|\"'`+(){}[]<>/\\*&%! \t\n\r")
}
2022-07-26 18:36:00 +03:00
func isInt(value any) (int, bool) {
2021-09-07 17:36:50 +03:00
var n int
switch value := value.(type) {
case int:
n = value
case int8:
n = int(value)
case int16:
n = int(value)
case int32:
n = int(value)
case int64:
n = int(value)
case uint:
n = int(value)
case uint8:
n = int(value)
case uint16:
n = int(value)
case uint32:
n = int(value)
case uint64:
n = int(value)
default:
return 0, false
}
return n, true
}
2024-11-13 12:56:39 +03:00
func setSimpleProperty(properties Properties, tag PropertyName, value any) bool {
2021-09-07 17:36:50 +03:00
if value == nil {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, nil)
2021-09-07 17:36:50 +03:00
return true
} else if text, ok := value.(string); ok {
text = strings.Trim(text, " \t\n\r")
if text == "" {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, nil)
2021-09-07 17:36:50 +03:00
return true
}
if isConstantName(text) {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, text)
2021-09-07 17:36:50 +03:00
return true
}
}
return false
}
2024-11-13 12:56:39 +03:00
func setStringPropertyValue(properties Properties, tag PropertyName, text any) []PropertyName {
if text != "" {
properties.setRaw(tag, text)
} else if properties.getRaw(tag) != nil {
properties.setRaw(tag, nil)
} else {
return []PropertyName{}
}
return []PropertyName{tag}
}
func setArrayPropertyValue[T any](properties Properties, tag PropertyName, value []T) []PropertyName {
if len(value) > 0 {
properties.setRaw(tag, value)
} else if properties.getRaw(tag) != nil {
properties.setRaw(tag, nil)
} else {
return []PropertyName{}
}
return []PropertyName{tag}
}
func setSizeProperty(properties Properties, tag PropertyName, value any) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
var size SizeUnit
switch value := value.(type) {
case string:
var ok bool
if fn := parseSizeFunc(value); fn != nil {
size.Type = SizeFunction
size.Function = fn
} else if size, ok = StringToSizeUnit(value); !ok {
2021-09-07 17:36:50 +03:00
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
case SizeUnit:
size = value
case SizeFunc:
size.Type = SizeFunction
size.Function = value
2021-09-07 17:36:50 +03:00
case float32:
size.Type = SizeInPixel
size.Value = float64(value)
case float64:
size.Type = SizeInPixel
size.Value = value
default:
if n, ok := isInt(value); ok {
size.Type = SizeInPixel
size.Value = float64(n)
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
if size.Type == Auto {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, nil)
2021-09-07 17:36:50 +03:00
} else {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, size)
2021-09-07 17:36:50 +03:00
}
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func setAngleProperty(properties Properties, tag PropertyName, value any) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
var angle AngleUnit
switch value := value.(type) {
case string:
var ok bool
if angle, ok = StringToAngleUnit(value); !ok {
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
case AngleUnit:
angle = value
case float32:
angle = Rad(float64(value))
case float64:
angle = Rad(value)
default:
if n, ok := isInt(value); ok {
angle = Rad(float64(n))
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, angle)
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func setColorProperty(properties Properties, tag PropertyName, value any) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
var result Color
switch value := value.(type) {
case string:
2022-05-01 13:27:04 +03:00
var err error
if result, err = stringToColor(value); err != nil {
2021-09-07 17:36:50 +03:00
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
case Color:
result = value
default:
if color, ok := isInt(value); ok {
result = Color(color)
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, result)
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func setEnumProperty(properties Properties, tag PropertyName, value any, values []string) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
var n int
if text, ok := value.(string); ok {
if n, ok = enumStringToInt(text, values, false); !ok {
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
} else if i, ok := isInt(value); ok {
if i < 0 || i >= len(values) {
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
n = i
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, n)
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func setBoolProperty(properties Properties, tag PropertyName, value any) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
if text, ok := value.(string); ok {
switch strings.ToLower(strings.Trim(text, " \t")) {
case "true", "yes", "on", "1":
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, true)
2021-09-07 17:36:50 +03:00
case "false", "no", "off", "0":
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, false)
2021-09-07 17:36:50 +03:00
default:
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
} else if n, ok := isInt(value); ok {
switch n {
case 1:
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, true)
2021-09-07 17:36:50 +03:00
case 0:
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, false)
2021-09-07 17:36:50 +03:00
default:
invalidPropertyValue(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
} else if b, ok := value.(bool); ok {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, b)
2021-09-07 17:36:50 +03:00
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func setIntProperty(properties Properties, tag PropertyName, value any) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
if text, ok := value.(string); ok {
n, err := strconv.Atoi(strings.Trim(text, " \t"))
if err != nil {
invalidPropertyValue(tag, value)
ErrorLog(err.Error())
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, n)
2021-09-07 17:36:50 +03:00
} else if n, ok := isInt(value); ok {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, n)
2021-09-07 17:36:50 +03:00
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func setFloatProperty(properties Properties, tag PropertyName, value any, min, max float64) []PropertyName {
if !setSimpleProperty(properties, tag, value) {
2021-09-07 17:36:50 +03:00
f := float64(0)
switch value := value.(type) {
case string:
var err error
if f, err = strconv.ParseFloat(strings.Trim(value, " \t"), 64); err != nil {
invalidPropertyValue(tag, value)
ErrorLog(err.Error())
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
2022-08-18 18:18:36 +03:00
if f < min || f > max {
ErrorLogF(`"%T" out of range of "%s" property`, value, tag)
2024-11-13 12:56:39 +03:00
return nil
2022-08-18 18:18:36 +03:00
}
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, value)
return nil
2021-09-07 17:36:50 +03:00
case float32:
f = float64(value)
case float64:
f = value
default:
if n, ok := isInt(value); ok {
f = float64(n)
} else {
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
if f >= min && f <= max {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, f)
2021-09-07 17:36:50 +03:00
} else {
ErrorLogF(`"%T" out of range of "%s" property`, value, tag)
2024-11-13 12:56:39 +03:00
return nil
2021-09-07 17:36:50 +03:00
}
}
2024-11-13 12:56:39 +03:00
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
2024-11-13 12:56:39 +03:00
func propertiesSet(properties Properties, tag PropertyName, value any) []PropertyName {
2021-09-07 17:36:50 +03:00
if _, ok := sizeProperties[tag]; ok {
2024-11-13 12:56:39 +03:00
return setSizeProperty(properties, tag, value)
2021-09-07 17:36:50 +03:00
}
if valuesData, ok := enumProperties[tag]; ok {
2024-11-13 12:56:39 +03:00
return setEnumProperty(properties, tag, value, valuesData.values)
2021-09-07 17:36:50 +03:00
}
if limits, ok := floatProperties[tag]; ok {
2024-11-13 12:56:39 +03:00
return setFloatProperty(properties, tag, value, limits.min, limits.max)
2021-09-07 17:36:50 +03:00
}
if isPropertyInList(tag, colorProperties) {
2024-11-13 12:56:39 +03:00
return setColorProperty(properties, tag, value)
2021-09-07 17:36:50 +03:00
}
if isPropertyInList(tag, angleProperties) {
2024-11-13 12:56:39 +03:00
return setAngleProperty(properties, tag, value)
2021-09-07 17:36:50 +03:00
}
if isPropertyInList(tag, boolProperties) {
2024-11-13 12:56:39 +03:00
return setBoolProperty(properties, tag, value)
2021-09-07 17:36:50 +03:00
}
if isPropertyInList(tag, intProperties) {
2024-11-13 12:56:39 +03:00
return setIntProperty(properties, tag, value)
2021-09-07 17:36:50 +03:00
}
if text, ok := value.(string); ok {
2024-11-13 12:56:39 +03:00
properties.setRaw(tag, text)
return []PropertyName{tag}
2021-09-07 17:36:50 +03:00
}
notCompatibleType(tag, value)
2024-11-13 12:56:39 +03:00
return nil
}
/*
func (properties *propertyList) Set(tag PropertyName, value any) bool {
tag = properties.normalize(tag)
if value == nil {
properties.remove(properties, tag)
return true
}
return properties.set(properties, tag, value) != nil
}
*/
func (data *dataProperty) Set(tag PropertyName, value any) bool {
if value == nil {
data.Remove(tag)
return true
}
tag = data.normalize(tag)
for _, supported := range data.supportedProperties {
if tag == supported {
return data.set(data, tag, value) != nil
}
}
ErrorLogF(`"%s" property is not supported`, string(tag))
2021-09-07 17:36:50 +03:00
return false
}