intermediate commit
Signed-off-by: Folling <mail@folling.io>
This commit is contained in:
parent
52580a4382
commit
2ab0109355
37 changed files with 131 additions and 1544 deletions
|
|
@ -1,151 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file blueprint_folder.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup blueprints Blueprints
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief A blueprint folder, storing blueprints and other blueprint folders.
|
|
||||||
struct IkarusBlueprintFolder;
|
|
||||||
|
|
||||||
/// \brief Creates a blueprint folder.
|
|
||||||
/// \param project The project the blueprint folder is part of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param parent The parent folder of the blueprint folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the blueprint folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the blueprint folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
/// \return The created blueprint folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API IkarusBlueprintFolder * ikarus_blueprint_folder_create(
|
|
||||||
struct IkarusProject * project, IkarusBlueprintFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Copies a blueprint folder.
|
|
||||||
/// \details Creates a copy of the blueprint folder without its children.
|
|
||||||
/// \param blueprint_folder The blueprint folder to copy.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param parent The parent folder of the blueprint folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the blueprint folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the blueprint folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
/// \return The created blueprint folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API IkarusBlueprintFolder * ikarus_blueprint_folder_copy(
|
|
||||||
IkarusBlueprintFolder * blueprint_folder, IkarusBlueprintFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Deletes a blueprint folder and all its children
|
|
||||||
/// \param blueprint_folder The blueprint folder to delete.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param keep_children If true, the children of the blueprint folder will be moved to the parent folder.
|
|
||||||
IKA_API void ikarus_blueprint_folder_delete(IkarusBlueprintFolder * blueprint_folder, bool keep_children);
|
|
||||||
|
|
||||||
/// \brief Gets the project of a blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to get the project of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The project of the blueprint folder or null if an error occurs.
|
|
||||||
IKA_API struct IkarusProject * ikarus_blueprint_folder_get_project(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the parent folder of a blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to get the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The parent folder of the blueprint folder or null if an error occurs.
|
|
||||||
IKA_API struct IkarusBlueprintFolder * ikarus_blueprint_folder_get_parent(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the position of a blueprint folder within its parent folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to get the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The position of the blueprint folder or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_blueprint_folder_get_position(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the name of a blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to get the name of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The name of the blueprint folder or null if an error occurs.
|
|
||||||
/// \remark The returned pointer is valid until the blueprint folder is freed but may be invalidated by other operations.
|
|
||||||
IKA_API char const * ikarus_blueprint_folder_get_name(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the number of children of a blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to get the number of children of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The number of children or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_blueprint_folder_get_child_count(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the children of a blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to get the children of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param children_out The buffer to write the children to.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \param children_out_size The size of the buffer.
|
|
||||||
IKA_API void ikarus_blueprint_folder_get_children(
|
|
||||||
IkarusBlueprintFolder const * blueprint_folder, struct IkarusBlueprintTreeItem ** children_out, size_t children_out_size
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the parent folder of an blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to set the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_parent The new parent folder of the blueprint folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the blueprint folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of old and new siblings.
|
|
||||||
IKA_API void ikarus_blueprint_folder_set_parent(
|
|
||||||
IkarusBlueprintFolder * blueprint_folder, struct IkarusEntityFolder * new_parent, size_t new_position
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the position of an blueprint folder within its parent folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to set the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the blueprint folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of siblings.
|
|
||||||
IKA_API void ikarus_blueprint_folder_set_position(IkarusBlueprintFolder * blueprint_folder, size_t new_position);
|
|
||||||
|
|
||||||
/// \brief Sets the name of an blueprint folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to set the name of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_name The new name of the blueprint folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
IKA_API void ikarus_blueprint_folder_set_name(IkarusBlueprintFolder * blueprint_folder, char const * new_name);
|
|
||||||
|
|
||||||
/// \brief Converts a blueprint folder to a generic folder.
|
|
||||||
/// \param blueprint_folder The blueprint folder to convert.
|
|
||||||
/// \return The constructed folder, representing the blueprint folder.
|
|
||||||
IKA_API struct IkarusFolder * ikarus_blueprint_folder_to_folder(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
/// \brief Converts a blueprint folder to an object.
|
|
||||||
/// \param blueprint_folder The blueprint folder to convert.
|
|
||||||
/// \return The constructed object, representing the blueprint folder.
|
|
||||||
IKA_API struct IkarusObject * ikarus_blueprint_folder_to_object(IkarusBlueprintFolder const * blueprint_folder);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
// @}
|
|
||||||
|
|
@ -1,31 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file blueprint_tree_item.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup blueprints Blueprints
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
struct IkarusBlueprintTreeItem;
|
|
||||||
|
|
||||||
/// \brief Visits a blueprint tree item, calling the appropriate visitor function.
|
|
||||||
/// \param item The item to visit.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param blueprint_visitor The visitor function called if the item is a blueprint. Skipped if null.
|
|
||||||
/// \param blueprint_folder_visitor The visitor function called if the item is a blueprint folder. Skipped if null.
|
|
||||||
/// \param data The data passed to the visitor functions.
|
|
||||||
IKA_API void ikarus_blueprint_tree_item_visit(
|
|
||||||
struct IkarusBlueprintTreeItem * item,
|
|
||||||
void (*blueprint_visitor)(struct IkarusBlueprint * blueprint, void * data),
|
|
||||||
void (*blueprint_folder_visitor)(struct IkarusBlueprintFolder * folder, void * data),
|
|
||||||
void * data
|
|
||||||
);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
/// @}
|
|
||||||
|
|
@ -1,151 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file entity_folder.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup entities Entities
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief A entity folder, storing entities and other entity folders.
|
|
||||||
struct IkarusEntityFolder;
|
|
||||||
|
|
||||||
/// \brief Creates a entity folder.
|
|
||||||
/// \param project The project the entity folder is part of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param parent The parent folder of the entity folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the entity folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the entity folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
/// \return The created entity folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API IkarusEntityFolder * ikarus_entity_folder_create(
|
|
||||||
struct IkarusProject * project, IkarusEntityFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Copies a entity folder.
|
|
||||||
/// \details Creates a copy of the entity folder without its children.
|
|
||||||
/// \param entity_folder The entity folder to copy.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param parent The parent folder of the entity folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the entity folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the entity folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
/// \return The created entity folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API IkarusEntityFolder * ikarus_entity_folder_copy(
|
|
||||||
IkarusEntityFolder * entity_folder, IkarusEntityFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Deletes a entity folder and all its children
|
|
||||||
/// \param entity_folder The entity folder to delete.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param keep_children If true, the children of the entity folder will be moved to the parent folder.
|
|
||||||
IKA_API void ikarus_entity_folder_delete(IkarusEntityFolder * entity_folder, bool keep_children);
|
|
||||||
|
|
||||||
/// \brief Gets the project of a entity folder.
|
|
||||||
/// \param entity_folder The entity folder to get the project of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The project of the entity folder or null if an error occurs.
|
|
||||||
IKA_API struct IkarusProject * ikarus_entity_folder_get_project(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the parent folder of a entity folder.
|
|
||||||
/// \param entity_folder The entity folder to get the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The parent folder of the entity folder or null if an error occurs.
|
|
||||||
IKA_API struct IkarusEntityFolder * ikarus_entity_folder_get_parent(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the position of a entity folder within its parent folder.
|
|
||||||
/// \param entity_folder The entity folder to get the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The position of the entity folder or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_entity_folder_get_position(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the name of a entity folder.
|
|
||||||
/// \param entity_folder The entity folder to get the name of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The name of the entity folder or null if an error occurs.
|
|
||||||
/// \remark The returned pointer is valid until the entity folder is freed but may be invalidated by other operations.
|
|
||||||
IKA_API char const * ikarus_entity_folder_get_name(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the number of children of a entity folder.
|
|
||||||
/// \param entity_folder The entity folder to get the number of children of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The number of children or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_entity_folder_get_child_count(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the children of a entity folder.
|
|
||||||
/// \param entity_folder The entity folder to get the children of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param children_out The buffer to write the children to.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \param children_out_size The size of the buffer.
|
|
||||||
IKA_API void ikarus_entity_folder_get_children(
|
|
||||||
IkarusEntityFolder const * entity_folder, struct IkarusEntityTreeItem ** children_out, size_t children_out_size
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the parent folder of an entity folder.
|
|
||||||
/// \param entity_folder The entity folder to set the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_parent The new parent folder of the entity folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the entity folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of old and new siblings.
|
|
||||||
IKA_API void ikarus_entity_folder_set_parent(
|
|
||||||
IkarusEntityFolder * entity_folder, struct IkarusEntityFolder * new_parent, size_t new_position
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the position of an entity folder within its parent folder.
|
|
||||||
/// \param entity_folder The entity folder to set the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the entity folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of siblings.
|
|
||||||
IKA_API void ikarus_entity_folder_set_position(IkarusEntityFolder * entity_folder, size_t new_position);
|
|
||||||
|
|
||||||
/// \brief Sets the name of an entity folder.
|
|
||||||
/// \param entity_folder The entity folder to set the name of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_name The new name of the entity folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
IKA_API void ikarus_entity_folder_set_name(IkarusEntityFolder * entity_folder, char const * new_name);
|
|
||||||
|
|
||||||
/// \brief Converts a entity folder to a generic folder.
|
|
||||||
/// \param entity_folder The entity folder to convert.
|
|
||||||
/// \return The constructed folder, representing the entity folder.
|
|
||||||
IKA_API struct IkarusFolder * ikarus_entity_folder_to_folder(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
/// \brief Converts a entity folder to an object.
|
|
||||||
/// \param entity_folder The entity folder to convert.
|
|
||||||
/// \return The constructed object, representing the entity folder.
|
|
||||||
IKA_API struct IkarusObject * ikarus_entity_folder_to_object(IkarusEntityFolder const * entity_folder);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
// @}
|
|
||||||
|
|
@ -1,31 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file entity_tree_item.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup entities Entities
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
struct IkarusEntityTreeItem;
|
|
||||||
|
|
||||||
/// \brief Visits a entity tree item, calling the appropriate visitor function.
|
|
||||||
/// \param item The item to visit.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param entity_visitor The visitor function called if the item is a entity. Skipped if null.
|
|
||||||
/// \param entity_folder_visitor The visitor function called if the item is a entity folder. Skipped if null.
|
|
||||||
/// \param data The data passed to the visitor functions.
|
|
||||||
IKA_API void ikarus_entity_tree_item_visit(
|
|
||||||
struct IkarusEntityTreeItem * item,
|
|
||||||
void (*entity_visitor)(struct IkarusEntity * entity, void * data),
|
|
||||||
void (*entity_folder_visitor)(struct IkarusEntityFolder * folder, void * data),
|
|
||||||
void * data
|
|
||||||
);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
/// @}
|
|
||||||
|
|
@ -1,38 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file folder.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/folders/blueprint_folder.h>
|
|
||||||
#include <ikarus/folders/entity_folder.h>
|
|
||||||
#include <ikarus/folders/folder_type.h>
|
|
||||||
#include <ikarus/folders/property_folder.h>
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \defgroup folder Folders
|
|
||||||
/// \brief Folders are used to group objects together.
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
/// \brief A generic folder. Similar to how Objects wrap all types of objects, Folders wrap all types of folders.
|
|
||||||
struct IkarusFolder;
|
|
||||||
|
|
||||||
/// \brief Special value for inserting objects at the end of a folder.
|
|
||||||
enum FolderPosition { FolderPosition_EndOfFolder = -1 };
|
|
||||||
|
|
||||||
/// \brief Visits a folder. Calling the appropriate function for the folder's type.
|
|
||||||
/// \param folder The folder to visit.
|
|
||||||
/// \param blueprint_visitor The function to call if the folder is a blueprint folder.
|
|
||||||
/// \param property_visitor The function to call if the folder is a property folder.
|
|
||||||
/// \param entity_visitor The function to call if the folder is an entity folder.
|
|
||||||
/// \param data The data passed to the visitor functions.
|
|
||||||
IKA_API void ikarus_folder_visit(
|
|
||||||
IkarusFolder * folder,
|
|
||||||
void (*blueprint_visitor)(IkarusBlueprintFolder *, void *),
|
|
||||||
void (*property_visitor)(IkarusPropertyFolder *, void *),
|
|
||||||
void (*entity_visitor)(IkarusEntityFolder *, void *),
|
|
||||||
void * data
|
|
||||||
);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
@ -1,26 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
// IMPLEMENTATION_DETAIL_FOLDER_TYPES
|
|
||||||
|
|
||||||
/// \file folder_type.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup folder folders
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
/// \brief The type of an folder.
|
|
||||||
/// \remark The values are identical to their counterparts in #IkarusObjectType.
|
|
||||||
enum IkarusFolderType {
|
|
||||||
/// \brief Not a folder or no folder.
|
|
||||||
IkarusFolderType_None = 0,
|
|
||||||
/// \brief An IkarusBlueprintFolder
|
|
||||||
IkarusFolderType_BlueprintFolder = 0b0100'0001,
|
|
||||||
/// \brief An IkarusPropertyFolder
|
|
||||||
IkarusFolderType_PropertyFolder = 0b0100'0010,
|
|
||||||
/// \brief An IkarusEntityFolder
|
|
||||||
IkarusFolderType_EntityFolder = 0b0100'0011,
|
|
||||||
};
|
|
||||||
|
|
||||||
/// @}
|
|
||||||
|
|
@ -1,159 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file property_folder.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup properties Properties
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief A property folder, storing properties and other property folders.
|
|
||||||
struct IkarusPropertyFolder;
|
|
||||||
|
|
||||||
/// \brief Creates a property folder.
|
|
||||||
/// \param project The project the property folder is part of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param parent The parent folder of the property folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the property folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the property folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
/// \return The created property folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API IkarusPropertyFolder * ikarus_property_folder_create(
|
|
||||||
struct IkarusProject * project, IkarusPropertyFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Copies a property folder.
|
|
||||||
/// \details Creates a copy of the property folder without its children.
|
|
||||||
/// \param property_folder The property folder to copy.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param parent The parent folder of the property folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the property folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the property folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
/// \return The created property folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API IkarusPropertyFolder * ikarus_property_folder_copy(
|
|
||||||
IkarusPropertyFolder * property_folder, IkarusPropertyFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Deletes a property folder and all its children
|
|
||||||
/// \param property_folder The property folder to delete.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param keep_children If true, the children of the property folder will be moved to the parent folder.
|
|
||||||
IKA_API void ikarus_property_folder_delete(IkarusPropertyFolder * property_folder, bool keep_children);
|
|
||||||
|
|
||||||
/// \brief Gets the project of a property folder.
|
|
||||||
/// \param property_folder The property folder to get the project of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The project of the property folder or null if an error occurs.
|
|
||||||
IKA_API struct IkarusProject * ikarus_property_folder_get_project(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the property source of a property folder.
|
|
||||||
/// \param property_folder The property folder to get the property source of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The property source of the property folder or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API struct IkarusPropertySource * ikarus_property_folder_get_source(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the parent folder of a property folder.
|
|
||||||
/// \param property_folder The property folder to get the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The parent folder of the property folder or null if an error occurs.
|
|
||||||
IKA_API struct IkarusPropertyFolder * ikarus_property_folder_get_parent(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the position of a property folder within its parent folder.
|
|
||||||
/// \param property_folder The property folder to get the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The position of the property folder or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_property_folder_get_position(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the name of a property folder.
|
|
||||||
/// \param property_folder The property folder to get the name of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The name of the property folder or null if an error occurs.
|
|
||||||
/// \remark The returned pointer is valid until the property folder is freed but may be invalidated by other operations.
|
|
||||||
IKA_API char const * ikarus_property_folder_get_name(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the number of children of a property folder.
|
|
||||||
/// \param property_folder The property folder to get the number of children of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The number of children or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_property_folder_get_child_count(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Gets the children of a property folder.
|
|
||||||
/// \param property_folder The property folder to get the children of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param children_out The buffer to write the children to.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \param children_out_size The size of the buffer.
|
|
||||||
IKA_API void ikarus_property_folder_get_children(
|
|
||||||
IkarusPropertyFolder const * property_folder, struct IkarusPropertyTreeItem ** children_out, size_t children_out_size
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the parent folder of an property folder.
|
|
||||||
/// \param property_folder The property folder to set the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_parent The new parent folder of the property folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the property folder in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of old and new siblings.
|
|
||||||
IKA_API void ikarus_property_folder_set_parent(
|
|
||||||
IkarusPropertyFolder * property_folder, struct IkarusPropertyFolder * new_parent, size_t new_position
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the position of an property folder within its parent folder.
|
|
||||||
/// \param property_folder The property folder to set the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the property folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of siblings.
|
|
||||||
IKA_API void ikarus_property_folder_set_position(IkarusPropertyFolder * property_folder, size_t new_position);
|
|
||||||
|
|
||||||
/// \brief Sets the name of an property folder.
|
|
||||||
/// \param property_folder The property folder to set the name of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_name The new name of the property folder.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must not be empty.
|
|
||||||
IKA_API void ikarus_property_folder_set_name(IkarusPropertyFolder * property_folder, char const * new_name);
|
|
||||||
|
|
||||||
/// \brief Converts a property folder to a generic folder.
|
|
||||||
/// \param property_folder The property folder to convert.
|
|
||||||
/// \return The constructed folder, representing the property folder.
|
|
||||||
IKA_API struct IkarusFolder * ikarus_property_folder_to_folder(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
/// \brief Converts a property folder to an object.
|
|
||||||
/// \param property_folder The property folder to convert.
|
|
||||||
/// \return The constructed object, representing the property folder.
|
|
||||||
IKA_API struct IkarusObject * ikarus_property_folder_to_object(IkarusPropertyFolder const * property_folder);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
// @}
|
|
||||||
|
|
@ -1,31 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file property_tree_item.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup properties Properties
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
struct IkarusPropertyTreeItem;
|
|
||||||
|
|
||||||
/// \brief Visits a property tree item, calling the appropriate visitor function.
|
|
||||||
/// \param item The item to visit.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param property_visitor The visitor function called if the item is a property. Skipped if null.
|
|
||||||
/// \param property_folder_visitor The visitor function called if the item is a property folder. Skipped if null.
|
|
||||||
/// \param data The data passed to the visitor functions.
|
|
||||||
IKA_API void ikarus_property_tree_item_visit(
|
|
||||||
struct IkarusPropertyTreeItem * item,
|
|
||||||
void (*property_visitor)(struct IkarusProperty * property, void * data),
|
|
||||||
void (*property_folder_visitor)(struct IkarusPropertyFolder * folder, void * data),
|
|
||||||
void * data
|
|
||||||
);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
/// @}
|
|
||||||
|
|
@ -21,37 +21,25 @@ struct IkarusBlueprint;
|
||||||
/// \param project The project the blueprint is part of.
|
/// \param project The project the blueprint is part of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must exist.
|
/// \pre \li Must exist.
|
||||||
/// \param parent The parent folder of the blueprint.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the blueprint in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the blueprint.
|
/// \param name The name of the blueprint.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must not be empty.
|
/// \pre \li Must not be empty.
|
||||||
/// \return The created blueprint or null if an error occurs.
|
/// \return The created blueprint or null if an error occurs.
|
||||||
/// \remark Must be freed using #ikarus_free.
|
/// \remark Must be freed using #ikarus_free.
|
||||||
IKA_API IkarusBlueprint * ikarus_blueprint_create(
|
IKA_API IkarusBlueprint * ikarus_blueprint_create(struct IkarusProject * project, char const * name);
|
||||||
struct IkarusProject * project, struct IkarusBlueprintFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Creates a blueprint from an entity.
|
/// \brief Creates a blueprint from an entity.
|
||||||
/// \details The created blueprint will have the same properties as the entity.
|
/// \details The created blueprint will have the same properties as the entity.
|
||||||
/// \param entity The entity to create the blueprint from.
|
/// \param entity The entity to create the blueprint from.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \param link_entity If true, the entity will be linked to the blueprint. If not they will remain separate.
|
/// \param link_entity If true, the entity will be linked to the blueprint. If not they will remain separate.
|
||||||
/// \param parent The parent folder of the blueprint.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the blueprint in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the blueprint. Must not be empty.
|
/// \param name The name of the blueprint. Must not be empty.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must not be empty.
|
/// \pre \li Must not be empty.
|
||||||
/// \return The created blueprint or null if an error occurs.
|
/// \return The created blueprint or null if an error occurs.
|
||||||
/// \remark Must be freed using #ikarus_free.
|
/// \remark Must be freed using #ikarus_free.
|
||||||
IKA_API IkarusBlueprint * ikarus_blueprint_create_from_entity(
|
IKA_API IkarusBlueprint * ikarus_blueprint_create_from_entity(
|
||||||
struct IkarusEntity * entity, bool link_entity, struct IkarusBlueprintFolder * parent, size_t position, char const * name
|
struct IkarusEntity * entity, bool link_entity, char const * name
|
||||||
);
|
);
|
||||||
|
|
||||||
/// \brief Copies a blueprint.
|
/// \brief Copies a blueprint.
|
||||||
|
|
@ -59,20 +47,13 @@ IKA_API IkarusBlueprint * ikarus_blueprint_create_from_entity(
|
||||||
/// \param blueprint The blueprint to copy.
|
/// \param blueprint The blueprint to copy.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must exist.
|
/// \pre \li Must exist.
|
||||||
/// \param parent The parent folder of the blueprint.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the blueprint in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the blueprint.
|
/// \param name The name of the blueprint.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must not be empty.
|
/// \pre \li Must not be empty.
|
||||||
/// \return The created blueprint or null if an error occurs.
|
/// \return The created blueprint or null if an error occurs.
|
||||||
/// \remark Linked entities won't be copied.
|
/// \remark Linked entities won't be copied.
|
||||||
/// \remark Must be freed using #ikarus_free.
|
/// \remark Must be freed using #ikarus_free.
|
||||||
IKA_API IkarusBlueprint * ikarus_blueprint_copy(
|
IKA_API IkarusBlueprint * ikarus_blueprint_copy(IkarusBlueprint const * blueprint, char const * name);
|
||||||
IkarusBlueprint const * blueprint, struct IkarusBlueprintFolder * parent, size_t position, char const * name
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Deletes a blueprint.
|
/// \brief Deletes a blueprint.
|
||||||
/// \param blueprint The blueprint to delete.
|
/// \param blueprint The blueprint to delete.
|
||||||
|
|
@ -88,20 +69,6 @@ IKA_API void ikarus_blueprint_delete(IkarusBlueprint * blueprint);
|
||||||
/// \return The project of the blueprint or null if an error occurs.
|
/// \return The project of the blueprint or null if an error occurs.
|
||||||
IKA_API struct IkarusProject * ikarus_blueprint_get_project(IkarusBlueprint const * blueprint);
|
IKA_API struct IkarusProject * ikarus_blueprint_get_project(IkarusBlueprint const * blueprint);
|
||||||
|
|
||||||
/// \brief Gets the parent folder of a blueprint.
|
|
||||||
/// \param blueprint The blueprint to get the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The parent folder of the blueprint or null if an error occurs.
|
|
||||||
IKA_API struct IkarusBlueprintFolder * ikarus_blueprint_get_parent(IkarusBlueprint const * blueprint);
|
|
||||||
|
|
||||||
/// \brief Gets the position of a blueprint within its parent folder.
|
|
||||||
/// \param blueprint The blueprint to get the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The position of the blueprint or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_blueprint_get_position(IkarusBlueprint const * blueprint);
|
|
||||||
|
|
||||||
/// \brief Gets the name of a blueprint.
|
/// \brief Gets the name of a blueprint.
|
||||||
/// \param blueprint The blueprint to get the name of.
|
/// \param blueprint The blueprint to get the name of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
@ -110,14 +77,6 @@ IKA_API size_t ikarus_blueprint_get_position(IkarusBlueprint const * blueprint);
|
||||||
/// \remark The returned pointer is valid until the blueprint is freed but may be invalidated by other operations.
|
/// \remark The returned pointer is valid until the blueprint is freed but may be invalidated by other operations.
|
||||||
IKA_API char const * ikarus_blueprint_get_name(IkarusBlueprint const * blueprint);
|
IKA_API char const * ikarus_blueprint_get_name(IkarusBlueprint const * blueprint);
|
||||||
|
|
||||||
/// \brief Gets the property root folder of a blueprint.
|
|
||||||
/// \param blueprint The blueprint to get the root folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The root folder of all properties of the blueprint or null if an error occurs.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API struct IkarusPropertyFolder * ikarus_blueprint_get_property_root_folder(IkarusBlueprint const * blueprint);
|
|
||||||
|
|
||||||
/// \brief Gets the number of properties of a blueprint.
|
/// \brief Gets the number of properties of a blueprint.
|
||||||
/// \param blueprint The blueprint to get the number of properties of.
|
/// \param blueprint The blueprint to get the number of properties of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
@ -154,29 +113,6 @@ IKA_API void ikarus_blueprint_get_linked_entities(
|
||||||
IkarusBlueprint const * blueprint, struct IkarusEntity ** entities_out, size_t entities_out_size
|
IkarusBlueprint const * blueprint, struct IkarusEntity ** entities_out, size_t entities_out_size
|
||||||
);
|
);
|
||||||
|
|
||||||
/// \brief Sets the parent folder of a blueprint.
|
|
||||||
/// \param blueprint The blueprint to set the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_parent The new parent folder of the blueprint.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the blueprint in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of old and new siblings.
|
|
||||||
IKA_API void ikarus_blueprint_set_parent(
|
|
||||||
IkarusBlueprint * blueprint, struct IkarusBlueprintFolder * new_parent, size_t new_position
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the position of a blueprint within its parent folder.
|
|
||||||
/// \param blueprint The blueprint to set the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the blueprint. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of siblings.
|
|
||||||
IKA_API void ikarus_blueprint_set_position(IkarusBlueprint * blueprint, size_t new_position);
|
|
||||||
|
|
||||||
/// \brief Sets the name of a blueprint.
|
/// \brief Sets the name of a blueprint.
|
||||||
/// \param blueprint The blueprint to set the name of.
|
/// \param blueprint The blueprint to set the name of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
@ -186,14 +122,6 @@ IKA_API void ikarus_blueprint_set_position(IkarusBlueprint * blueprint, size_t n
|
||||||
/// \pre \li Must not be empty.
|
/// \pre \li Must not be empty.
|
||||||
IKA_API void ikarus_blueprint_set_name(IkarusBlueprint * blueprint, char const * new_name);
|
IKA_API void ikarus_blueprint_set_name(IkarusBlueprint * blueprint, char const * new_name);
|
||||||
|
|
||||||
/// \brief Converts a blueprint to an object.
|
|
||||||
/// \param blueprint The blueprint to convert.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The constructed object, representing the blueprint.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API struct IkarusObject * ikarus_blueprint_to_object(IkarusBlueprint const * blueprint);
|
|
||||||
|
|
||||||
/// \brief Compares two blueprints.
|
/// \brief Compares two blueprints.
|
||||||
/// \param left The left blueprint to compare.
|
/// \param left The left blueprint to compare.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
#include <ikarus/macros.h>
|
||||||
|
#include <ikarus/stdtypes.h>
|
||||||
|
|
||||||
/// \file entity.h
|
/// \file entity.h
|
||||||
/// \author Folling <folling@ikarus.world>
|
/// \author Folling <folling@ikarus.world>
|
||||||
|
|
@ -230,12 +231,6 @@ IKA_API void ikarus_entity_set_value(
|
||||||
IkarusEntity * entity, struct IkarusProperty const * property, struct IkarusValue * value, bool validate_settings
|
IkarusEntity * entity, struct IkarusProperty const * property, struct IkarusValue * value, bool validate_settings
|
||||||
);
|
);
|
||||||
|
|
||||||
/// \brief Converts an entity to an object.
|
|
||||||
/// \param entity The entity to convert.
|
|
||||||
/// \return The constructed object, representing the entity.
|
|
||||||
/// \remark Must be freed using #ikarus_free.
|
|
||||||
IKA_API struct IkarusObject * ikarus_entity_to_object(IkarusEntity const * entity);
|
|
||||||
|
|
||||||
/// \brief Compares two entities.
|
/// \brief Compares two entities.
|
||||||
/// \param left The left entity to compare.
|
/// \param left The left entity to compare.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,7 @@
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
#include <ikarus/macros.h>
|
||||||
#include <ikarus/objects/property_type.h>
|
#include <ikarus/objects/property_type.h>
|
||||||
|
#include <ikarus/stdtypes.h>
|
||||||
|
|
||||||
/// \defgroup properties Properties
|
/// \defgroup properties Properties
|
||||||
/// \brief Properties define the structure and types of data.
|
/// \brief Properties define the structure and types of data.
|
||||||
|
|
@ -58,11 +59,6 @@ struct IkarusProperty;
|
||||||
/// \param property_source The property source the property is part of.
|
/// \param property_source The property source the property is part of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must exist.
|
/// \pre \li Must exist.
|
||||||
/// \param parent_folder The parent folder of the property.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the property in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the property.
|
/// \param name The name of the property.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must not be empty.
|
/// \pre \li Must not be empty.
|
||||||
|
|
@ -73,8 +69,6 @@ struct IkarusProperty;
|
||||||
IKA_API struct IkarusProperty * ikarus_property_create(
|
IKA_API struct IkarusProperty * ikarus_property_create(
|
||||||
struct IkarusProject * project,
|
struct IkarusProject * project,
|
||||||
struct IkarusPropertySource * property_source,
|
struct IkarusPropertySource * property_source,
|
||||||
struct IkarusPropertyFolder * parent_folder,
|
|
||||||
size_t position,
|
|
||||||
char const * name,
|
char const * name,
|
||||||
struct IkarusPropertyTypeInfo * property_info
|
struct IkarusPropertyTypeInfo * property_info
|
||||||
);
|
);
|
||||||
|
|
@ -87,22 +81,13 @@ IKA_API struct IkarusProperty * ikarus_property_create(
|
||||||
/// \param source The source to copy the property to.
|
/// \param source The source to copy the property to.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must exist.
|
/// \pre \li Must exist.
|
||||||
/// \param parent_folder The parent folder of the property.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param position The position of the property in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \param name The name of the property.
|
/// \param name The name of the property.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
/// \pre \li Must not be empty.
|
/// \pre \li Must not be empty.
|
||||||
/// \return The created property or null if an error occurs.
|
/// \return The created property or null if an error occurs.
|
||||||
/// \remark Must be freed using #ikarus_free.
|
/// \remark Must be freed using #ikarus_free.
|
||||||
IKA_API struct IkarusProperty * ikarus_property_copy(
|
IKA_API struct IkarusProperty * ikarus_property_copy(
|
||||||
struct IkarusProperty * property,
|
struct IkarusProperty * property, struct IkarusPropertySource * source, char const * name
|
||||||
struct IkarusPropertySource * source,
|
|
||||||
struct IkarusPropertyFolder * parent_folder,
|
|
||||||
size_t position,
|
|
||||||
char const * name
|
|
||||||
);
|
);
|
||||||
|
|
||||||
/// \brief Deletes a property.
|
/// \brief Deletes a property.
|
||||||
|
|
@ -119,20 +104,6 @@ IKA_API void ikarus_property_delete(struct IkarusProperty * property);
|
||||||
/// \return The project of the property or null if an error occurs.
|
/// \return The project of the property or null if an error occurs.
|
||||||
IKA_API struct IkarusProject * ikarus_property_get_project(IkarusProperty const * property);
|
IKA_API struct IkarusProject * ikarus_property_get_project(IkarusProperty const * property);
|
||||||
|
|
||||||
/// \brief Gets the parent folder of a property.
|
|
||||||
/// \param property The property to get the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The parent folder of the property or null if an error occurs.
|
|
||||||
IKA_API struct IkarusPropertyFolder * ikarus_property_get_parent(IkarusProperty const * property);
|
|
||||||
|
|
||||||
/// \brief Gets the position of a property within its parent folder.
|
|
||||||
/// \param property The property to get the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \return The position of the property or undefined if an error occurs.
|
|
||||||
IKA_API size_t ikarus_property_get_position(IkarusProperty const * property);
|
|
||||||
|
|
||||||
/// \brief Gets the name of a property.
|
/// \brief Gets the name of a property.
|
||||||
/// \param property The property to get the name of.
|
/// \param property The property to get the name of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
@ -165,29 +136,6 @@ IKA_API struct IkarusPropertySource * ikarus_property_get_source(IkarusProperty
|
||||||
/// \remark Must be freed using #ikarus_free.
|
/// \remark Must be freed using #ikarus_free.
|
||||||
IKA_API struct IkarusValue * ikarus_property_get_default_value(IkarusProperty const * property);
|
IKA_API struct IkarusValue * ikarus_property_get_default_value(IkarusProperty const * property);
|
||||||
|
|
||||||
/// \brief Sets the parent folder of a property.
|
|
||||||
/// \param property The property to set the parent folder of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_parent The new parent folder of the property.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the property in the parent folder. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of old and new siblings.
|
|
||||||
IKA_API void ikarus_property_set_parent(
|
|
||||||
IkarusProperty * property, struct IkarusPropertyFolder * new_parent, size_t new_position
|
|
||||||
);
|
|
||||||
|
|
||||||
/// \brief Sets the position of a property within its parent folder.
|
|
||||||
/// \param property The property to set the position of.
|
|
||||||
/// \pre \li Must not be null.
|
|
||||||
/// \pre \li Must exist.
|
|
||||||
/// \param new_position The new position of the property. \see #FolderPosition
|
|
||||||
/// \pre \li Must be within bounds for the parent folder.
|
|
||||||
/// \remark This adjusts the positions of siblings.
|
|
||||||
IKA_API void ikarus_property_set_position(IkarusProperty * property, size_t new_position);
|
|
||||||
|
|
||||||
/// \brief Sets the name of a property.
|
/// \brief Sets the name of a property.
|
||||||
/// \param property The property to set the name of.
|
/// \param property The property to set the name of.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
@ -208,11 +156,6 @@ IKA_API void ikarus_property_set_type_info(
|
||||||
IkarusProperty * property, struct IkarusPropertyTypeInfo new_type_info, bool attempt_conversion
|
IkarusProperty * property, struct IkarusPropertyTypeInfo new_type_info, bool attempt_conversion
|
||||||
);
|
);
|
||||||
|
|
||||||
/// \brief Converts a property to an object.
|
|
||||||
/// \param property The property to convert.
|
|
||||||
/// \return The constructed object, representing the property.
|
|
||||||
IKA_API struct IkarusObject * ikarus_property_to_object(IkarusProperty const * property);
|
|
||||||
|
|
||||||
/// \brief Compares two properties.
|
/// \brief Compares two properties.
|
||||||
/// \param left The left property to compare.
|
/// \param left The left property to compare.
|
||||||
/// \pre \li Must not be null.
|
/// \pre \li Must not be null.
|
||||||
|
|
|
||||||
|
|
@ -1,30 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file blueprint_scope.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/id.h>
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup object_scopes ObjectScopes
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief The global scope of all blueprints.
|
|
||||||
struct IkarusBlueprintScope;
|
|
||||||
|
|
||||||
/// \brief Creates a blueprint scope.
|
|
||||||
/// \return The created blueprint scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API IkarusBlueprintScope * ikarus_blueprint_scope_create();
|
|
||||||
|
|
||||||
/// \brief Converts a blueprint scope to an object scope.
|
|
||||||
/// \param scope The scope to convert.
|
|
||||||
/// \return The converted scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API struct IkarusObjectScope * ikarus_blueprint_scope_to_object_scope(IkarusBlueprintScope const * scope);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
// @}
|
|
||||||
|
|
@ -1,29 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file entity_scope.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup object_scopes ObjectScopes
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief The global scope of all entities.
|
|
||||||
struct IkarusEntityScope;
|
|
||||||
|
|
||||||
/// \brief Creates an entity scope.
|
|
||||||
/// \return The created entity scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API IkarusEntityScope * ikarus_entity_scope_create();
|
|
||||||
|
|
||||||
/// Converts an entity scope to an object scope.
|
|
||||||
/// \param scope The scope to convert.
|
|
||||||
/// \return The converted scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API struct IkarusObjectScope * ikarus_entity_scope_to_object_scope(IkarusEntityScope const * scope);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
// @}
|
|
||||||
|
|
@ -1,46 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
// IMPLEMENTATION_DETAIL_OBJECT_SCOPES
|
|
||||||
|
|
||||||
/// \file object_scope.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \defgroup object_scopes Object Scopes
|
|
||||||
/// \brief Scopes define where objects belong to.
|
|
||||||
/// \details They are required to differentiate between different types of objects with NULL as their parent.
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief The scope of an object.
|
|
||||||
struct IkarusObjectScope;
|
|
||||||
|
|
||||||
/// \brief The type of an object scope.
|
|
||||||
enum IkarusObjectScopeType {
|
|
||||||
/// \brief The scope is a blueprint scope.
|
|
||||||
IkarusObjectScopeType_Blueprint = 1,
|
|
||||||
/// \brief The scope is a property scope.
|
|
||||||
IkarusObjectScopeType_Property = 2,
|
|
||||||
/// \brief The scope is an entity scope.
|
|
||||||
IkarusObjectScopeType_Entity = 3
|
|
||||||
};
|
|
||||||
|
|
||||||
/// \brief Visits an object scope, calling the appropriate function.
|
|
||||||
/// \param scope The scope to visit.
|
|
||||||
/// \param blueprint_visitor The function to call if the scope is an #IkarusBlueprintScope.
|
|
||||||
/// \param property_visitor The function to call if the scope is an #IkarusPropertyScope.
|
|
||||||
/// \param entity_visitor The function to call if the scope is an #IkarusEntityScope.
|
|
||||||
/// \remark function pointers may be null in which case they are not called.
|
|
||||||
IKA_API void ikarus_object_scope_visit(
|
|
||||||
IkarusObjectScope * scope,
|
|
||||||
void (*blueprint_visitor)(struct IkarusBlueprintScope *, void *),
|
|
||||||
void (*property_visitor)(struct IkarusPropertyScope *, void *),
|
|
||||||
void (*entity_visitor)(struct IkarusEntityScope *, void *),
|
|
||||||
void * data
|
|
||||||
);
|
|
||||||
|
|
||||||
/// @}
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
@ -1,48 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
/// \file property_scope.h
|
|
||||||
/// \author Folling <folling@ikarus.world>
|
|
||||||
|
|
||||||
#include <ikarus/id.h>
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
|
|
||||||
/// \addtogroup object_scopes ObjectScopes
|
|
||||||
/// @{
|
|
||||||
|
|
||||||
IKARUS_BEGIN_HEADER
|
|
||||||
|
|
||||||
/// \brief The scope of a property
|
|
||||||
struct IkarusPropertyScope;
|
|
||||||
|
|
||||||
/// \brief Creates a property scope from a blueprint.
|
|
||||||
/// \param blueprint The blueprint the property is scoped to.
|
|
||||||
/// \return The created property scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API IkarusPropertyScope * ikarus_property_scope_create_blueprint(struct IkarusBlueprint * blueprint);
|
|
||||||
/// \brief Creates a property scope from an entity.
|
|
||||||
/// \param entity The entity the property is scoped to.
|
|
||||||
/// \return The created property scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API IkarusPropertyScope * ikarus_property_scope_create_entity(struct IkarusEntity * entity);
|
|
||||||
|
|
||||||
/// \brief Converts a property scope to an object scope.
|
|
||||||
/// \param scope The scope to convert.
|
|
||||||
/// \return The converted scope.
|
|
||||||
/// \remark Must be freed with #ikarus_free.
|
|
||||||
IKA_API struct IkarusObjectScope * ikarus_property_scope_to_object_scope(IkarusPropertyScope const * scope);
|
|
||||||
|
|
||||||
/// \brief Visits a property scope, calling the appropriate function.
|
|
||||||
/// \param scope The scope to to visit
|
|
||||||
/// \param blueprint_visitor The function to call if the property is scoped to a blueprint.
|
|
||||||
/// \param entity_visitor The function to call if the property is scoped to an entity.
|
|
||||||
/// \param data The data passed to the visitor functions.
|
|
||||||
IKA_API void ikarus_property_scope_visit(
|
|
||||||
IkarusPropertyScope * scope,
|
|
||||||
void (*blueprint_visitor)(struct IkarusBlueprint *, void *),
|
|
||||||
void (*entity_visitor)(struct IkarusEntity *, void *),
|
|
||||||
void * data
|
|
||||||
);
|
|
||||||
|
|
||||||
IKARUS_END_HEADER
|
|
||||||
|
|
||||||
// @}
|
|
||||||
|
|
@ -1,8 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <ikarus/folders/blueprint_folder.h>
|
|
||||||
|
|
||||||
struct IkarusBlueprintFolder {
|
|
||||||
IkarusId id;
|
|
||||||
std::string name_buffer;
|
|
||||||
};
|
|
||||||
|
|
@ -1,8 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <ikarus/folders/entity_folder.h>
|
|
||||||
|
|
||||||
struct IkarusEntityFolder {
|
|
||||||
IkarusId id;
|
|
||||||
std::string name_buffer;
|
|
||||||
};
|
|
||||||
|
|
@ -1,13 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <variant>
|
|
||||||
|
|
||||||
#include <ikarus/folders/folder.h>
|
|
||||||
|
|
||||||
#include <folders/blueprint_folder.hpp>
|
|
||||||
#include <folders/entity_folder.hpp>
|
|
||||||
#include <folders/property_folder.hpp>
|
|
||||||
|
|
||||||
struct IkarusEntityFolder {
|
|
||||||
std::variant<IkarusBlueprintFolder, IkarusPropertyFolder, IkarusEntityFolder> data;
|
|
||||||
};
|
|
||||||
|
|
@ -1,8 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <ikarus/folders/property_folder.h>
|
|
||||||
|
|
||||||
struct IkarusPropertyFolder {
|
|
||||||
IkarusId id;
|
|
||||||
std::string name_buffer;
|
|
||||||
};
|
|
||||||
26
src/id.cpp
26
src/id.cpp
|
|
@ -1,4 +1,4 @@
|
||||||
#include "ikarus/id.h"
|
#include "id.hpp"
|
||||||
|
|
||||||
#include <catch2/catch_test_macros.hpp>
|
#include <catch2/catch_test_macros.hpp>
|
||||||
|
|
||||||
|
|
@ -15,21 +15,11 @@ auto ikarus_id_is_equal(IkarusId left, IkarusId right) -> bool {
|
||||||
return left == right;
|
return left == right;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto ikarus_id_is_none(IkarusId id) -> bool {
|
|
||||||
return ikarus_id_is_equal(id, IKARUS_ID_NONE);
|
|
||||||
}
|
|
||||||
|
|
||||||
auto ikarus_id_is_unspecified(IkarusId id) -> bool {
|
|
||||||
return ikarus_id_is_equal(id, IKARUS_ID_UNSPECIFIED);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("id_object_type", "[id]") {
|
TEST_CASE("id_object_type", "[id]") {
|
||||||
// NOLINTNEXTLINE(readability-magic-numbers)
|
// NOLINTNEXTLINE(readability-magic-numbers)
|
||||||
auto id = static_cast<uint64_t>(IkarusObjectType_Blueprint) << IKARUS_ID_OBJECT_RANDOM_BITS;
|
auto id = static_cast<uint64_t>(IkarusObjectType_Blueprint) << IKARUS_ID_OBJECT_RANDOM_BITS;
|
||||||
|
|
||||||
REQUIRE(ikarus_id_get_object_type(id) == IkarusObjectType_Blueprint);
|
REQUIRE(ikarus_id_get_object_type(id) == IkarusObjectType_Blueprint);
|
||||||
REQUIRE(!ikarus_id_is_none(id) == IkarusObjectType_Blueprint);
|
|
||||||
REQUIRE(!ikarus_id_is_unspecified(id) == IkarusObjectType_Blueprint);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("id_equal", "[id]") {
|
TEST_CASE("id_equal", "[id]") {
|
||||||
|
|
@ -40,17 +30,3 @@ TEST_CASE("id_equal", "[id]") {
|
||||||
REQUIRE(ikarus_id_is_equal(id, copy));
|
REQUIRE(ikarus_id_is_equal(id, copy));
|
||||||
REQUIRE(!ikarus_id_is_equal(id, third));
|
REQUIRE(!ikarus_id_is_equal(id, third));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("id_none", "[id]") {
|
|
||||||
auto id = IKARUS_ID_NONE;
|
|
||||||
|
|
||||||
REQUIRE(ikarus_id_is_none(id));
|
|
||||||
REQUIRE(!ikarus_id_is_unspecified(id));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("id_unspecified", "[id]") {
|
|
||||||
auto id = IKARUS_ID_UNSPECIFIED;
|
|
||||||
|
|
||||||
REQUIRE(!ikarus_id_is_none(id));
|
|
||||||
REQUIRE(ikarus_id_is_unspecified(id));
|
|
||||||
}
|
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,9 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <ikarus/objects/blueprint.h>
|
#include <id.hpp>
|
||||||
|
|
||||||
/// \private
|
/// \private
|
||||||
struct IkarusBlueprint {
|
struct IkarusBlueprint {
|
||||||
|
struct IkarusProject * project;
|
||||||
IkarusId id;
|
IkarusId id;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,9 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <ikarus/objects/entity.h>
|
#include <id.hpp>
|
||||||
|
|
||||||
/// \private
|
/// \private
|
||||||
struct IkarusEntity {
|
struct IkarusEntity {
|
||||||
|
struct IkarusProject * project;
|
||||||
IkarusId id;
|
IkarusId id;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,25 +0,0 @@
|
||||||
#include "ikarus/objects/object.h"
|
|
||||||
|
|
||||||
#include <catch2/catch_test_macros.hpp>
|
|
||||||
|
|
||||||
#include <objects/object.hpp>
|
|
||||||
|
|
||||||
IkarusObjectType ikarus_object_get_type(IkarusObject const * object) {
|
|
||||||
return object->type;
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("object_type", "[object]") {
|
|
||||||
auto types = {
|
|
||||||
IkarusObjectType_Blueprint,
|
|
||||||
IkarusObjectType_Property,
|
|
||||||
IkarusObjectType_Entity,
|
|
||||||
IkarusObjectType_BlueprintFolder,
|
|
||||||
IkarusObjectType_PropertyFolder,
|
|
||||||
IkarusObjectType_EntityFolder,
|
|
||||||
};
|
|
||||||
|
|
||||||
for (auto type : types) {
|
|
||||||
auto object = IkarusObject{.type = type};
|
|
||||||
REQUIRE(ikarus_object_get_type(&object) == type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -2,14 +2,12 @@
|
||||||
|
|
||||||
#include <variant>
|
#include <variant>
|
||||||
|
|
||||||
#include <folders/blueprint_folder.hpp>
|
|
||||||
#include <folders/entity_folder.hpp>
|
|
||||||
#include <folders/property_folder.hpp>
|
|
||||||
#include <objects/blueprint.hpp>
|
#include <objects/blueprint.hpp>
|
||||||
#include <objects/entity.hpp>
|
#include <objects/entity.hpp>
|
||||||
#include <objects/property.hpp>
|
#include <objects/property.hpp>
|
||||||
|
|
||||||
struct IkarusObject {
|
union IkarusObject {
|
||||||
std::variant<IkarusBlueprint, IkarusProperty, IkarusEntity, IkarusBlueprintFolder, IkarusPropertyFolder, IkarusEntityFolder>
|
IkarusBlueprint blueprint;
|
||||||
data;
|
IkarusEntity entity;
|
||||||
|
IkarusProperty property;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,9 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <ikarus/objects/property.h>
|
#include <id.hpp>
|
||||||
|
|
||||||
/// \private
|
/// \private
|
||||||
struct IkarusProperty {
|
struct IkarusProperty {
|
||||||
|
struct IkarusProject * project;
|
||||||
IkarusId id;
|
IkarusId id;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
111
src/persistence/migrations/m1_initial_layout.sql
Normal file
111
src/persistence/migrations/m1_initial_layout.sql
Normal file
|
|
@ -0,0 +1,111 @@
|
||||||
|
CREATE TABLE `objects`
|
||||||
|
(
|
||||||
|
`do_not_access_rowid_alias` INTEGER PRIMARY KEY,
|
||||||
|
`object_type` INT NOT NULL,
|
||||||
|
`id` INT GENERATED ALWAYS AS (`do_not_access_rowid_alias` | (`object_type` << 56)
|
||||||
|
) VIRTUAL,
|
||||||
|
`name` TEXT NOT NULL,
|
||||||
|
`information` TEXT NOT NULL
|
||||||
|
) STRICT;
|
||||||
|
|
||||||
|
CREATE UNIQUE INDEX `object_id` ON `objects` (`id`);
|
||||||
|
CREATE INDEX `object_type` ON `objects` (`object_type`);
|
||||||
|
|
||||||
|
CREATE
|
||||||
|
VIRTUAL TABLE `objects_fts` USING fts5
|
||||||
|
(
|
||||||
|
`name`,
|
||||||
|
`information`,
|
||||||
|
content=
|
||||||
|
'objects',
|
||||||
|
content_rowid=
|
||||||
|
'id',
|
||||||
|
tokenize=
|
||||||
|
"unicode61 remove_diacritics 2 tokenchars '-_'"
|
||||||
|
);
|
||||||
|
|
||||||
|
CREATE TABLE `blueprints`
|
||||||
|
(
|
||||||
|
`id` INT,
|
||||||
|
|
||||||
|
PRIMARY KEY (`id`),
|
||||||
|
FOREIGN KEY (`id`) REFERENCES `objects` (`id`) ON DELETE CASCADE
|
||||||
|
) WITHOUT ROWID, STRICT;
|
||||||
|
|
||||||
|
CREATE TABLE `entities`
|
||||||
|
(
|
||||||
|
`id` INT,
|
||||||
|
|
||||||
|
PRIMARY KEY (`id`),
|
||||||
|
FOREIGN KEY (`id`) REFERENCES `objects` (`id`) ON DELETE CASCADE
|
||||||
|
) WITHOUT ROWID, STRICT;
|
||||||
|
|
||||||
|
CREATE TABLE `entity_blueprints`
|
||||||
|
(
|
||||||
|
`entity` INT NOT NULL,
|
||||||
|
`blueprint` INT NOT NULL,
|
||||||
|
|
||||||
|
PRIMARY KEY (`entity`),
|
||||||
|
UNIQUE (`entity`, `blueprint`),
|
||||||
|
FOREIGN KEY (`blueprint`) REFERENCES `blueprints` (`id`) ON DELETE CASCADE
|
||||||
|
) WITHOUT ROWID, STRICT;
|
||||||
|
|
||||||
|
CREATE INDEX `entity_blueprints_blueprint` ON `entity_blueprints` (`blueprint`);
|
||||||
|
|
||||||
|
CREATE TABLE `properties`
|
||||||
|
(
|
||||||
|
`id` INT,
|
||||||
|
`type` INT NOT NULL,
|
||||||
|
`default_value` TEXT NOT NULL,
|
||||||
|
`settings` TEXT NOT NULL,
|
||||||
|
|
||||||
|
PRIMARY KEY (`id`),
|
||||||
|
FOREIGN KEY (`id`) REFERENCES `objects` (`id`) ON DELETE CASCADE
|
||||||
|
) WITHOUT ROWID, STRICT;
|
||||||
|
|
||||||
|
CREATE INDEX `properties_type` ON `properties` (`type`);
|
||||||
|
|
||||||
|
CREATE
|
||||||
|
VIRTUAL TABLE `property_default_value_fts` USING fts5
|
||||||
|
(
|
||||||
|
`default_value`,
|
||||||
|
content=
|
||||||
|
'properties',
|
||||||
|
content_rowid=
|
||||||
|
'object_id',
|
||||||
|
tokenize=
|
||||||
|
"unicode61 remove_diacritics 2 tokenchars '-_'"
|
||||||
|
);
|
||||||
|
|
||||||
|
CREATE
|
||||||
|
VIRTUAL TABLE `property_settings_fts` USING fts5
|
||||||
|
(
|
||||||
|
`settings`,
|
||||||
|
content=
|
||||||
|
'properties',
|
||||||
|
content_rowid=
|
||||||
|
'object_id',
|
||||||
|
tokenize=
|
||||||
|
"unicode61 remove_diacritics 2 tokenchars '-_'"
|
||||||
|
);
|
||||||
|
|
||||||
|
CREATE TABLE `values`
|
||||||
|
(
|
||||||
|
`entity` INT NOT NULL,
|
||||||
|
`property` INT NOT NULL,
|
||||||
|
`value` TEXT NOT NULL,
|
||||||
|
|
||||||
|
PRIMARY KEY (`entity`, `property`),
|
||||||
|
FOREIGN KEY (`entity`) REFERENCES `entities` (`id`) ON DELETE CASCADE,
|
||||||
|
FOREIGN KEY (`property`) REFERENCES `properties` (`id`) ON DELETE CASCADE
|
||||||
|
) WITHOUT ROWID, STRICT;
|
||||||
|
|
||||||
|
CREATE
|
||||||
|
VIRTUAL TABLE `values_fts` USING fts5
|
||||||
|
(
|
||||||
|
`value`,
|
||||||
|
content=
|
||||||
|
'values',
|
||||||
|
tokenize=
|
||||||
|
"unicode61 remove_diacritics 2 tokenchars '-_'"
|
||||||
|
)
|
||||||
|
|
@ -1,10 +1,11 @@
|
||||||
#include "ikarus/project/project.h"
|
|
||||||
|
|
||||||
#include <filesystem>
|
#include <filesystem>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
|
#include <sqlitecpp/connection.hpp>
|
||||||
|
|
||||||
/// \private
|
/// \private
|
||||||
struct IkarusProject {
|
struct IkarusProject {
|
||||||
std::string name;
|
std::string name;
|
||||||
std::filesystem::path path;
|
std::filesystem::path path;
|
||||||
|
std::unique_ptr<sqlitecpp::Connection> db;
|
||||||
};
|
};
|
||||||
|
|
@ -1,12 +0,0 @@
|
||||||
#include "ikarus/scopes/blueprint_scope.h"
|
|
||||||
|
|
||||||
#include <scopes/blueprint_scope.hpp>
|
|
||||||
#include <scopes/object_scope.hpp>
|
|
||||||
|
|
||||||
IkarusBlueprintScope * ikarus_blueprint_scope_create() {
|
|
||||||
return new IkarusBlueprintScope{};
|
|
||||||
}
|
|
||||||
|
|
||||||
struct IkarusObjectScope * ikarus_blueprint_scope_to_object_scope(IkarusBlueprintScope const * scope) {
|
|
||||||
return new IkarusObjectScope{.data = *scope};
|
|
||||||
}
|
|
||||||
|
|
@ -1,5 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <ikarus/scopes/blueprint_scope.h>
|
|
||||||
|
|
||||||
struct IkarusBlueprintScope {};
|
|
||||||
|
|
@ -1,12 +0,0 @@
|
||||||
#include "ikarus/scopes/entity_scope.h"
|
|
||||||
|
|
||||||
#include <scopes/entity_scope.hpp>
|
|
||||||
#include <scopes/object_scope.hpp>
|
|
||||||
|
|
||||||
IkarusEntityScope * ikarus_entity_scope_create() {
|
|
||||||
return new IkarusEntityScope{};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusObjectScope * ikarus_entity_scope_to_object_scope(IkarusEntityScope const * scope) {
|
|
||||||
return new IkarusObjectScope{.data = *scope};
|
|
||||||
}
|
|
||||||
|
|
@ -1,5 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <ikarus/scopes/entity_scope.h>
|
|
||||||
|
|
||||||
struct IkarusEntityScope {};
|
|
||||||
|
|
@ -1,100 +0,0 @@
|
||||||
#include "ikarus/scopes/object_scope.h"
|
|
||||||
|
|
||||||
#include <initializer_list>
|
|
||||||
#include <utility>
|
|
||||||
#include <variant>
|
|
||||||
|
|
||||||
#include <catch2/catch_test_macros.hpp>
|
|
||||||
|
|
||||||
#include <cppbase/templates.hpp>
|
|
||||||
|
|
||||||
#include <ikarus/scopes/blueprint_scope.h>
|
|
||||||
#include <ikarus/scopes/entity_scope.h>
|
|
||||||
#include <ikarus/scopes/property_scope.h>
|
|
||||||
|
|
||||||
#include <scopes/object_scope.hpp>
|
|
||||||
|
|
||||||
IkarusObjectScopeType ikarus_object_scope_get_type(IkarusObjectScope * scope) {
|
|
||||||
return std::visit(
|
|
||||||
cppbase::overloaded{
|
|
||||||
[]([[maybe_unused]] IkarusBlueprintScope const& scope) { return IkarusObjectScopeType_Blueprint; },
|
|
||||||
[]([[maybe_unused]] IkarusPropertyScope const& scope) { return IkarusObjectScopeType_Property; },
|
|
||||||
[]([[maybe_unused]] IkarusEntityScope const& scope) { return IkarusObjectScopeType_Entity; }},
|
|
||||||
scope->data
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ikarus_object_scope_visit(
|
|
||||||
IkarusObjectScope * scope,
|
|
||||||
void(blueprint_visitor)(IkarusBlueprintScope *, void *),
|
|
||||||
void(property_visitor)(IkarusPropertyScope *, void *),
|
|
||||||
void(entity_visitor)(IkarusEntityScope *, void *),
|
|
||||||
void * data
|
|
||||||
) {
|
|
||||||
std::visit(
|
|
||||||
cppbase::overloaded{
|
|
||||||
[blueprint_visitor, data](IkarusBlueprintScope& scope) { blueprint_visitor(&scope, data); },
|
|
||||||
[property_visitor, data](IkarusPropertyScope& scope) { property_visitor(&scope, data); },
|
|
||||||
[entity_visitor, data](IkarusEntityScope& scope) { entity_visitor(&scope, data); }},
|
|
||||||
scope->data
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("blueprint_object_scope_conversion", "[object_scope]") {
|
|
||||||
auto * blueprint_scope = ikarus_blueprint_scope_create();
|
|
||||||
auto * blueprint_object_scope = ikarus_blueprint_scope_to_object_scope(blueprint_scope);
|
|
||||||
REQUIRE(ikarus_object_scope_get_type(blueprint_object_scope) == IkarusObjectScopeType_Blueprint);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("property_object_scope_conversion", "[object_scope]") {
|
|
||||||
auto * blueprint = ikarus_blueprint_create();
|
|
||||||
auto * entity = ikarus_entity_create();
|
|
||||||
|
|
||||||
auto * property_blueprint_scope = ikarus_property_scope_create_blueprint(blueprint);
|
|
||||||
auto * property_blueprint_object_scope = ikarus_property_scope_to_object_scope(property_blueprint_scope);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_object_scope_get_type(property_blueprint_object_scope) == IkarusObjectScopeType_Property);
|
|
||||||
|
|
||||||
auto * property_entity_scope = ikarus_property_scope_create_entity(entity);
|
|
||||||
auto * property_entity_object_scope = ikarus_property_scope_to_object_scope(property_entity_scope);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_object_scope_get_type(property_entity_object_scope) == IkarusObjectScopeType_Property);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("entity_object_scope_conversion", "[object_scope]") {
|
|
||||||
auto * entity_scope = ikarus_entity_scope_create();
|
|
||||||
auto * entity_object_scope = ikarus_entity_scope_to_object_scope(entity_scope);
|
|
||||||
REQUIRE(ikarus_object_scope_get_type(entity_object_scope) == IkarusObjectScopeType_Entity);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("object_scope_visiting", "[object_scope]") {
|
|
||||||
auto * blueprint = ikarus_blueprint_create();
|
|
||||||
|
|
||||||
auto * blueprint_scope = ikarus_blueprint_scope_create();
|
|
||||||
auto * property_scope = ikarus_property_scope_create_blueprint(blueprint);
|
|
||||||
auto * entity_scope = ikarus_entity_scope_create();
|
|
||||||
|
|
||||||
auto * blueprint_object_scope = ikarus_blueprint_scope_to_object_scope(blueprint_scope);
|
|
||||||
auto * property_object_scope = ikarus_property_scope_to_object_scope(property_scope);
|
|
||||||
auto * entity_object_scope = ikarus_entity_scope_to_object_scope(entity_scope);
|
|
||||||
|
|
||||||
auto scopes = {
|
|
||||||
std::make_pair(blueprint_object_scope, 1),
|
|
||||||
std::make_pair(property_object_scope, 2),
|
|
||||||
std::make_pair(entity_object_scope, 3),
|
|
||||||
};
|
|
||||||
|
|
||||||
for (auto [scope, value] : scopes) {
|
|
||||||
int test = 0;
|
|
||||||
|
|
||||||
ikarus_object_scope_visit(
|
|
||||||
scope,
|
|
||||||
[](IkarusBlueprintScope *, void * data) { *static_cast<decltype(test) *>(data) = 1; },
|
|
||||||
[](IkarusPropertyScope *, void * data) { *static_cast<decltype(test) *>(data) = 2; },
|
|
||||||
[](IkarusEntityScope *, void * data) { *static_cast<decltype(test) *>(data) = 3; },
|
|
||||||
&test
|
|
||||||
);
|
|
||||||
|
|
||||||
REQUIRE(test == value);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,11 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <ikarus/scopes/object_scope.h>
|
|
||||||
|
|
||||||
#include <scopes/blueprint_scope.hpp>
|
|
||||||
#include <scopes/entity_scope.hpp>
|
|
||||||
#include <scopes/property_scope.hpp>
|
|
||||||
|
|
||||||
struct IkarusObjectScope {
|
|
||||||
std::variant<IkarusBlueprintScope, IkarusPropertyScope, IkarusEntityScope> data;
|
|
||||||
};
|
|
||||||
|
|
@ -1,35 +0,0 @@
|
||||||
#include "ikarus/scopes/property_scope.h"
|
|
||||||
|
|
||||||
#include <cppbase/templates.hpp>
|
|
||||||
|
|
||||||
#include <objects/blueprint.hpp>
|
|
||||||
#include <objects/entity.hpp>
|
|
||||||
#include <scopes/object_scope.hpp>
|
|
||||||
#include <scopes/property_scope.hpp>
|
|
||||||
|
|
||||||
IkarusPropertyScope * ikarus_property_scope_create_blueprint(IkarusBlueprint * blueprint) {
|
|
||||||
return new IkarusPropertyScope{.data = *blueprint};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusPropertyScope * ikarus_property_scope_create_entity(IkarusEntity * entity) {
|
|
||||||
return new IkarusPropertyScope{.data = *entity};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusObjectScope * ikarus_property_scope_to_object_scope(IkarusPropertyScope const * scope) {
|
|
||||||
return new IkarusObjectScope{.data = *scope};
|
|
||||||
}
|
|
||||||
|
|
||||||
void ikarus_property_scope_visit(
|
|
||||||
IkarusPropertyScope * scope,
|
|
||||||
void (*blueprint_func)(IkarusBlueprint *, void *),
|
|
||||||
void (*entity_func)(IkarusEntity *, void *),
|
|
||||||
void * data
|
|
||||||
) {
|
|
||||||
std::visit(
|
|
||||||
cppbase::overloaded{
|
|
||||||
[blueprint_func, data](IkarusBlueprint& blueprint) { blueprint_func(&blueprint, data); },
|
|
||||||
[entity_func, data](IkarusEntity& entity) { entity_func(&entity, data); },
|
|
||||||
},
|
|
||||||
scope->data
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
@ -1,12 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <variant>
|
|
||||||
|
|
||||||
#include <ikarus/scopes/property_scope.h>
|
|
||||||
|
|
||||||
#include <objects/blueprint.hpp>
|
|
||||||
#include <objects/entity.hpp>
|
|
||||||
|
|
||||||
struct IkarusPropertyScope {
|
|
||||||
std::variant<IkarusBlueprint, IkarusEntity> data;
|
|
||||||
};
|
|
||||||
|
|
@ -1,343 +0,0 @@
|
||||||
#include "ikarus/values/value.h"
|
|
||||||
|
|
||||||
#include <cmath>
|
|
||||||
#include <cstring>
|
|
||||||
#include <initializer_list>
|
|
||||||
#include <limits>
|
|
||||||
#include <utility>
|
|
||||||
|
|
||||||
#include <catch2/catch_test_macros.hpp>
|
|
||||||
|
|
||||||
#include <ikarus/macros.h>
|
|
||||||
#include <ikarus/objects/property.h>
|
|
||||||
|
|
||||||
/// \brief Creates an indeterminate entity value of a given type.
|
|
||||||
/// \param type The type of the value.
|
|
||||||
/// \return The entity value.
|
|
||||||
IKA_API IkarusEntityValue value_create_invalid(IkarusPropertyType type) {
|
|
||||||
return IkarusEntityValue{
|
|
||||||
._type = type,
|
|
||||||
._data = IkarusEntityValueData{},
|
|
||||||
._state = IkarusEntityValueState_Invalid,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusEntityValue ikarus_value_create_toggle(bool value) {
|
|
||||||
return IkarusEntityValue{
|
|
||||||
._type = IkarusPropertyType_Toggle,
|
|
||||||
._data = IkarusEntityValueData{._toggle = IkarusToggleValue{._value = value}},
|
|
||||||
._state = IkarusEntityValueState_Normal,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusEntityValue ikarus_value_create_number(long double value) {
|
|
||||||
if (auto fp_class = std::fpclassify(value); fp_class != FP_NORMAL && fp_class != FP_ZERO) {
|
|
||||||
return value_create_invalid(IkarusPropertyType_Number);
|
|
||||||
}
|
|
||||||
|
|
||||||
return IkarusEntityValue{
|
|
||||||
._type = IkarusPropertyType_Number,
|
|
||||||
._data = IkarusEntityValueData{._number = IkarusNumberValue{._value = value}},
|
|
||||||
._state = IkarusEntityValueState_Normal,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusEntityValue ikarus_value_create_text(char const * value) {
|
|
||||||
if (value == nullptr) {
|
|
||||||
return value_create_invalid(IkarusPropertyType_Text);
|
|
||||||
}
|
|
||||||
|
|
||||||
return IkarusEntityValue{
|
|
||||||
._type = IkarusPropertyType_Text,
|
|
||||||
._data = IkarusEntityValueData{._text = IkarusTextValue{._value = value}},
|
|
||||||
._state = IkarusEntityValueState_Normal,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusEntityValue ikarus_value_create_indeterminate(IkarusPropertyType type) {
|
|
||||||
IkarusEntityValueData data{};
|
|
||||||
|
|
||||||
switch (type) {
|
|
||||||
case IkarusPropertyType_Toggle: {
|
|
||||||
data._toggle = IkarusToggleValue{._value = false};
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case IkarusPropertyType_Number: {
|
|
||||||
data._number = IkarusNumberValue{._value = 0.0};
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case IkarusPropertyType_Text: {
|
|
||||||
data._text = IkarusTextValue{._value = ""};
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default: return value_create_invalid(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
return IkarusEntityValue{
|
|
||||||
._type = type,
|
|
||||||
._data = data,
|
|
||||||
._state = IkarusEntityValueState_Indeterminate,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusEntityValue ikarus_value_get_default(IkarusPropertyType type) {
|
|
||||||
switch (type) {
|
|
||||||
case IkarusPropertyType_Toggle: return ikarus_value_create_toggle(false);
|
|
||||||
case IkarusPropertyType_Number: return ikarus_value_create_number(0.0);
|
|
||||||
case IkarusPropertyType_Text: return ikarus_value_create_text("");
|
|
||||||
default: return value_create_invalid(type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ikarus_toggle_value_get_underlying(IkarusToggleValue const * value) {
|
|
||||||
return value->_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
long double ikarus_number_value_get_underlying(IkarusNumberValue const * value) {
|
|
||||||
return value->_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
char const * ikarus_text_value_get_underlying(IkarusTextValue const * value) {
|
|
||||||
return value->_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
// no need to check for validity here, since these concrete types are only created by the library
|
|
||||||
bool ikarus_toggle_value_is_equal(IkarusToggleValue const * value, bool check) {
|
|
||||||
return value != nullptr && value->_value == check;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ikarus_number_value_is_equal(IkarusNumberValue const * value, long double check) {
|
|
||||||
return value != nullptr && value->_value == check;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ikarus_text_value_is_equal(IkarusTextValue const * value, char const * check) {
|
|
||||||
return value != nullptr && check != nullptr && std::strcmp(value->_value, check) == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ikarus_value_is_equal(IkarusEntityValue const * left, IkarusEntityValue const * right) {
|
|
||||||
if (left == nullptr || right == nullptr) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (left->_state == IkarusEntityValueState_Invalid || right->_state == IkarusEntityValueState_Invalid) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (left->_type != right->_type) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// indeterminate values are only equal if they have the same type
|
|
||||||
if (left->_state == IkarusEntityValueState_Indeterminate && right->_state == IkarusEntityValueState_Indeterminate) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (left->_type) {
|
|
||||||
case IkarusPropertyType_Toggle: return left->_data._toggle._value == right->_data._toggle._value;
|
|
||||||
case IkarusPropertyType_Number: return left->_data._number._value == right->_data._number._value;
|
|
||||||
case IkarusPropertyType_Text: return std::strcmp(left->_data._text._value, right->_data._text._value) == 0;
|
|
||||||
default: return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ikarus_value_is_invalid(IkarusEntityValue const * value) {
|
|
||||||
return value == nullptr || value->_state == IkarusEntityValueState_Invalid;
|
|
||||||
}
|
|
||||||
|
|
||||||
IkarusPropertyType ikarus_value_get_type(IkarusEntityValue const * value) {
|
|
||||||
return value->_type;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ikarus_value_visit(
|
|
||||||
IkarusEntityValue const * value,
|
|
||||||
void (*toggle)(IkarusToggleValue const * value, void * data),
|
|
||||||
void (*number)(IkarusNumberValue const * value, void * data),
|
|
||||||
void (*text)(IkarusTextValue const * value, void * data),
|
|
||||||
void * data
|
|
||||||
) {
|
|
||||||
if (value == nullptr) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (value->_type) {
|
|
||||||
case IkarusPropertyType_Toggle: {
|
|
||||||
if (toggle != nullptr) {
|
|
||||||
toggle(&value->_data._toggle, data);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case IkarusPropertyType_Number: {
|
|
||||||
if (number != nullptr) {
|
|
||||||
number(&value->_data._number, data);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case IkarusPropertyType_Text: {
|
|
||||||
if (text != nullptr) {
|
|
||||||
text(&value->_data._text, data);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default: break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("toggle_value_creation", "[value]") {
|
|
||||||
auto toggle_value = ikarus_value_create_toggle(true);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_value_get_type(&toggle_value) == IkarusPropertyType_Toggle);
|
|
||||||
REQUIRE(ikarus_toggle_value_is_equal(&toggle_value._data._toggle, true));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("number_value_creation", "[value]") {
|
|
||||||
auto number_value = ikarus_value_create_number(1.0);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_value_get_type(&number_value) == IkarusPropertyType_Number);
|
|
||||||
REQUIRE(ikarus_number_value_is_equal(&number_value._data._number, 1.0));
|
|
||||||
|
|
||||||
auto nan_value = ikarus_value_create_number(std::numeric_limits<long double>::quiet_NaN());
|
|
||||||
REQUIRE(ikarus_value_is_invalid(&nan_value));
|
|
||||||
auto signaling_non_value = ikarus_value_create_number(std::numeric_limits<long double>::signaling_NaN());
|
|
||||||
REQUIRE(ikarus_value_is_invalid(&signaling_non_value));
|
|
||||||
auto inf_value = ikarus_value_create_number(std::numeric_limits<long double>::infinity());
|
|
||||||
REQUIRE(ikarus_value_is_invalid(&inf_value));
|
|
||||||
auto neg_inf_value = ikarus_value_create_number(-std::numeric_limits<long double>::infinity());
|
|
||||||
REQUIRE(ikarus_value_is_invalid(&neg_inf_value));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("text_value_creation", "[value]") {
|
|
||||||
auto text_value = ikarus_value_create_text("test");
|
|
||||||
|
|
||||||
REQUIRE(ikarus_value_get_type(&text_value) == IkarusPropertyType_Text);
|
|
||||||
REQUIRE(ikarus_text_value_is_equal(&text_value._data._text, "test"));
|
|
||||||
|
|
||||||
auto null_value = ikarus_value_create_text(nullptr);
|
|
||||||
REQUIRE(ikarus_value_is_invalid(&null_value));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("default_value_creation", "[value]") {
|
|
||||||
auto types = {
|
|
||||||
IkarusPropertyType_Toggle,
|
|
||||||
IkarusPropertyType_Number,
|
|
||||||
IkarusPropertyType_Text,
|
|
||||||
};
|
|
||||||
|
|
||||||
for (auto type : types) {
|
|
||||||
auto value = ikarus_value_get_default(type);
|
|
||||||
REQUIRE(ikarus_value_get_type(&value) == type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("toggle_value_underlying", "[value]") {
|
|
||||||
auto true_toggle_value = ikarus_value_create_toggle(true);
|
|
||||||
auto false_toggle_value = ikarus_value_create_toggle(false);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_toggle_value_get_underlying(&true_toggle_value._data._toggle) == true);
|
|
||||||
REQUIRE(ikarus_toggle_value_get_underlying(&false_toggle_value._data._toggle) == false);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("number_value_underlying", "[value]") {
|
|
||||||
auto zero_number_value = ikarus_value_create_number(0.0);
|
|
||||||
auto third_number_value = ikarus_value_create_number(1.0 / 3.0);
|
|
||||||
auto large_number_value = ikarus_value_create_number(1.2345678910e123);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_number_value_get_underlying(&zero_number_value._data._number) == 0.0);
|
|
||||||
REQUIRE(ikarus_number_value_get_underlying(&third_number_value._data._number) == 1.0 / 3.0);
|
|
||||||
REQUIRE(ikarus_number_value_get_underlying(&large_number_value._data._number) == 1.2345678910e123);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("text_value_underlying", "[value]") {
|
|
||||||
auto test_value = ikarus_value_create_text("test");
|
|
||||||
auto empty_value = ikarus_value_create_text("");
|
|
||||||
|
|
||||||
REQUIRE(std::strcmp(ikarus_text_value_get_underlying(&test_value._data._text), "test") == 0);
|
|
||||||
REQUIRE(std::strcmp(ikarus_text_value_get_underlying(&empty_value._data._text), "") == 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("toggle_comparison", "[value]") {
|
|
||||||
auto true_toggle_value = ikarus_value_create_toggle(true);
|
|
||||||
auto false_toggle_value = ikarus_value_create_toggle(false);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_toggle_value_is_equal(&true_toggle_value._data._toggle, true));
|
|
||||||
REQUIRE(ikarus_toggle_value_is_equal(&false_toggle_value._data._toggle, false));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("number_comparison", "[value]") {
|
|
||||||
auto zero_number_value = ikarus_value_create_number(0.0);
|
|
||||||
auto third_number_value = ikarus_value_create_number(1.0 / 3.0);
|
|
||||||
auto large_number_value = ikarus_value_create_number(1.2345678910e123);
|
|
||||||
|
|
||||||
REQUIRE(ikarus_number_value_is_equal(&zero_number_value._data._number, 0.0));
|
|
||||||
REQUIRE(ikarus_number_value_is_equal(&third_number_value._data._number, 1.0 / 6.0 + 1.0 / 6.0));
|
|
||||||
REQUIRE(ikarus_number_value_is_equal(&large_number_value._data._number, 1.2345678910e123));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("text_comparison", "[value]") {
|
|
||||||
auto test_value = ikarus_value_create_text("test");
|
|
||||||
auto empty_value = ikarus_value_create_text("");
|
|
||||||
|
|
||||||
REQUIRE(ikarus_text_value_is_equal(&test_value._data._text, "test"));
|
|
||||||
REQUIRE(ikarus_text_value_is_equal(&empty_value._data._text, ""));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("value_comparison", "[value]") {
|
|
||||||
auto true_toggle_value = ikarus_value_create_toggle(true);
|
|
||||||
auto false_toggle_value = ikarus_value_create_toggle(false);
|
|
||||||
auto number_value1 = ikarus_value_create_number(0.0);
|
|
||||||
auto number_value2 = ikarus_value_create_number(0.0);
|
|
||||||
auto invalid_value = ikarus_value_create_text(nullptr);
|
|
||||||
|
|
||||||
auto indeterminate_toggle = ikarus_value_create_indeterminate(IkarusPropertyType_Toggle);
|
|
||||||
auto indeterminate_number1 = ikarus_value_create_indeterminate(IkarusPropertyType_Number);
|
|
||||||
auto indeterminate_number2 = ikarus_value_create_indeterminate(IkarusPropertyType_Number);
|
|
||||||
|
|
||||||
REQUIRE(!ikarus_value_is_equal(nullptr, nullptr));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&true_toggle_value, nullptr));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(nullptr, &true_toggle_value));
|
|
||||||
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&invalid_value, &invalid_value));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&true_toggle_value, &invalid_value));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&invalid_value, &true_toggle_value));
|
|
||||||
|
|
||||||
REQUIRE(ikarus_value_is_equal(&true_toggle_value, &true_toggle_value));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&true_toggle_value, &false_toggle_value));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&true_toggle_value, &number_value1));
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&number_value1, &true_toggle_value));
|
|
||||||
REQUIRE(ikarus_value_is_equal(&number_value1, &number_value2));
|
|
||||||
|
|
||||||
REQUIRE(!ikarus_value_is_equal(&indeterminate_toggle, &indeterminate_number1));
|
|
||||||
REQUIRE(ikarus_value_is_equal(&indeterminate_number1, &indeterminate_number2));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("invalid_value", "[value]") {
|
|
||||||
auto invalid_value = ikarus_value_create_toggle(false);
|
|
||||||
invalid_value._state = IkarusEntityValueState_Invalid;
|
|
||||||
|
|
||||||
REQUIRE(ikarus_value_is_invalid(&invalid_value));
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_CASE("visit_value", "[value]") {
|
|
||||||
auto toggle_value = ikarus_value_create_toggle(true);
|
|
||||||
auto number_value = ikarus_value_create_number(0.0);
|
|
||||||
auto text_value = ikarus_value_create_text("test");
|
|
||||||
|
|
||||||
auto values = {
|
|
||||||
std::make_pair(toggle_value, 1),
|
|
||||||
std::make_pair(number_value, 2),
|
|
||||||
std::make_pair(text_value, 3),
|
|
||||||
};
|
|
||||||
|
|
||||||
for (auto [value, expected] : values) {
|
|
||||||
int test = 0;
|
|
||||||
|
|
||||||
ikarus_value_visit(
|
|
||||||
&value,
|
|
||||||
[](IkarusToggleValue const *, void * data) { *reinterpret_cast<decltype(test) *>(data) = 1; },
|
|
||||||
[](IkarusNumberValue const *, void * data) { *reinterpret_cast<decltype(test) *>(data) = 2; },
|
|
||||||
[](IkarusTextValue const *, void * data) { *reinterpret_cast<decltype(test) *>(data) = 3; },
|
|
||||||
&test
|
|
||||||
);
|
|
||||||
|
|
||||||
REQUIRE(test == expected);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue