mirror of
https://github.com/dyne/frei0r.git
synced 2025-12-05 14:19:59 +01:00
mirr0r filter added (#196)
* mirr0r filter added * removed redundant and unused includes * Using Cairo graphics library * fixed parameters range * Clear the screen before drawing, to avoid problems with image sources with transparency. * Remove unused import
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -39,3 +39,4 @@ doc/html
|
||||
/out/
|
||||
/.vs/
|
||||
CMakeSettings.json
|
||||
.vscode
|
||||
|
||||
@@ -12,6 +12,7 @@ endif (${OpenCV_FOUND})
|
||||
if (${Cairo_FOUND})
|
||||
add_subdirectory (cairoimagegrid)
|
||||
add_subdirectory (cairogradient)
|
||||
add_subdirectory (mirr0r)
|
||||
endif (${Cairo_FOUND})
|
||||
|
||||
add_subdirectory (3dflippo)
|
||||
|
||||
15
src/filter/mirr0r/CMakeLists.txt
Executable file
15
src/filter/mirr0r/CMakeLists.txt
Executable file
@@ -0,0 +1,15 @@
|
||||
set (SOURCES mirr0r.cpp)
|
||||
set (TARGET mirr0r)
|
||||
|
||||
include_directories(${Cairo_INCLUDE_DIR})
|
||||
set(LIBS ${LIBS} ${Cairo_LIBRARY})
|
||||
|
||||
if (MSVC)
|
||||
set (SOURCES ${SOURCES} ${FREI0R_DEF})
|
||||
endif (MSVC)
|
||||
|
||||
add_library (${TARGET} MODULE ${SOURCES})
|
||||
|
||||
set_target_properties (${TARGET} PROPERTIES PREFIX "")
|
||||
target_link_libraries(mirr0r ${LIBS})
|
||||
install (TARGETS ${TARGET} LIBRARY DESTINATION ${LIBDIR})
|
||||
136
src/filter/mirr0r/mirr0r.cpp
Executable file
136
src/filter/mirr0r/mirr0r.cpp
Executable file
@@ -0,0 +1,136 @@
|
||||
/*
|
||||
* Copyright (C) 2024 Johann JEG (johannjeg1057@gmail.com)
|
||||
*
|
||||
* This file is a Frei0r plugin.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* as published by the Free Software Foundation, either version 3 of
|
||||
* the License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "frei0r.hpp"
|
||||
#include <cairo.h>
|
||||
#define _USE_MATH_DEFINES
|
||||
#include <cmath>
|
||||
|
||||
class Mirr0r : public frei0r::filter {
|
||||
|
||||
private:
|
||||
|
||||
unsigned int width;
|
||||
unsigned int height;
|
||||
double x_offset;
|
||||
double y_offset;
|
||||
double zoom;
|
||||
double rotation;
|
||||
|
||||
public:
|
||||
|
||||
Mirr0r(unsigned int width, unsigned int height){
|
||||
register_param(this->x_offset, "x_offset", "Horizontal offset for image positioning.");
|
||||
register_param(this->y_offset, "y_offset", "Vertical offset for image positioning.");
|
||||
register_param(this->zoom, "zoom", "Zoom level for image scaling.");
|
||||
register_param(this->rotation, "rotation", "Rotation angle in degrees.");
|
||||
|
||||
this->width = width;
|
||||
this->height = height;
|
||||
this->x_offset = 0.0;
|
||||
this->y_offset = 0.0;
|
||||
this->zoom = 0.5;
|
||||
this->rotation = 0.0;
|
||||
}
|
||||
|
||||
~Mirr0r(){
|
||||
|
||||
}
|
||||
|
||||
void clearScreen(cairo_t* cr, int width, int height) {
|
||||
cairo_save (cr);
|
||||
cairo_set_source_rgba(cr, 0.0, 0.0, 0.0, 0.0);
|
||||
cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE);
|
||||
cairo_paint (cr);
|
||||
cairo_restore (cr);
|
||||
}
|
||||
|
||||
virtual void update(double time, uint32_t* out, const uint32_t* in) {
|
||||
|
||||
int w = this->width;
|
||||
int h = this->height;
|
||||
|
||||
// Calculate the stride for the image surface based on width and format
|
||||
int stride = cairo_format_stride_for_width(CAIRO_FORMAT_ARGB32, w);
|
||||
|
||||
// Create a Cairo surface for the destination image
|
||||
cairo_surface_t* dest_image = cairo_image_surface_create_for_data((unsigned char*)out,
|
||||
CAIRO_FORMAT_ARGB32,
|
||||
w,
|
||||
h,
|
||||
stride);
|
||||
|
||||
// Create a Cairo drawing context for the destination surface
|
||||
cairo_t *cr = cairo_create(dest_image);
|
||||
|
||||
// Clear the screen
|
||||
clearScreen(cr, w, h);
|
||||
|
||||
// Create a Cairo surface for the source image
|
||||
cairo_surface_t *image = cairo_image_surface_create_for_data((unsigned char*)in,
|
||||
CAIRO_FORMAT_ARGB32,
|
||||
w,
|
||||
h,
|
||||
stride);
|
||||
// Create a pattern from the source image surface
|
||||
cairo_pattern_t *pattern = cairo_pattern_create_for_surface(image);
|
||||
// Set the pattern extend mode to reflect (mirror) when the pattern is out of bounds
|
||||
cairo_pattern_set_extend (pattern, CAIRO_EXTEND_REFLECT);
|
||||
|
||||
// Initialize the transformation matrix
|
||||
cairo_matrix_t matrix;
|
||||
cairo_matrix_init_identity(&matrix);
|
||||
|
||||
// Calculate the center coordinates of the destination image
|
||||
float center_x = (float)w / 2.0f;
|
||||
float center_y = (float)h / 2.0f;
|
||||
|
||||
float scale_factor = 1.5f - this->zoom;
|
||||
|
||||
// Apply transformations
|
||||
cairo_matrix_translate(&matrix, center_x - (this->x_offset) * w, center_y - (this->y_offset) * h);
|
||||
cairo_matrix_scale(&matrix, scale_factor, scale_factor);
|
||||
cairo_matrix_rotate(&matrix, this->rotation * M_PI);
|
||||
cairo_matrix_translate(&matrix, -center_x, -center_y);
|
||||
|
||||
// Set the transformation matrix for the pattern
|
||||
cairo_pattern_set_matrix(pattern, &matrix);
|
||||
// Set the source pattern to be used for drawing
|
||||
cairo_set_source(cr, pattern);
|
||||
|
||||
// Draw a rectangle covering the entire image area
|
||||
cairo_rectangle(cr, 0, 0, w, h);
|
||||
// Fill the rectangle with the source pattern
|
||||
cairo_fill(cr);
|
||||
|
||||
// Clean up resources
|
||||
cairo_pattern_destroy (pattern);
|
||||
cairo_surface_destroy (image);
|
||||
cairo_surface_destroy (dest_image);
|
||||
cairo_destroy (cr);
|
||||
}
|
||||
};
|
||||
|
||||
frei0r::construct<Mirr0r> plugin(
|
||||
"Mirr0r",
|
||||
"Repeats and flips the input image when it goes out of bounds, allowing for adjustable offset, zoom and rotation. A versatile tool for creative video effects.",
|
||||
"Johann JEG",
|
||||
1, 0,
|
||||
F0R_COLOR_MODEL_RGBA8888);
|
||||
|
||||
Reference in New Issue
Block a user