there some weird stuff going on
parent
42de832ab5
commit
e6760e1147
|
@ -1,5 +1,5 @@
|
||||||
cmake_minimum_required(VERSION 3.25)
|
cmake_minimum_required(VERSION 3.25)
|
||||||
project(image-gp-6 VERSION 0.0.14)
|
project(image-gp-6 VERSION 0.0.15)
|
||||||
|
|
||||||
include(FetchContent)
|
include(FetchContent)
|
||||||
|
|
||||||
|
|
|
@ -46,4 +46,7 @@ blt::gp::prog_config_t config = blt::gp::prog_config_t()
|
||||||
.set_pop_size(POP_SIZE)
|
.set_pop_size(POP_SIZE)
|
||||||
.set_thread_count(0);
|
.set_thread_count(0);
|
||||||
|
|
||||||
|
inline blt::gp::type_provider type_system;
|
||||||
|
inline blt::gp::gp_program program{type_system, SEED, config};
|
||||||
|
|
||||||
#endif //IMAGE_GP_6_CONFIG_H
|
#endif //IMAGE_GP_6_CONFIG_H
|
||||||
|
|
|
@ -0,0 +1,52 @@
|
||||||
|
#pragma once
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2024 Brett Terpstra
|
||||||
|
*
|
||||||
|
* 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 <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <blt/gp/program.h>
|
||||||
|
#include <functional>
|
||||||
|
#include <helper.h>
|
||||||
|
|
||||||
|
#ifndef IMAGE_GP_6_FLOAT_OPERATIONS_H
|
||||||
|
#define IMAGE_GP_6_FLOAT_OPERATIONS_H
|
||||||
|
|
||||||
|
inline blt::gp::operation_t f_add([](float a, float b) {
|
||||||
|
return a + b;
|
||||||
|
}, "add");
|
||||||
|
inline blt::gp::operation_t f_sub([](float a, float b) {
|
||||||
|
return a - b;
|
||||||
|
}, "sub");
|
||||||
|
inline blt::gp::operation_t f_mul([](float a, float b) {
|
||||||
|
return a * b;
|
||||||
|
}, "mul");
|
||||||
|
inline blt::gp::operation_t f_pro_div([](float a, float b) {
|
||||||
|
return b == 0.0f ? 0.0f : (a / b);
|
||||||
|
}, "div");
|
||||||
|
inline blt::gp::operation_t f_literal([]() {
|
||||||
|
return program.get_random().get_float(0.0, 1.0);
|
||||||
|
}, "float_lit");
|
||||||
|
|
||||||
|
template<typename context>
|
||||||
|
void create_float_operations(blt::gp::operator_builder<context>& builder)
|
||||||
|
{
|
||||||
|
builder.add_operator(f_add);
|
||||||
|
builder.add_operator(f_sub);
|
||||||
|
builder.add_operator(f_mul);
|
||||||
|
builder.add_operator(f_pro_div);
|
||||||
|
builder.add_operator(f_literal, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif //IMAGE_GP_6_FLOAT_OPERATIONS_H
|
|
@ -19,6 +19,8 @@
|
||||||
#ifndef IMAGE_GP_6_HELPER_H
|
#ifndef IMAGE_GP_6_HELPER_H
|
||||||
#define IMAGE_GP_6_HELPER_H
|
#define IMAGE_GP_6_HELPER_H
|
||||||
|
|
||||||
|
#include <images.h>
|
||||||
|
|
||||||
template<typename SINGLE_FUNC>
|
template<typename SINGLE_FUNC>
|
||||||
constexpr static auto make_single(SINGLE_FUNC&& func)
|
constexpr static auto make_single(SINGLE_FUNC&& func)
|
||||||
{
|
{
|
||||||
|
@ -41,4 +43,37 @@ constexpr static auto make_double(DOUBLE_FUNC&& func)
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct context
|
||||||
|
{
|
||||||
|
float x, y;
|
||||||
|
};
|
||||||
|
|
||||||
|
inline context get_ctx(blt::size_t i)
|
||||||
|
{
|
||||||
|
context ctx{};
|
||||||
|
i /= CHANNELS;
|
||||||
|
ctx.y = std::floor(static_cast<float>(i) / static_cast<float>(IMAGE_SIZE));
|
||||||
|
ctx.x = static_cast<float>(i) - (ctx.y * IMAGE_SIZE);
|
||||||
|
return ctx;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline context get_pop_ctx(blt::size_t i)
|
||||||
|
{
|
||||||
|
auto const sq = static_cast<float>(std::sqrt(POP_SIZE));
|
||||||
|
context ctx{};
|
||||||
|
ctx.y = std::floor(static_cast<float>(i) / static_cast<float>(sq));
|
||||||
|
ctx.x = static_cast<float>(i) - (ctx.y * sq);
|
||||||
|
return ctx;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline blt::size_t get_index(blt::size_t x, blt::size_t y)
|
||||||
|
{
|
||||||
|
return y * IMAGE_SIZE + x;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline float perlin_noise(float x, float y, float z)
|
||||||
|
{
|
||||||
|
return (stb_perlin_noise3(x, y, z, 0, 0, 0) + 1.0f) / 2.0f;
|
||||||
|
}
|
||||||
|
|
||||||
#endif //IMAGE_GP_6_HELPER_H
|
#endif //IMAGE_GP_6_HELPER_H
|
||||||
|
|
|
@ -0,0 +1,339 @@
|
||||||
|
#pragma once
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2024 Brett Terpstra
|
||||||
|
*
|
||||||
|
* 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 <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <blt/gp/program.h>
|
||||||
|
#include <functional>
|
||||||
|
#include <helper.h>
|
||||||
|
|
||||||
|
#ifndef IMAGE_GP_6_IMAGE_OPERATIONS_H
|
||||||
|
#define IMAGE_GP_6_IMAGE_OPERATIONS_H
|
||||||
|
|
||||||
|
inline blt::gp::operation_t add(make_double(std::plus()), "add");
|
||||||
|
inline blt::gp::operation_t sub(make_double(std::minus()), "sub");
|
||||||
|
inline blt::gp::operation_t mul(make_double(std::multiplies()), "mul");
|
||||||
|
inline blt::gp::operation_t pro_div([](const full_image_t& a, const full_image_t& b) {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
img.rgb_data[i] = b.rgb_data[i] == 0 ? 0 : (a.rgb_data[i] / b.rgb_data[i]);
|
||||||
|
return img;
|
||||||
|
}, "div");
|
||||||
|
inline blt::gp::operation_t op_sin(make_single([](float a) {
|
||||||
|
return (std::sin(a) + 1.0f) / 2.0f;
|
||||||
|
}), "sin");
|
||||||
|
inline blt::gp::operation_t op_cos(make_single([](float a) {
|
||||||
|
return (std::cos(a) + 1.0f) / 2.0f;
|
||||||
|
}), "cos");
|
||||||
|
inline blt::gp::operation_t op_atan(make_single((float (*)(float)) &std::atan), "atan");
|
||||||
|
inline blt::gp::operation_t op_exp(make_single((float (*)(float)) &std::exp), "exp");
|
||||||
|
inline blt::gp::operation_t op_abs(make_single((float (*)(float)) &std::abs), "abs");
|
||||||
|
inline blt::gp::operation_t op_log(make_single((float (*)(float)) &std::log), "log");
|
||||||
|
inline blt::gp::operation_t op_v_mod([](const full_image_t& a, const full_image_t& b) {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
img.rgb_data[i] = b.rgb_data[i] <= 0 ? 0 : static_cast<float>(blt::mem::type_cast<unsigned int>(a.rgb_data[i]) %
|
||||||
|
blt::mem::type_cast<unsigned int>(b.rgb_data[i]));
|
||||||
|
return img;
|
||||||
|
}, "v_mod");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t bitwise_and([](const full_image_t& a, const full_image_t& b) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
img.rgb_data[i] = static_cast<float>(type_cast<unsigned int>(a.rgb_data[i]) & type_cast<unsigned int>(b.rgb_data[i]));
|
||||||
|
return img;
|
||||||
|
}, "and");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t bitwise_or([](const full_image_t& a, const full_image_t& b) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
img.rgb_data[i] = static_cast<float>(type_cast<unsigned int>(a.rgb_data[i]) | type_cast<unsigned int>(b.rgb_data[i]));
|
||||||
|
return img;
|
||||||
|
}, "or");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t bitwise_invert([](const full_image_t& a) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
img.rgb_data[i] = static_cast<float>(~type_cast<unsigned int>(a.rgb_data[i]));
|
||||||
|
return img;
|
||||||
|
}, "invert");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t bitwise_xor([](const full_image_t& a, const full_image_t& b) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto in_a = type_cast<unsigned int>(a.rgb_data[i]);
|
||||||
|
auto in_b = type_cast<unsigned int>(b.rgb_data[i]);
|
||||||
|
img.rgb_data[i] = static_cast<float>(in_a ^ in_b);
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "xor");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t dissolve([](const full_image_t& a, const full_image_t& b) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto diff = (a.rgb_data[i] - b.rgb_data[i]) / 2.0f;
|
||||||
|
img.rgb_data[i] = a.rgb_data[i] + diff;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "dissolve");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t band_pass([](const full_image_t& a, float min, float max) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
{
|
||||||
|
if (a.rgb_data[i] >= min && a.rgb_data[i] <= max)
|
||||||
|
{
|
||||||
|
img.rgb_data[i] = a.rgb_data[i];
|
||||||
|
} else if (a.rgb_data[i] < min)
|
||||||
|
{
|
||||||
|
auto dist_min = min == 0 ? 0.0f : (a.rgb_data[i] / min);
|
||||||
|
img.rgb_data[i] = a.rgb_data[i] * dist_min;
|
||||||
|
} else if (a.rgb_data[i] > max)
|
||||||
|
{
|
||||||
|
auto dist_max = max == 0 ? 0.0f : ((a.rgb_data[i] - max) / max);
|
||||||
|
img.rgb_data[i] = a.rgb_data[i] * dist_max;
|
||||||
|
} else {
|
||||||
|
img.rgb_data[i] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "band_pass");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t hsv_to_rgb([](const full_image_t& a) {
|
||||||
|
using blt::mem::type_cast;
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto h = static_cast<blt::i32>(a.rgb_data[i * CHANNELS + 0]) % 360;
|
||||||
|
auto s = a.rgb_data[i * CHANNELS + 1];
|
||||||
|
auto v = a.rgb_data[i * CHANNELS + 2];
|
||||||
|
auto c = v * s;
|
||||||
|
auto x = c * static_cast<float>(1 - std::abs(((h / 60) % 2) - 1));
|
||||||
|
auto m = v - c;
|
||||||
|
|
||||||
|
blt::vec3 rgb;
|
||||||
|
if (h >= 0 && h < 60)
|
||||||
|
rgb = {c, x, 0.0f};
|
||||||
|
else if (h >= 60 && h < 120)
|
||||||
|
rgb = {x, c, 0.0f};
|
||||||
|
else if (h >= 120 && h < 180)
|
||||||
|
rgb = {0.0f, c, x};
|
||||||
|
else if (h >= 180 && h < 240)
|
||||||
|
rgb = {0.0f, x, c};
|
||||||
|
else if (h >= 240 && h < 300)
|
||||||
|
rgb = {x, 0.0f, c};
|
||||||
|
else if (h >= 300 && h < 360)
|
||||||
|
rgb = {c, 0.0f, x};
|
||||||
|
|
||||||
|
img.rgb_data[i * CHANNELS] = rgb.x() + m;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = rgb.y() + m;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = rgb.z() + m;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "hsv");
|
||||||
|
|
||||||
|
inline blt::gp::operation_t lit([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
auto r = program.get_random().get_float(0.0f, 1.0f);
|
||||||
|
auto g = program.get_random().get_float(0.0f, 1.0f);
|
||||||
|
auto b = program.get_random().get_float(0.0f, 1.0f);
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
img.rgb_data[i * CHANNELS] = r;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = g;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = b;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "lit");
|
||||||
|
inline blt::gp::operation_t random_val([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (auto& i : img.rgb_data)
|
||||||
|
i = program.get_random().get_float(0.0f, 1.0f);
|
||||||
|
return img;
|
||||||
|
}, "color_noise");
|
||||||
|
inline blt::gp::operation_t perlin([](const full_image_t& x, const full_image_t& y, const full_image_t& z, const full_image_t& scale) {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto s = scale.rgb_data[i];
|
||||||
|
img.rgb_data[i] = perlin_noise(x.rgb_data[i] / s, y.rgb_data[i] / s, z.rgb_data[i] / s);
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "perlin");
|
||||||
|
inline blt::gp::operation_t perlin_terminal([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i);
|
||||||
|
img.rgb_data[i] = perlin_noise(ctx.x / IMAGE_SIZE, ctx.y / IMAGE_SIZE, static_cast<float>(i % CHANNELS) / CHANNELS);
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "perlin_term");
|
||||||
|
inline blt::gp::operation_t perlin_warped([](const full_image_t& u, const full_image_t& v) {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i);
|
||||||
|
img.rgb_data[i] = perlin_noise(ctx.x / IMAGE_SIZE + u.rgb_data[i], ctx.y / IMAGE_SIZE + v.rgb_data[i],
|
||||||
|
static_cast<float>(i % CHANNELS) / CHANNELS);
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "perlin_warped");
|
||||||
|
inline blt::gp::operation_t op_img_size([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (float& i : img.rgb_data)
|
||||||
|
{
|
||||||
|
i = IMAGE_SIZE;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "img_size");
|
||||||
|
inline blt::gp::operation_t op_x_r([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).x;
|
||||||
|
img.rgb_data[i * CHANNELS] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = 0;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "x_r");
|
||||||
|
inline blt::gp::operation_t op_x_g([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).x;
|
||||||
|
img.rgb_data[i * CHANNELS] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = 0;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "x_g");
|
||||||
|
inline blt::gp::operation_t op_x_b([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).x;
|
||||||
|
img.rgb_data[i * CHANNELS] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = ctx;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "x_b");
|
||||||
|
inline blt::gp::operation_t op_x_rgb([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).x;
|
||||||
|
img.rgb_data[i * CHANNELS] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = ctx;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "x_rgb");
|
||||||
|
inline blt::gp::operation_t op_y_r([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).y;
|
||||||
|
img.rgb_data[i * CHANNELS] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = 0;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "y_r");
|
||||||
|
inline blt::gp::operation_t op_y_g([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).y;
|
||||||
|
img.rgb_data[i * CHANNELS] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = 0;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "y_g");
|
||||||
|
inline blt::gp::operation_t op_y_b([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).y;
|
||||||
|
img.rgb_data[i * CHANNELS] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = 0;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = ctx;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "y_b");
|
||||||
|
inline blt::gp::operation_t op_y_rgb([]() {
|
||||||
|
full_image_t img{};
|
||||||
|
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
||||||
|
{
|
||||||
|
auto ctx = get_ctx(i).y;
|
||||||
|
img.rgb_data[i * CHANNELS] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 1] = ctx;
|
||||||
|
img.rgb_data[i * CHANNELS + 2] = ctx;
|
||||||
|
}
|
||||||
|
return img;
|
||||||
|
}, "y_rgb");
|
||||||
|
|
||||||
|
template<typename context>
|
||||||
|
void create_image_operations(blt::gp::operator_builder<context>& builder)
|
||||||
|
{
|
||||||
|
builder.add_operator(perlin);
|
||||||
|
builder.add_operator(perlin_terminal);
|
||||||
|
builder.add_operator(perlin_warped);
|
||||||
|
|
||||||
|
builder.add_operator(add);
|
||||||
|
builder.add_operator(sub);
|
||||||
|
builder.add_operator(mul);
|
||||||
|
builder.add_operator(pro_div);
|
||||||
|
builder.add_operator(op_sin);
|
||||||
|
builder.add_operator(op_cos);
|
||||||
|
builder.add_operator(op_atan);
|
||||||
|
builder.add_operator(op_exp);
|
||||||
|
builder.add_operator(op_log);
|
||||||
|
builder.add_operator(op_abs);
|
||||||
|
builder.add_operator(op_v_mod);
|
||||||
|
builder.add_operator(bitwise_and);
|
||||||
|
builder.add_operator(bitwise_or);
|
||||||
|
builder.add_operator(bitwise_invert);
|
||||||
|
builder.add_operator(bitwise_xor);
|
||||||
|
builder.add_operator(dissolve);
|
||||||
|
builder.add_operator(band_pass);
|
||||||
|
builder.add_operator(hsv_to_rgb);
|
||||||
|
|
||||||
|
bool state = false;
|
||||||
|
builder.add_operator(lit, true);
|
||||||
|
builder.add_operator(random_val);
|
||||||
|
builder.add_operator(op_x_r, state);
|
||||||
|
builder.add_operator(op_x_g, state);
|
||||||
|
builder.add_operator(op_x_b, state);
|
||||||
|
builder.add_operator(op_x_rgb, state);
|
||||||
|
builder.add_operator(op_y_r, state);
|
||||||
|
builder.add_operator(op_y_g, state);
|
||||||
|
builder.add_operator(op_y_b, state);
|
||||||
|
builder.add_operator(op_y_rgb, state);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif //IMAGE_GP_6_IMAGE_OPERATIONS_H
|
328
src/main.cpp
328
src/main.cpp
|
@ -36,15 +36,17 @@
|
||||||
#include "opencv2/imgproc.hpp"
|
#include "opencv2/imgproc.hpp"
|
||||||
#include <random>
|
#include <random>
|
||||||
#include "slr.h"
|
#include "slr.h"
|
||||||
|
#include "float_operations.h"
|
||||||
#include <images.h>
|
#include <images.h>
|
||||||
#include <helper.h>
|
#include <helper.h>
|
||||||
|
#include <image_operations.h>
|
||||||
|
|
||||||
blt::gfx::matrix_state_manager global_matrices;
|
blt::gfx::matrix_state_manager global_matrices;
|
||||||
blt::gfx::resource_manager resources;
|
blt::gfx::resource_manager resources;
|
||||||
blt::gfx::batch_renderer_2d renderer_2d(resources, global_matrices);
|
blt::gfx::batch_renderer_2d renderer_2d(resources, global_matrices);
|
||||||
blt::gfx::first_person_camera_2d camera;
|
blt::gfx::first_person_camera_2d camera;
|
||||||
|
|
||||||
static constexpr blt::size_t TYPE_COUNT = 1;
|
static constexpr blt::size_t TYPE_COUNT = 2;
|
||||||
|
|
||||||
std::array<double, POP_SIZE> fitness_values{};
|
std::array<double, POP_SIZE> fitness_values{};
|
||||||
double last_fitness = 0;
|
double last_fitness = 0;
|
||||||
|
@ -53,6 +55,7 @@ double hovered_fitness_value = 0;
|
||||||
bool evaluate = true;
|
bool evaluate = true;
|
||||||
|
|
||||||
std::array<bool, TYPE_COUNT> has_literal_converter = {
|
std::array<bool, TYPE_COUNT> has_literal_converter = {
|
||||||
|
true,
|
||||||
true
|
true
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -69,6 +72,16 @@ std::array<std::function<void(blt::gp::gp_program& program, void*, void*, void*,
|
||||||
c1_out.rgb_data[i] = p1_in.rgb_data[i] - diff;
|
c1_out.rgb_data[i] = p1_in.rgb_data[i] - diff;
|
||||||
c2_out.rgb_data[i] = p2_in.rgb_data[i] + diff;
|
c2_out.rgb_data[i] = p2_in.rgb_data[i] + diff;
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
[](blt::gp::gp_program&, void* p1_in_ptr, void* p2_in_ptr, void* c1_out_ptr, void* c2_out_ptr) {
|
||||||
|
auto& p1_in = *static_cast<float*>(p1_in_ptr);
|
||||||
|
auto& p2_in = *static_cast<float*>(p2_in_ptr);
|
||||||
|
auto& c1_out = *static_cast<float*>(c1_out_ptr);
|
||||||
|
auto& c2_out = *static_cast<float*>(c2_out_ptr);
|
||||||
|
|
||||||
|
auto diff = p1_in - p2_in;
|
||||||
|
c1_out = p1_in - diff;
|
||||||
|
c2_out = p2_in + diff;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -79,49 +92,27 @@ std::array<std::function<void(blt::gp::gp_program& program, void*, void*)>, TYPE
|
||||||
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
||||||
c1_out.rgb_data[i] = p1_in.rgb_data[i] + program.get_random().get_float(-1.0f, 1.0f);
|
c1_out.rgb_data[i] = p1_in.rgb_data[i] + program.get_random().get_float(-1.0f, 1.0f);
|
||||||
|
},
|
||||||
|
[](blt::gp::gp_program& program, void* p1_in_ptr, void* c1_out_ptr) {
|
||||||
|
auto& p1_in = *static_cast<float*>(p1_in_ptr);
|
||||||
|
auto& c1_out = *static_cast<float*>(c1_out_ptr);
|
||||||
|
|
||||||
|
c1_out = p1_in + program.get_random().get_float(-1.0f, 1.0f);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class image_crossover_t : public blt::gp::crossover_t
|
class image_crossover_t : public blt::gp::crossover_t
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
blt::expected<result_t, error_t> apply(blt::gp::gp_program& program, const blt::gp::tree_t& p1, const blt::gp::tree_t& p2) final
|
blt::expected<result_t, error_t> apply(blt::gp::gp_program& prog, const blt::gp::tree_t& p1, const blt::gp::tree_t& p2) final
|
||||||
{
|
{
|
||||||
auto sel = program.get_random().choice();
|
auto sel = prog.get_random().choice();
|
||||||
if (sel)
|
if (sel)
|
||||||
return blt::gp::crossover_t::apply(program, p1, p2);
|
return blt::gp::crossover_t::apply(prog, p1, p2);
|
||||||
std::abort();
|
std::abort();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct context
|
|
||||||
{
|
|
||||||
float x, y;
|
|
||||||
};
|
|
||||||
|
|
||||||
inline context get_ctx(blt::size_t i)
|
|
||||||
{
|
|
||||||
context ctx{};
|
|
||||||
i /= CHANNELS;
|
|
||||||
ctx.y = std::floor(static_cast<float>(i) / static_cast<float>(IMAGE_SIZE));
|
|
||||||
ctx.x = static_cast<float>(i) - (ctx.y * IMAGE_SIZE);
|
|
||||||
return ctx;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline context get_pop_ctx(blt::size_t i)
|
|
||||||
{
|
|
||||||
auto const sq = static_cast<float>(std::sqrt(POP_SIZE));
|
|
||||||
context ctx{};
|
|
||||||
ctx.y = std::floor(static_cast<float>(i) / static_cast<float>(sq));
|
|
||||||
ctx.x = static_cast<float>(i) - (ctx.y * sq);
|
|
||||||
return ctx;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline blt::size_t get_index(blt::size_t x, blt::size_t y)
|
|
||||||
{
|
|
||||||
return y * IMAGE_SIZE + x;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::array<full_image_t, POP_SIZE> generation_images;
|
std::array<full_image_t, POP_SIZE> generation_images;
|
||||||
|
|
||||||
full_image_t base_image;
|
full_image_t base_image;
|
||||||
|
@ -129,240 +120,8 @@ blt::size_t last_run = 0;
|
||||||
blt::i32 time_between_runs = 16;
|
blt::i32 time_between_runs = 16;
|
||||||
bool is_running = false;
|
bool is_running = false;
|
||||||
|
|
||||||
blt::gp::type_provider type_system;
|
|
||||||
blt::gp::gp_program program{type_system, SEED, config};
|
|
||||||
std::unique_ptr<std::thread> gp_thread = nullptr;
|
std::unique_ptr<std::thread> gp_thread = nullptr;
|
||||||
|
|
||||||
blt::gp::operation_t add(make_double(std::plus()), "add");
|
|
||||||
blt::gp::operation_t sub(make_double(std::minus()), "sub");
|
|
||||||
blt::gp::operation_t mul(make_double(std::multiplies()), "mul");
|
|
||||||
blt::gp::operation_t pro_div([](const full_image_t& a, const full_image_t& b) {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
img.rgb_data[i] = b.rgb_data[i] == 0 ? 0 : (a.rgb_data[i] / b.rgb_data[i]);
|
|
||||||
return img;
|
|
||||||
}, "div");
|
|
||||||
blt::gp::operation_t op_sin(make_single([](float a) {
|
|
||||||
return (std::sin(a) + 1.0f) / 2.0f;
|
|
||||||
}), "sin");
|
|
||||||
blt::gp::operation_t op_cos(make_single([](float a) {
|
|
||||||
return (std::cos(a) + 1.0f) / 2.0f;
|
|
||||||
}), "cos");
|
|
||||||
blt::gp::operation_t op_atan(make_single((float (*)(float)) &std::atan), "atan");
|
|
||||||
blt::gp::operation_t op_exp(make_single((float (*)(float)) &std::exp), "exp");
|
|
||||||
blt::gp::operation_t op_abs(make_single((float (*)(float)) &std::abs), "abs");
|
|
||||||
blt::gp::operation_t op_log(make_single((float (*)(float)) &std::log), "log");
|
|
||||||
blt::gp::operation_t op_v_mod([](const full_image_t& a, const full_image_t& b) {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
img.rgb_data[i] = b.rgb_data[i] <= 0 ? 0 : static_cast<float>(blt::mem::type_cast<unsigned int>(a.rgb_data[i]) %
|
|
||||||
blt::mem::type_cast<unsigned int>(b.rgb_data[i]));
|
|
||||||
return img;
|
|
||||||
}, "v_mod");
|
|
||||||
|
|
||||||
blt::gp::operation_t bitwise_and([](const full_image_t& a, const full_image_t& b) {
|
|
||||||
using blt::mem::type_cast;
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
img.rgb_data[i] = static_cast<float>(type_cast<unsigned int>(a.rgb_data[i]) & type_cast<unsigned int>(b.rgb_data[i]));
|
|
||||||
return img;
|
|
||||||
}, "and");
|
|
||||||
|
|
||||||
blt::gp::operation_t bitwise_or([](const full_image_t& a, const full_image_t& b) {
|
|
||||||
using blt::mem::type_cast;
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
img.rgb_data[i] = static_cast<float>(type_cast<unsigned int>(a.rgb_data[i]) | type_cast<unsigned int>(b.rgb_data[i]));
|
|
||||||
return img;
|
|
||||||
}, "or");
|
|
||||||
|
|
||||||
blt::gp::operation_t bitwise_invert([](const full_image_t& a) {
|
|
||||||
using blt::mem::type_cast;
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
img.rgb_data[i] = static_cast<float>(~type_cast<unsigned int>(a.rgb_data[i]));
|
|
||||||
return img;
|
|
||||||
}, "invert");
|
|
||||||
|
|
||||||
blt::gp::operation_t bitwise_xor([](const full_image_t& a, const full_image_t& b) {
|
|
||||||
using blt::mem::type_cast;
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto in_a = type_cast<unsigned int>(a.rgb_data[i]);
|
|
||||||
auto in_b = type_cast<unsigned int>(b.rgb_data[i]);
|
|
||||||
img.rgb_data[i] = static_cast<float>(in_a ^ in_b);
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "xor");
|
|
||||||
|
|
||||||
blt::gp::operation_t dissolve([](const full_image_t& a, const full_image_t& b) {
|
|
||||||
using blt::mem::type_cast;
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto diff = (a.rgb_data[i] - b.rgb_data[i]) / 2.0f;
|
|
||||||
img.rgb_data[i] = a.rgb_data[i] + diff;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "dissolve");
|
|
||||||
|
|
||||||
blt::gp::operation_t hsv_to_rgb([](const full_image_t& a) {
|
|
||||||
using blt::mem::type_cast;
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto h = static_cast<blt::i32>(a.rgb_data[i * CHANNELS + 0]) % 360;
|
|
||||||
auto s = a.rgb_data[i * CHANNELS + 1];
|
|
||||||
auto v = a.rgb_data[i * CHANNELS + 2];
|
|
||||||
auto c = v * s;
|
|
||||||
auto x = c * static_cast<float>(1 - std::abs(((h / 60) % 2) - 1));
|
|
||||||
auto m = v - c;
|
|
||||||
|
|
||||||
blt::vec3 rgb;
|
|
||||||
if (h >= 0 && h < 60)
|
|
||||||
rgb = {c, x, 0.0f};
|
|
||||||
else if (h >= 60 && h < 120)
|
|
||||||
rgb = {x, c, 0.0f};
|
|
||||||
else if (h >= 120 && h < 180)
|
|
||||||
rgb = {0.0f, c, x};
|
|
||||||
else if (h >= 180 && h < 240)
|
|
||||||
rgb = {0.0f, x, c};
|
|
||||||
else if (h >= 240 && h < 300)
|
|
||||||
rgb = {x, 0.0f, c};
|
|
||||||
else if (h >= 300 && h < 360)
|
|
||||||
rgb = {c, 0.0f, x};
|
|
||||||
|
|
||||||
img.rgb_data[i * CHANNELS] = rgb.x() + m;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = rgb.y() + m;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = rgb.z() + m;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "hsv");
|
|
||||||
|
|
||||||
blt::gp::operation_t lit([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
auto r = program.get_random().get_float(0.0f, 1.0f);
|
|
||||||
auto g = program.get_random().get_float(0.0f, 1.0f);
|
|
||||||
auto b = program.get_random().get_float(0.0f, 1.0f);
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
img.rgb_data[i * CHANNELS] = r;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = g;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = b;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "lit");
|
|
||||||
blt::gp::operation_t random_val([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (auto& i : img.rgb_data)
|
|
||||||
i = program.get_random().get_float(0.0f, 1.0f);
|
|
||||||
return img;
|
|
||||||
}, "color_noise");
|
|
||||||
static blt::gp::operation_t perlin([](const full_image_t& x, const full_image_t& y, const full_image_t& z, const full_image_t& scale) {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto s = scale.rgb_data[i];
|
|
||||||
img.rgb_data[i] = stb_perlin_noise3(x.rgb_data[i] / s, y.rgb_data[i] / s, z.rgb_data[i] / s, 0, 0, 0);
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "perlin");
|
|
||||||
static blt::gp::operation_t perlin_terminal([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i);
|
|
||||||
img.rgb_data[i] =
|
|
||||||
stb_perlin_noise3(ctx.x / IMAGE_SIZE, ctx.y / IMAGE_SIZE, static_cast<float>(i % CHANNELS) / CHANNELS, 0, 0, 0);
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "perlin_term");
|
|
||||||
static blt::gp::operation_t perlin_warped([](const full_image_t& u, const full_image_t& v) {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_CHANNELS_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i);
|
|
||||||
img.rgb_data[i] = stb_perlin_noise3(ctx.x / IMAGE_SIZE + u.rgb_data[i], ctx.y / IMAGE_SIZE + v.rgb_data[i],
|
|
||||||
static_cast<float>(i % CHANNELS) / CHANNELS, 0, 0, 0);
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "perlin_warped");
|
|
||||||
static blt::gp::operation_t op_img_size([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (float& i : img.rgb_data)
|
|
||||||
{
|
|
||||||
i = IMAGE_SIZE;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "img_size");
|
|
||||||
static blt::gp::operation_t op_x_r([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i).x;
|
|
||||||
img.rgb_data[i * CHANNELS] = ctx;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = 0;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "x_r");
|
|
||||||
static blt::gp::operation_t op_x_g([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i).x;
|
|
||||||
img.rgb_data[i * CHANNELS] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = ctx;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = 0;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "x_g");
|
|
||||||
static blt::gp::operation_t op_x_b([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i).x;
|
|
||||||
img.rgb_data[i * CHANNELS] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = ctx;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "x_b");
|
|
||||||
static blt::gp::operation_t op_y_r([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i).y;
|
|
||||||
img.rgb_data[i * CHANNELS] = ctx;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = 0;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "y_r");
|
|
||||||
static blt::gp::operation_t op_y_g([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i).y;
|
|
||||||
img.rgb_data[i * CHANNELS] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = ctx;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = 0;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "y_g");
|
|
||||||
static blt::gp::operation_t op_y_b([]() {
|
|
||||||
full_image_t img{};
|
|
||||||
for (blt::size_t i = 0; i < DATA_SIZE; i++)
|
|
||||||
{
|
|
||||||
auto ctx = get_ctx(i).y;
|
|
||||||
img.rgb_data[i * CHANNELS] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 1] = 0;
|
|
||||||
img.rgb_data[i * CHANNELS + 2] = ctx;
|
|
||||||
}
|
|
||||||
return img;
|
|
||||||
}, "y_b");
|
|
||||||
|
|
||||||
constexpr float compare_values(float a, float b)
|
constexpr float compare_values(float a, float b)
|
||||||
{
|
{
|
||||||
if (std::isnan(a) || std::isnan(b) || std::isinf(a) || std::isinf(b))
|
if (std::isnan(a) || std::isnan(b) || std::isinf(a) || std::isinf(b))
|
||||||
|
@ -561,39 +320,11 @@ void init(const blt::gfx::window_data&)
|
||||||
|
|
||||||
BLT_DEBUG("Setup Types and Operators");
|
BLT_DEBUG("Setup Types and Operators");
|
||||||
type_system.register_type<full_image_t>();
|
type_system.register_type<full_image_t>();
|
||||||
|
type_system.register_type<float>();
|
||||||
|
|
||||||
blt::gp::operator_builder<context> builder{type_system};
|
blt::gp::operator_builder<context> builder{type_system};
|
||||||
builder.add_operator(perlin);
|
create_image_operations(builder);
|
||||||
builder.add_operator(perlin_terminal);
|
create_float_operations(builder);
|
||||||
builder.add_operator(perlin_warped);
|
|
||||||
|
|
||||||
builder.add_operator(add);
|
|
||||||
builder.add_operator(sub);
|
|
||||||
builder.add_operator(mul);
|
|
||||||
builder.add_operator(pro_div);
|
|
||||||
builder.add_operator(op_sin);
|
|
||||||
builder.add_operator(op_cos);
|
|
||||||
builder.add_operator(op_atan);
|
|
||||||
builder.add_operator(op_exp);
|
|
||||||
builder.add_operator(op_log);
|
|
||||||
builder.add_operator(op_abs);
|
|
||||||
builder.add_operator(op_v_mod);
|
|
||||||
builder.add_operator(bitwise_and);
|
|
||||||
builder.add_operator(bitwise_or);
|
|
||||||
builder.add_operator(bitwise_invert);
|
|
||||||
builder.add_operator(bitwise_xor);
|
|
||||||
builder.add_operator(dissolve);
|
|
||||||
builder.add_operator(hsv_to_rgb);
|
|
||||||
|
|
||||||
builder.add_operator(lit, true);
|
|
||||||
builder.add_operator(random_val);
|
|
||||||
const bool state = false;
|
|
||||||
builder.add_operator(op_x_r, true);
|
|
||||||
builder.add_operator(op_x_g, true);
|
|
||||||
builder.add_operator(op_x_b, state);
|
|
||||||
builder.add_operator(op_y_r, state);
|
|
||||||
builder.add_operator(op_y_g, state);
|
|
||||||
builder.add_operator(op_y_b, state);
|
|
||||||
|
|
||||||
program.set_operations(builder.build());
|
program.set_operations(builder.build());
|
||||||
|
|
||||||
|
@ -636,8 +367,9 @@ void update(const blt::gfx::window_data& data)
|
||||||
const auto mouse_pos = blt::make_vec2(blt::gfx::calculateRay2D(data.width, data.height, global_matrices.getScale2D(), global_matrices.getView2D(),
|
const auto mouse_pos = blt::make_vec2(blt::gfx::calculateRay2D(data.width, data.height, global_matrices.getScale2D(), global_matrices.getView2D(),
|
||||||
global_matrices.getOrtho()));
|
global_matrices.getOrtho()));
|
||||||
|
|
||||||
for (blt::size_t i = 0; i < config.population_size; i++)
|
for (blt::size_t i = 0; i < program.get_current_pop().get_individuals().size(); i++)
|
||||||
{
|
{
|
||||||
|
auto& ind = program.get_current_pop().get_individuals()[i];
|
||||||
auto ctx = get_pop_ctx(i);
|
auto ctx = get_pop_ctx(i);
|
||||||
float x = ctx.x * IMAGE_SIZE + ctx.x * IMAGE_PADDING;
|
float x = ctx.x * IMAGE_SIZE + ctx.x * IMAGE_PADDING;
|
||||||
float y = ctx.y * IMAGE_SIZE + ctx.y * IMAGE_PADDING;
|
float y = ctx.y * IMAGE_SIZE + ctx.y * IMAGE_PADDING;
|
||||||
|
@ -652,7 +384,6 @@ void update(const blt::gfx::window_data& data)
|
||||||
renderer_2d.drawRectangleInternal(blt::make_color(0.9, 0.9, 0.3),
|
renderer_2d.drawRectangleInternal(blt::make_color(0.9, 0.9, 0.3),
|
||||||
{x, y, IMAGE_SIZE + IMAGE_PADDING / 2.0f, IMAGE_SIZE + IMAGE_PADDING / 2.0f},
|
{x, y, IMAGE_SIZE + IMAGE_PADDING / 2.0f, IMAGE_SIZE + IMAGE_PADDING / 2.0f},
|
||||||
10.0f);
|
10.0f);
|
||||||
auto& ind = program.get_current_pop().get_individuals()[i];
|
|
||||||
|
|
||||||
auto& io = ImGui::GetIO();
|
auto& io = ImGui::GetIO();
|
||||||
|
|
||||||
|
@ -681,8 +412,9 @@ void update(const blt::gfx::window_data& data)
|
||||||
hovered_fitness_value = fitness_values[i];
|
hovered_fitness_value = fitness_values[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto val = static_cast<float>(ind.fitness.adjusted_fitness);
|
||||||
renderer_2d.drawRectangleInternal(
|
renderer_2d.drawRectangleInternal(
|
||||||
blt::make_vec4(blt::vec3(static_cast<float>(program.get_current_pop().get_individuals()[i].fitness.adjusted_fitness)), 1.0),
|
blt::make_color(val, val, val),
|
||||||
{x, y, IMAGE_SIZE + IMAGE_PADDING / 2.0f, IMAGE_SIZE + IMAGE_PADDING / 2.0f},
|
{x, y, IMAGE_SIZE + IMAGE_PADDING / 2.0f, IMAGE_SIZE + IMAGE_PADDING / 2.0f},
|
||||||
5.0f);
|
5.0f);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue