Веб-сайт самохостера Lotigara

summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKae <80987908+Novaenia@users.noreply.github.com>2024-12-28 13:07:51 +1100
committerKae <80987908+Novaenia@users.noreply.github.com>2024-12-28 13:07:51 +1100
commit6b49f382e3a9429e97bc47a9b3c18c3ca8feb65c (patch)
tree4f3afffbc25f60e0930bc651ef98f21f4a6ac719
parent9da08e898d9c666f655c7f901d0c67b17a746608 (diff)
move image scaling functions to their own unit, as -O2
-rw-r--r--source/core/CMakeLists.txt6
-rw-r--r--source/core/StarImageProcessing.cpp99
-rw-r--r--source/core/StarImageProcessing.hpp4
-rw-r--r--source/core/StarImageScaling.cpp98
-rw-r--r--source/core/StarImageScaling.hpp8
5 files changed, 113 insertions, 102 deletions
diff --git a/source/core/CMakeLists.txt b/source/core/CMakeLists.txt
index fa1d246..6deb473 100644
--- a/source/core/CMakeLists.txt
+++ b/source/core/CMakeLists.txt
@@ -41,6 +41,7 @@ SET (star_core_HEADERS
StarIdMap.hpp
StarImage.hpp
StarImageProcessing.hpp
+ StarImageScaling.hpp
StarInputEvent.hpp
StarInterpolation.hpp
StarRefPtr.hpp
@@ -152,6 +153,7 @@ SET (star_core_SOURCES
StarIODevice.cpp
StarImage.cpp
StarImageProcessing.cpp
+ StarImageScaling.cpp
StarInputEvent.cpp
StarJson.cpp
StarJsonBuilder.cpp
@@ -229,6 +231,10 @@ IF(STAR_PRECOMPILED_HEADERS)
TARGET_PRECOMPILE_HEADERS (star_core PUBLIC StarPch.hpp)
ENDIF()
+IF(STAR_COMPILER STREQUAL "gnu")
+ SET_SOURCE_FILES_PROPERTIES(StarImageScaling.cpp PROPERTIES COMPILE_FLAGS "-O2")
+ENDIF()
+
IF(STAR_USE_JEMALLOC AND JEMALLOC_IS_PREFIXED)
SET_SOURCE_FILES_PROPERTIES(StarMemory.cpp PROPERTIES
COMPILE_DEFINITIONS STAR_JEMALLOC_IS_PREFIXED
diff --git a/source/core/StarImageProcessing.cpp b/source/core/StarImageProcessing.cpp
index 96edc0b..1cfd847 100644
--- a/source/core/StarImageProcessing.cpp
+++ b/source/core/StarImageProcessing.cpp
@@ -1,4 +1,5 @@
#include "StarImageProcessing.hpp"
+#include "StarImageScaling.hpp"
#include "StarMatrix3.hpp"
#include "StarInterpolation.hpp"
#include "StarLexicalCast.hpp"
@@ -10,104 +11,6 @@
namespace Star {
-Image scaleNearest(Image const& srcImage, Vec2F const& scale) {
- Vec2U srcSize = srcImage.size();
- Vec2U destSize = Vec2U::round(vmult(Vec2F(srcSize), scale));
- destSize[0] = max(destSize[0], 1u);
- destSize[1] = max(destSize[1], 1u);
-
- Image destImage(destSize, srcImage.pixelFormat());
-
- for (unsigned y = 0; y < destSize[1]; ++y) {
- for (unsigned x = 0; x < destSize[0]; ++x)
- destImage.set({x, y}, srcImage.clamp(Vec2I::round(vdiv(Vec2F(x, y), scale))));
- }
- return destImage;
-}
-
-#pragma GCC push_options
-#pragma GCC optimize("-fno-unsafe-math-optimizations", "-ffloat-store")
-Image scaleBilinear(Image const& srcImage, Vec2F const& scale) {
- Vec2U srcSize = srcImage.size();
- Vec2U destSize = Vec2U::round(vmult(Vec2F(srcSize), scale));
- destSize[0] = max(destSize[0], 1u);
- destSize[1] = max(destSize[1], 1u);
-
- Image destImage(destSize, srcImage.pixelFormat());
-
- auto lerpVec = [](float const& offset, Vec4F f0, Vec4F f1) {
- return f0 * (1 - offset) + f1 * (offset);
- };
-
- for (unsigned y = 0; y < destSize[1]; ++y) {
- for (unsigned x = 0; x < destSize[0]; ++x) {
- auto pos = vdiv(Vec2F(x, y), scale);
- auto ipart = Vec2I::floor(pos);
- auto fpart = pos - Vec2F(ipart);
-
- auto result = lerpVec(fpart[1], lerpVec(fpart[0], Vec4F(srcImage.clamp(ipart[0], ipart[1])), Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1]))), lerpVec(fpart[0],
- Vec4F(srcImage.clamp(ipart[0], ipart[1] + 1)), Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 1))));
-
- destImage.set({x, y}, Vec4B(result));
- }
- }
-
- return destImage;
-}
-
-Image scaleBicubic(Image const& srcImage, Vec2F const& scale) {
- Vec2U srcSize = srcImage.size();
- Vec2U destSize = Vec2U::round(vmult(Vec2F(srcSize), scale));
- destSize[0] = max(destSize[0], 1u);
- destSize[1] = max(destSize[1], 1u);
-
- Image destImage(destSize, srcImage.pixelFormat());
-
- for (unsigned y = 0; y < destSize[1]; ++y) {
- for (unsigned x = 0; x < destSize[0]; ++x) {
- auto pos = vdiv(Vec2F(x, y), scale);
- auto ipart = Vec2I::floor(pos);
- auto fpart = pos - Vec2F(ipart);
-
- Vec4F a = cubic4(fpart[0],
- Vec4F(srcImage.clamp(ipart[0], ipart[1])),
- Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1])),
- Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1])),
- Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1])));
-
- Vec4F b = cubic4(fpart[0],
- Vec4F(srcImage.clamp(ipart[0], ipart[1] + 1)),
- Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 1)),
- Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1] + 1)),
- Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1] + 1)));
-
- Vec4F c = cubic4(fpart[0],
- Vec4F(srcImage.clamp(ipart[0], ipart[1] + 2)),
- Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 2)),
- Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1] + 2)),
- Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1] + 2)));
-
- Vec4F d = cubic4(fpart[0],
- Vec4F(srcImage.clamp(ipart[0], ipart[1] + 3)),
- Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 3)),
- Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1] + 3)),
- Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1] + 3)));
-
- auto result = cubic4(fpart[1], a, b, c, d);
-
- destImage.set({x, y}, Vec4B(
- clamp(result[0], 0.0f, 255.0f),
- clamp(result[1], 0.0f, 255.0f),
- clamp(result[2], 0.0f, 255.0f),
- clamp(result[3], 0.0f, 255.0f)
- ));
- }
- }
-
- return destImage;
-}
-#pragma GCC pop_options
-
StringList colorDirectivesFromConfig(JsonArray const& directives) {
List<String> result;
diff --git a/source/core/StarImageProcessing.hpp b/source/core/StarImageProcessing.hpp
index 8316d18..dfc9420 100644
--- a/source/core/StarImageProcessing.hpp
+++ b/source/core/StarImageProcessing.hpp
@@ -10,10 +10,6 @@ STAR_CLASS(Image);
STAR_EXCEPTION(ImageOperationException, StarException);
-Image scaleNearest(Image const& srcImage, Vec2F const& scale);
-Image scaleBilinear(Image const& srcImage, Vec2F const& scale);
-Image scaleBicubic(Image const& srcImage, Vec2F const& scale);
-
StringList colorDirectivesFromConfig(JsonArray const& directives);
String paletteSwapDirectivesFromConfig(Json const& swaps);
diff --git a/source/core/StarImageScaling.cpp b/source/core/StarImageScaling.cpp
new file mode 100644
index 0000000..96837aa
--- /dev/null
+++ b/source/core/StarImageScaling.cpp
@@ -0,0 +1,98 @@
+#include "StarImage.hpp"
+#include "StarImageScaling.hpp"
+#include "StarInterpolation.hpp"
+
+namespace Star {
+
+Image scaleNearest(Image const& srcImage, Vec2F const& scale) {
+ Vec2U srcSize = srcImage.size();
+ Vec2U destSize = Vec2U::round(vmult(Vec2F(srcSize), scale));
+ destSize[0] = max(destSize[0], 1u);
+ destSize[1] = max(destSize[1], 1u);
+
+ Image destImage(destSize, srcImage.pixelFormat());
+
+ for (unsigned y = 0; y < destSize[1]; ++y) {
+ for (unsigned x = 0; x < destSize[0]; ++x)
+ destImage.set({x, y}, srcImage.clamp(Vec2I::round(vdiv(Vec2F(x, y), scale))));
+ }
+ return destImage;
+}
+
+Image scaleBilinear(Image const& srcImage, Vec2F const& scale) {
+ Vec2U srcSize = srcImage.size();
+ Vec2U destSize = Vec2U::round(vmult(Vec2F(srcSize), scale));
+ destSize[0] = max(destSize[0], 1u);
+ destSize[1] = max(destSize[1], 1u);
+
+ Image destImage(destSize, srcImage.pixelFormat());
+
+ for (unsigned y = 0; y < destSize[1]; ++y) {
+ for (unsigned x = 0; x < destSize[0]; ++x) {
+ auto pos = vdiv(Vec2F(x, y), scale);
+ auto ipart = Vec2I::floor(pos);
+ auto fpart = pos - Vec2F(ipart);
+
+ auto result = lerp(fpart[1], lerp(fpart[0], Vec4F(srcImage.clamp(ipart[0], ipart[1])), Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1]))), lerp(fpart[0],
+ Vec4F(srcImage.clamp(ipart[0], ipart[1] + 1)), Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 1))));
+
+ destImage.set({x, y}, Vec4B(result));
+ }
+ }
+
+ return destImage;
+}
+
+Image scaleBicubic(Image const& srcImage, Vec2F const& scale) {
+ Vec2U srcSize = srcImage.size();
+ Vec2U destSize = Vec2U::round(vmult(Vec2F(srcSize), scale));
+ destSize[0] = max(destSize[0], 1u);
+ destSize[1] = max(destSize[1], 1u);
+
+ Image destImage(destSize, srcImage.pixelFormat());
+
+ for (unsigned y = 0; y < destSize[1]; ++y) {
+ for (unsigned x = 0; x < destSize[0]; ++x) {
+ auto pos = vdiv(Vec2F(x, y), scale);
+ auto ipart = Vec2I::floor(pos);
+ auto fpart = pos - Vec2F(ipart);
+
+ Vec4F a = cubic4(fpart[0],
+ Vec4F(srcImage.clamp(ipart[0], ipart[1])),
+ Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1])),
+ Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1])),
+ Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1])));
+
+ Vec4F b = cubic4(fpart[0],
+ Vec4F(srcImage.clamp(ipart[0], ipart[1] + 1)),
+ Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 1)),
+ Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1] + 1)),
+ Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1] + 1)));
+
+ Vec4F c = cubic4(fpart[0],
+ Vec4F(srcImage.clamp(ipart[0], ipart[1] + 2)),
+ Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 2)),
+ Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1] + 2)),
+ Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1] + 2)));
+
+ Vec4F d = cubic4(fpart[0],
+ Vec4F(srcImage.clamp(ipart[0], ipart[1] + 3)),
+ Vec4F(srcImage.clamp(ipart[0] + 1, ipart[1] + 3)),
+ Vec4F(srcImage.clamp(ipart[0] + 2, ipart[1] + 3)),
+ Vec4F(srcImage.clamp(ipart[0] + 3, ipart[1] + 3)));
+
+ auto result = cubic4(fpart[1], a, b, c, d);
+
+ destImage.set({x, y}, Vec4B(
+ clamp(result[0], 0.0f, 255.0f),
+ clamp(result[1], 0.0f, 255.0f),
+ clamp(result[2], 0.0f, 255.0f),
+ clamp(result[3], 0.0f, 255.0f)
+ ));
+ }
+ }
+
+ return destImage;
+}
+
+} \ No newline at end of file
diff --git a/source/core/StarImageScaling.hpp b/source/core/StarImageScaling.hpp
new file mode 100644
index 0000000..6a7271b
--- /dev/null
+++ b/source/core/StarImageScaling.hpp
@@ -0,0 +1,8 @@
+namespace Star {
+
+STAR_CLASS(Image);
+Image scaleNearest(Image const& srcImage, Vec2F const& scale);
+Image scaleBilinear(Image const& srcImage, Vec2F const& scale);
+Image scaleBicubic(Image const& srcImage, Vec2F const& scale);
+
+} \ No newline at end of file