From 4dad9c6c05921cf98c9ee59a5f28358496912433 Mon Sep 17 00:00:00 2001
From: katsuhisa yuasa <berupon@gmail.com>
Date: Sat, 19 Oct 2024 12:37:56 +0900
Subject: [PATCH] optimize ImageLoaderSVG::create_image_from_utf8_buffer

---
 modules/svg/image_loader_svg.cpp | 26 ++++----------------------
 1 file changed, 4 insertions(+), 22 deletions(-)

diff --git a/modules/svg/image_loader_svg.cpp b/modules/svg/image_loader_svg.cpp
index d90313719561..b9d493b84401 100644
--- a/modules/svg/image_loader_svg.cpp
+++ b/modules/svg/image_loader_svg.cpp
@@ -104,51 +104,33 @@ Error ImageLoaderSVG::create_image_from_utf8_buffer(Ref<Image> p_image, const ui
 	picture->size(width, height);
 
 	std::unique_ptr<tvg::SwCanvas> sw_canvas = tvg::SwCanvas::gen();
-	// Note: memalloc here, be sure to memfree before any return.
-	uint32_t *buffer = (uint32_t *)memalloc(sizeof(uint32_t) * width * height);
+	Vector<uint8_t> buffer;
+	buffer.resize(sizeof(uint32_t) * width * height);
 
-	tvg::Result res = sw_canvas->target(buffer, width, width, height, tvg::SwCanvas::ARGB8888S);
+	tvg::Result res = sw_canvas->target((uint32_t *)buffer.ptrw(), width, width, height, tvg::SwCanvas::ABGR8888S);
 	if (res != tvg::Result::Success) {
-		memfree(buffer);
 		ERR_FAIL_V_MSG(FAILED, "ImageLoaderSVG: Couldn't set target on ThorVG canvas.");
 	}
 
 	res = sw_canvas->push(std::move(picture));
 	if (res != tvg::Result::Success) {
-		memfree(buffer);
 		ERR_FAIL_V_MSG(FAILED, "ImageLoaderSVG: Couldn't insert ThorVG picture on canvas.");
 	}
 
 	res = sw_canvas->draw();
 	if (res != tvg::Result::Success) {
-		memfree(buffer);
 		ERR_FAIL_V_MSG(FAILED, "ImageLoaderSVG: Couldn't draw ThorVG pictures on canvas.");
 	}
 
 	res = sw_canvas->sync();
 	if (res != tvg::Result::Success) {
-		memfree(buffer);
 		ERR_FAIL_V_MSG(FAILED, "ImageLoaderSVG: Couldn't sync ThorVG canvas.");
 	}
 
-	Vector<uint8_t> image;
-	image.resize(width * height * sizeof(uint32_t));
-
-	for (uint32_t y = 0; y < height; y++) {
-		for (uint32_t x = 0; x < width; x++) {
-			uint32_t n = buffer[y * width + x];
-			const size_t offset = sizeof(uint32_t) * width * y + sizeof(uint32_t) * x;
-			image.write[offset + 0] = (n >> 16) & 0xff;
-			image.write[offset + 1] = (n >> 8) & 0xff;
-			image.write[offset + 2] = n & 0xff;
-			image.write[offset + 3] = (n >> 24) & 0xff;
-		}
-	}
+	p_image->set_data(width, height, false, Image::FORMAT_RGBA8, buffer);
 
 	res = sw_canvas->clear(true);
-	memfree(buffer);
 
-	p_image->set_data(width, height, false, Image::FORMAT_RGBA8, image);
 	return OK;
 }