From 3561a34322989d08f83394a1c9cee0d4b1535c86 Mon Sep 17 00:00:00 2001 From: GoodNotesCI Date: Sat, 14 Jun 2025 21:24:52 +0800 Subject: [PATCH 1/4] Parse rgba string --- Source/Parser/SVG/SVGParserBasics.swift | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/Source/Parser/SVG/SVGParserBasics.swift b/Source/Parser/SVG/SVGParserBasics.swift index 3c15b18..e4c7d7f 100644 --- a/Source/Parser/SVG/SVGParserBasics.swift +++ b/Source/Parser/SVG/SVGParserBasics.swift @@ -97,7 +97,7 @@ extension SVGHelper { } } if let color = parseColor(colorString, style) { - return color.opacity(parseOpacity(style, "fill-opacity", alternativeKeys: ["opacity"])) + return color.opacity(color.opacity * parseOpacity(style, "fill-opacity", alternativeKeys: ["opacity"])) } return .none @@ -112,7 +112,7 @@ extension SVGHelper { } else if let defaultColor = SVGColor.by(name: normalized) { return defaultColor } else if normalized.hasPrefix("rgb") { - return parseRGBNotation(colorString: normalized) + return parseRGBANotation(colorString: normalized) } else { return createColorFromHex(normalized) } @@ -130,8 +130,9 @@ extension SVGHelper { return SVGColor(hex: cleanedHexString) } - static func parseRGBNotation(colorString: String) -> SVGColor { - let from = colorString.index(colorString.startIndex, offsetBy: 4) + static func parseRGBANotation(colorString: String) -> SVGColor { + let fromIndex = colorString.hasPrefix("rgba") ? 5 : 4 + let from = colorString.index(colorString.startIndex, offsetBy: fromIndex) let inPercentage = colorString.contains("%") let sp = String(colorString.suffix(from: from)) .replacingOccurrences(of: "%", with: "") @@ -141,6 +142,7 @@ extension SVGHelper { var red = 0.0 var green = 0.0 var blue = 0.0 + var alpha = 1.0 // Default to fully opaque if x.count == 3 { if let r = Double(x[0]), let g = Double(x[1]), let b = Double(x[2]) { blue = b @@ -148,10 +150,16 @@ extension SVGHelper { red = r } } + if x.count == 4, let a = Double(x[3]) { + alpha = a + } if inPercentage { red *= 2.55 green *= 2.55 blue *= 2.55 + if x.count == 4, let a = Double(x[3]) { + alpha *= 2.55 + } } return SVGColor(r: Int(round(red)), g: Int(round(green)), b: Int(round(blue))) } From 96a1b6174730ab03734b6cf952e63b0a9f85f25b Mon Sep 17 00:00:00 2001 From: GoodNotesCI Date: Sat, 14 Jun 2025 22:19:12 +0800 Subject: [PATCH 2/4] Set transparency for outher color --- Source/Parser/SVG/SVGParserBasics.swift | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/Source/Parser/SVG/SVGParserBasics.swift b/Source/Parser/SVG/SVGParserBasics.swift index e4c7d7f..f96d1d1 100644 --- a/Source/Parser/SVG/SVGParserBasics.swift +++ b/Source/Parser/SVG/SVGParserBasics.swift @@ -127,7 +127,7 @@ extension SVGHelper { let x = Array(cleanedHexString) cleanedHexString = "\(x[0])\(x[0])\(x[1])\(x[1])\(x[2])\(x[2])" } - return SVGColor(hex: cleanedHexString) + return SVGColor(hex: cleanedHexString).opacity(1.0) } static func parseRGBANotation(colorString: String) -> SVGColor { @@ -142,8 +142,8 @@ extension SVGHelper { var red = 0.0 var green = 0.0 var blue = 0.0 - var alpha = 1.0 // Default to fully opaque - if x.count == 3 { + var alpha = 1.0 // Default to fully opaque, always from 0 to 1 in CSS + if x.count <= 3 { if let r = Double(x[0]), let g = Double(x[1]), let b = Double(x[2]) { blue = b green = g @@ -157,11 +157,11 @@ extension SVGHelper { red *= 2.55 green *= 2.55 blue *= 2.55 - if x.count == 4, let a = Double(x[3]) { - alpha *= 2.55 + if x.count == 4 { + alpha *= 0.01 } } - return SVGColor(r: Int(round(red)), g: Int(round(green)), b: Int(round(blue))) + return SVGColor(r: Int(round(red)), g: Int(round(green)), b: Int(round(blue))).opacity(round(alpha)) } static private func parseIdFromUrl(_ urlString: String) -> String? { From 4d0ff3b766dc4ad87a9dd9818dd936564aaaef13 Mon Sep 17 00:00:00 2001 From: GoodNotesCI Date: Sat, 14 Jun 2025 23:01:50 +0800 Subject: [PATCH 3/4] Fix shark test cases --- Source/Parser/SVG/SVGParserBasics.swift | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Source/Parser/SVG/SVGParserBasics.swift b/Source/Parser/SVG/SVGParserBasics.swift index f96d1d1..f6cedcc 100644 --- a/Source/Parser/SVG/SVGParserBasics.swift +++ b/Source/Parser/SVG/SVGParserBasics.swift @@ -143,7 +143,7 @@ extension SVGHelper { var green = 0.0 var blue = 0.0 var alpha = 1.0 // Default to fully opaque, always from 0 to 1 in CSS - if x.count <= 3 { + if x.count >= 3 { if let r = Double(x[0]), let g = Double(x[1]), let b = Double(x[2]) { blue = b green = g @@ -161,7 +161,7 @@ extension SVGHelper { alpha *= 0.01 } } - return SVGColor(r: Int(round(red)), g: Int(round(green)), b: Int(round(blue))).opacity(round(alpha)) + return SVGColor(r: Int(round(red)), g: Int(round(green)), b: Int(round(blue))).opacity(min(max(alpha, 0.0), 1.0)) } static private func parseIdFromUrl(_ urlString: String) -> String? { From 7f3e8166c7b712e1718743a6b3c9f38180d7abe9 Mon Sep 17 00:00:00 2001 From: GoodNotesCI Date: Sun, 15 Jun 2025 11:01:05 +0800 Subject: [PATCH 4/4] Add Tesla graph test --- GenerateReferencesCLI/cli.swift | 1 + Tests/SVGViewTests/SVGCustomTests.swift | 8 ++ .../SVGViewTests/w3c/Custom/refs/graph-01.ref | 78 +++++++++++++++++++ .../SVGViewTests/w3c/Custom/svg/graph-01.svg | 16 ++++ 4 files changed, 103 insertions(+) create mode 100644 Tests/SVGViewTests/w3c/Custom/refs/graph-01.ref create mode 100644 Tests/SVGViewTests/w3c/Custom/svg/graph-01.svg diff --git a/GenerateReferencesCLI/cli.swift b/GenerateReferencesCLI/cli.swift index 5294b4e..f682ff1 100644 --- a/GenerateReferencesCLI/cli.swift +++ b/GenerateReferencesCLI/cli.swift @@ -148,6 +148,7 @@ struct cli: ParsableCommand { static let customRefs: [String] = [ "viewport-01", "viewport-02", + "graph-01", ] mutating func run() throws { diff --git a/Tests/SVGViewTests/SVGCustomTests.swift b/Tests/SVGViewTests/SVGCustomTests.swift index eaf9b70..ec4043b 100644 --- a/Tests/SVGViewTests/SVGCustomTests.swift +++ b/Tests/SVGViewTests/SVGCustomTests.swift @@ -9,8 +9,16 @@ class SVGCustomTests: BaseTestCase { return "Custom" } + func testGraph01() { + compareToReference("graph-01") + } + func testViewport01() { compareToReference("viewport-01") } + func testViewport02() { + compareToReference("viewport-02") + } + } \ No newline at end of file diff --git a/Tests/SVGViewTests/w3c/Custom/refs/graph-01.ref b/Tests/SVGViewTests/w3c/Custom/refs/graph-01.ref new file mode 100644 index 0000000..acc343a --- /dev/null +++ b/Tests/SVGViewTests/w3c/Custom/refs/graph-01.ref @@ -0,0 +1,78 @@ +SVGViewport { + width: "2000", + height: "2000", + scaling: "none", + contents: [ + SVGRect { width: 2000, height: 2000, fill: "#F4F4F4" }, + SVGRect { width: 2000, height: 2000, rx: 10, ry: 10, fill: "white" }, + SVGRect { x: 900, y: 900, width: 200, height: 200, rx: 50, ry: 50, fill: "#E82127" }, + SVGText { + text: "Tesla RoboTaxi", + font: { name: "Arial, sans-serif", size: 20, weight: "700" }, + fill: "white", + transform: [1, 0, 0, 1, 917.34375, 1008] + }, + SVGRect { x: 1425, y: 925, width: 150, height: 150, rx: 50, ry: 50, fill: "black" }, + SVGText { + text: "Technology", + font: { name: "Arial, sans-serif", weight: "400" }, + fill: "white", + transform: [1, 0, 0, 1, 1455.1875, 1006.5] + }, + SVGRect { x: 1000, y: 1000, width: 500, height: 2, fill: "#888888" }, + SVGRect { + x: 1709.796875, + y: 800, + width: 104, + height: 104, + rx: 50, + ry: 50, + fill: "white", + stroke: { fill: "#E82127", width: 2 } + }, + SVGText { + text: "Full Self-Driving", + font: { name: "Arial, sans-serif", size: 12, weight: "400" }, + fill: "black", + transform: [1, 0, 0, 1, 1714.921875, 850] + }, + SVGText { + text: "(FSD)", + font: { name: "Arial, sans-serif", size: 12, weight: "400" }, + fill: "black", + transform: [1, 0, 0, 1, 1714.921875, 864] + }, + SVGRect { + x: 1500, + y: 999.9999971679687, + width: 300, + height: 2, + fill: "#888888", + transform: [0.866025, -0.5, 0.5, 0.866025, 0, 0] + }, + SVGRect { + x: 1735.3125, + y: 857.28125, + width: 104, + height: 104, + rx: 50, + ry: 50, + fill: "white", + stroke: { fill: "#E82127", width: 2 } + }, + SVGText { + text: "Computer Vision", + font: { name: "Arial, sans-serif", size: 12, weight: "400" }, + fill: "black", + transform: [1, 0, 0, 1, 1737.671875, 914.28125] + }, + SVGRect { + x: 1500.0000570390625, + y: 1000.0000290703125, + width: 300, + height: 2, + fill: "#888888", + transform: [0.951057, -0.309017, 0.309017, 0.951057, 0, 0] + } + ] +} diff --git a/Tests/SVGViewTests/w3c/Custom/svg/graph-01.svg b/Tests/SVGViewTests/w3c/Custom/svg/graph-01.svg new file mode 100644 index 0000000..9bd653f --- /dev/null +++ b/Tests/SVGViewTests/w3c/Custom/svg/graph-01.svg @@ -0,0 +1,16 @@ + + + + + Tesla RoboTaxi + + Technology + + + Full Self-Driving + (FSD) + + + Computer Vision + + \ No newline at end of file