diff --git a/.github/workflows/darwin.yml b/.github/workflows/darwin.yml index 2151810..c865cf5 100644 --- a/.github/workflows/darwin.yml +++ b/.github/workflows/darwin.yml @@ -13,8 +13,8 @@ jobs: - { os: "macos-12", xcode: "13.4.1", arch: "x64" } - { os: "macos-13", xcode: "14.3.1", arch: "x64" } - { os: "macos-13", xcode: "14.3.1", arch: "arm64" } - - { os: "macos-14", xcode: "15.2", arch: "x64" } - - { os: "macos-14", xcode: "15.2", arch: "arm64" } + - { os: "macos-14", xcode: "15.4", arch: "x64" } + - { os: "macos-14", xcode: "15.4", arch: "arm64" } name: "xcode-${{matrix.config.xcode}}-${{matrix.config.arch}}" steps: - name: Setup diff --git a/.github/workflows/linux.yml b/.github/workflows/linux.yml index bc1a603..68f3f1b 100644 --- a/.github/workflows/linux.yml +++ b/.github/workflows/linux.yml @@ -12,8 +12,8 @@ jobs: # https://github.com/actions/runner-images/tree/main/images/ubuntu - { os: "ubuntu-20.04", cc: "gcc-10", cxx: "g++-10" } - { os: "ubuntu-20.04", cc: "clang-10", cxx: "clang++-10" } - - { os: "ubuntu-22.04", cc: "gcc-13", cxx: "g++-13" } - - { os: "ubuntu-22.04", cc: "clang-15", cxx: "clang++-15" } + - { os: "ubuntu-24.04", cc: "gcc-14", cxx: "g++-14" } + - { os: "ubuntu-24.04", cc: "clang-18", cxx: "clang++-18" } name: "${{matrix.config.cxx}}" steps: - name: Setup diff --git a/CMakePresets.json b/CMakePresets.json index 1d6ddf4..1be62dd 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -35,11 +35,11 @@ } }, { - "name": "linux-clang-15", + "name": "linux-clang-18", "inherits": "linux-base", "cacheVariables": { - "CMAKE_C_COMPILER": "clang-15", - "CMAKE_CXX_COMPILER": "clang++-15" + "CMAKE_C_COMPILER": "clang-18", + "CMAKE_CXX_COMPILER": "clang++-18" } }, { @@ -51,11 +51,11 @@ } }, { - "name": "linux-gcc-13", + "name": "linux-gcc-14", "inherits": "linux-base", "cacheVariables": { - "CMAKE_C_COMPILER": "gcc-13", - "CMAKE_CXX_COMPILER": "g++-13" + "CMAKE_C_COMPILER": "gcc-14", + "CMAKE_CXX_COMPILER": "g++-14" } }, { @@ -213,14 +213,14 @@ "configurePreset": "linux-clang-10" }, { - "name": "linux-clang-15-debug", + "name": "linux-clang-18-debug", "configuration": "Debug", - "configurePreset": "linux-clang-15" + "configurePreset": "linux-clang-18" }, { - "name": "linux-clang-15-release", + "name": "linux-clang-18-release", "configuration": "Release", - "configurePreset": "linux-clang-15" + "configurePreset": "linux-clang-18" }, { "name": "linux-gcc-10-debug", @@ -233,14 +233,14 @@ "configurePreset": "linux-gcc-10" }, { - "name": "linux-gcc-13-debug", + "name": "linux-gcc-14-debug", "configuration": "Debug", - "configurePreset": "linux-gcc-13" + "configurePreset": "linux-gcc-14" }, { - "name": "linux-gcc-13-release", + "name": "linux-gcc-14-release", "configuration": "Release", - "configurePreset": "linux-gcc-13" + "configurePreset": "linux-gcc-14" }, { "name": "macos-arm64-debug", @@ -347,9 +347,9 @@ "configurePreset": "linux-clang-10" }, { - "name": "linux-clang-15", + "name": "linux-clang-18", "inherits": "test-base", - "configurePreset": "linux-clang-15" + "configurePreset": "linux-clang-18" }, { "name": "linux-gcc-10", @@ -357,9 +357,9 @@ "configurePreset": "linux-gcc-10" }, { - "name": "linux-gcc-13", + "name": "linux-gcc-14", "inherits": "test-base", - "configurePreset": "linux-gcc-13" + "configurePreset": "linux-gcc-14" }, { "name": "macos-arm64", diff --git a/ROADMAP.md b/ROADMAP.md index 8a5e91b..3777bcf 100644 --- a/ROADMAP.md +++ b/ROADMAP.md @@ -3,6 +3,7 @@ ## Backlog - add coverage information +- add an ucast function with a dynamic `to` argument ## Version 1.0 diff --git a/develop/cmake/SetupTargets.cmake b/develop/cmake/SetupTargets.cmake index 87b5573..0c4c323 100644 --- a/develop/cmake/SetupTargets.cmake +++ b/develop/cmake/SetupTargets.cmake @@ -14,7 +14,10 @@ target_compile_options(${PROJECT_NAME}.setup_targets INTERFACE -Wno-exit-time-destructors -Wno-global-constructors -Wno-padded + -Wno-switch-default + -Wno-unknown-warning-option -Wno-unneeded-internal-declaration + -Wno-unsafe-buffer-usage -Wno-unused-macros -Wno-unused-member-function -Wno-weak-vtables diff --git a/develop/manuals/meta_examples/ucast_example.cpp b/develop/manuals/meta_examples/ucast_example.cpp index 4fd482c..52aec9c 100644 --- a/develop/manuals/meta_examples/ucast_example.cpp +++ b/develop/manuals/meta_examples/ucast_example.cpp @@ -18,11 +18,15 @@ namespace // like `ucast` or `resolve_type(T&&)` struct A { + A() = default; + A(const A&) = default; virtual ~A() = default; META_HPP_ENABLE_POLY_INFO() }; struct B { + B() = default; + B(const B&) = default; virtual ~B() = default; META_HPP_ENABLE_POLY_INFO() }; diff --git a/develop/singles/headers/meta.hpp/meta_all.hpp b/develop/singles/headers/meta.hpp/meta_all.hpp index 8772f07..12f7971 100644 --- a/develop/singles/headers/meta.hpp/meta_all.hpp +++ b/develop/singles/headers/meta.hpp/meta_all.hpp @@ -4679,6 +4679,12 @@ private: META_HPP_ENABLE_BASE_INFO(__VA_ARGS__) \ public: \ META_HPP_DETAIL_IGNORE_OVERRIDE_WARNINGS_PUSH() \ + virtual ::meta_hpp::uvalue meta_poly_ptr() { \ + return ::meta_hpp::uvalue{this}; \ + } \ + virtual ::meta_hpp::uvalue meta_poly_ptr() const { \ + return ::meta_hpp::uvalue{this}; \ + } \ virtual ::meta_hpp::detail::poly_info meta_poly_info(::meta_hpp::detail::type_registry& registry) const { \ using self_type = std::remove_cvref_t; \ return ::meta_hpp::detail::poly_info{.ptr = this, .type = registry.resolve_by_type()}; \ diff --git a/develop/untests/meta_issues/github_discussion_88.cpp b/develop/untests/meta_issues/github_discussion_88.cpp new file mode 100644 index 0000000..4aee3af --- /dev/null +++ b/develop/untests/meta_issues/github_discussion_88.cpp @@ -0,0 +1,74 @@ +/******************************************************************************* + * This file is part of the "https://github.com/blackmatov/meta.hpp" + * For conditions of distribution and use, see copyright notice in LICENSE.md + * Copyright (C) 2021-2024, by Matvey Cherevko (blackmatov@gmail.com) + ******************************************************************************/ + +#include +#include + +namespace +{ + struct component { + component() = default; + component(const component&) = default; + virtual ~component() = default; + META_HPP_ENABLE_POLY_INFO() + }; + + struct position_component : component { + META_HPP_ENABLE_POLY_INFO(component) + public: + explicit position_component(int nx, int ny) : x{nx}, y{ny} {} + + int x{}; + int y{}; + }; +} + +TEST_CASE("meta/meta_discussion/88") { + namespace meta = meta_hpp; + + meta::class_() + .member_("x", &position_component::x, meta::member_policy::as_pointer) + .member_("y", &position_component::y, meta::member_policy::as_pointer); + + position_component position{21, 42}; + + std::vector components{&position}; + + for (component* c : components) { + // meta_poly_ptr returns a pointer of the most derived type (position_component* in this case) + meta::uvalue derived_instance_ptr = c->meta_poly_ptr(); + meta::any_type derived_instance_ptr_type = derived_instance_ptr.get_type(); + CHECK(derived_instance_ptr_type == meta::resolve_type()); + + // to get all members of the component we should extract a class type from the pointer (position_component) + meta::class_type derived_instance_type = derived_instance_ptr_type.as_pointer().get_data_type().as_class(); + CHECK(derived_instance_type == meta::resolve_type()); + + // for each member we can show our debug inspector (imgui input for example) + for (const meta::member& m : derived_instance_type.get_members()) { + // we registered members as pointers (member_policy::as_pointer), so the type of the member is a pointer + CHECK(m.get_type() == meta::resolve_type()); + CHECK(m.get_type().get_value_type() == meta::resolve_type()); + + // Note: + // We can register members without any policy then member::get will return copy of this member value, + // and to change this member we will have to call member::set function. + // But in this case we will change values in-place by a pointer + + meta::uvalue value = m.get(derived_instance_ptr); + CHECK(value.get_type() == meta::resolve_type()); + + int* raw_value = value.as(); + + // here we can show the value on the screen or change it + CHECK((*raw_value == 21 || *raw_value == 42)); + *raw_value = 84; + } + + CHECK(position.x == 84); + CHECK(position.y == 84); + } +} diff --git a/develop/untests/meta_types/poly_resolving2_tests.cpp b/develop/untests/meta_types/poly_resolving2_tests.cpp index a47c223..457b1e9 100644 --- a/develop/untests/meta_types/poly_resolving2_tests.cpp +++ b/develop/untests/meta_types/poly_resolving2_tests.cpp @@ -13,6 +13,8 @@ namespace struct derived : base {}; struct poly_base { + poly_base() = default; + poly_base(const poly_base&) = default; virtual ~poly_base() = default; META_HPP_ENABLE_POLY_INFO() }; diff --git a/develop/untests/meta_types/poly_resolving_tests.cpp b/develop/untests/meta_types/poly_resolving_tests.cpp index b36284b..46d969c 100644 --- a/develop/untests/meta_types/poly_resolving_tests.cpp +++ b/develop/untests/meta_types/poly_resolving_tests.cpp @@ -9,6 +9,8 @@ namespace { struct A { + A() = default; + A(const A&) = default; virtual ~A() = default; META_HPP_ENABLE_POLY_INFO() }; diff --git a/headers/meta.hpp/meta_detail/base_info.hpp b/headers/meta.hpp/meta_detail/base_info.hpp index e2a5c44..e6b2e6c 100644 --- a/headers/meta.hpp/meta_detail/base_info.hpp +++ b/headers/meta.hpp/meta_detail/base_info.hpp @@ -8,6 +8,7 @@ #include "../meta_base.hpp" #include "../meta_types.hpp" +#include "../meta_uvalue.hpp" #include "type_registry.hpp" @@ -45,6 +46,12 @@ private: META_HPP_ENABLE_BASE_INFO(__VA_ARGS__) \ public: \ META_HPP_DETAIL_IGNORE_OVERRIDE_WARNINGS_PUSH() \ + virtual ::meta_hpp::uvalue meta_poly_ptr() { \ + return ::meta_hpp::uvalue{this}; \ + } \ + virtual ::meta_hpp::uvalue meta_poly_ptr() const { \ + return ::meta_hpp::uvalue{this}; \ + } \ virtual ::meta_hpp::detail::poly_info meta_poly_info(::meta_hpp::detail::type_registry& registry) const { \ using self_type = std::remove_cvref_t; \ return ::meta_hpp::detail::poly_info{.ptr = this, .type = registry.resolve_by_type()}; \