diff --git a/CMakeLists.txt b/CMakeLists.txt
index 395d47b8..074b406b 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -30,6 +30,7 @@ option(SOURCEPP_USE_MDLPP "Build mdlpp library" ${SOURC
option(SOURCEPP_USE_SNDPP "Build sndpp library" ${SOURCEPP_LIBS_START_ENABLED})
option(SOURCEPP_USE_STEAMPP "Build steampp library" ${SOURCEPP_LIBS_START_ENABLED})
option(SOURCEPP_USE_TOOLPP "Build toolpp library" ${SOURCEPP_LIBS_START_ENABLED})
+option(SOURCEPP_USE_VCDPP "Build vcdpp library" ${SOURCEPP_LIBS_START_ENABLED})
option(SOURCEPP_USE_VCRYPTPP "Build vcryptpp library" ${SOURCEPP_LIBS_START_ENABLED})
option(SOURCEPP_USE_VPKPP "Build vpkpp library" ${SOURCEPP_LIBS_START_ENABLED})
option(SOURCEPP_USE_VTFPP "Build vtfpp library" ${SOURCEPP_LIBS_START_ENABLED})
@@ -74,6 +75,9 @@ endif()
if(SOURCEPP_USE_TOOLPP)
set(SOURCEPP_USE_KVPP ON CACHE INTERNAL "" FORCE)
endif()
+if(SOURCEPP_USE_VCDPP)
+ set(SOURCEPP_USE_VPKPP ON CACHE INTERNAL "" FORCE)
+endif()
if(SOURCEPP_USE_VPKPP)
set(SOURCEPP_USE_KVPP ON CACHE INTERNAL "" FORCE)
endif()
@@ -164,6 +168,7 @@ add_sourcepp_library(mdlpp TEST ) # sourcepp::mdlpp
add_sourcepp_library(sndpp TEST ) # sourcepp::sndpp
add_sourcepp_library(steampp C CSHARP PYTHON TEST ) # sourcepp::steampp
add_sourcepp_library(toolpp PYTHON TEST ) # sourcepp::toolpp
+add_sourcepp_library(vcdpp TEST ) # sourcepp::vcdpp
add_sourcepp_library(vcryptpp C CSHARP PYTHON TEST ) # sourcepp::vcryptpp
add_sourcepp_library(vpkpp C CSHARP PYTHON TEST ) # sourcepp::vpkpp
add_sourcepp_library(vtfpp C CSHARP PYTHON TEST BENCH) # sourcepp::vtfpp
@@ -179,7 +184,7 @@ sourcepp_test_setup_post()
# Print options
print_options(OPTIONS
- USE_BSPPP USE_DMXPP USE_FSPP USE_GAMEPP USE_KVPP USE_MDLPP USE_SNDPP USE_STEAMPP USE_TOOLPP USE_VCRYPTPP USE_VPKPP USE_VTFPP "\n"
+ USE_BSPPP USE_DMXPP USE_FSPP USE_GAMEPP USE_KVPP USE_MDLPP USE_SNDPP USE_STEAMPP USE_TOOLPP USE_VCDPP USE_VCRYPTPP USE_VPKPP USE_VTFPP "\n"
BUILD_C_WRAPPERS BUILD_CSHARP_WRAPPERS BUILD_PYTHON_WRAPPERS BUILD_WASM_WRAPPERS "\n"
BUILD_BENCHMARKS BUILD_WITH_TBB BUILD_WITH_THREADS BUILD_TESTS BUILD_TESTS_EXTRA BUILD_WIN7_COMPAT LINK_STATIC_MSVC_RUNTIME "\n")
diff --git a/README.md b/README.md
index befcb20b..f3fde517 100644
--- a/README.md
+++ b/README.md
@@ -173,6 +173,25 @@ The Python wrappers can be found on PyPI in the [sourcepp](https://pypi.org/proj
|
vcryptpp
diff --git a/include/vcdpp/IMAGE.h b/include/vcdpp/IMAGE.h
new file mode 100644
index 00000000..6f70f09b
--- /dev/null
+++ b/include/vcdpp/IMAGE.h
@@ -0,0 +1 @@
+#pragma once
diff --git a/include/vcdpp/VCD.h b/include/vcdpp/VCD.h
new file mode 100644
index 00000000..d1b85ad9
--- /dev/null
+++ b/include/vcdpp/VCD.h
@@ -0,0 +1,283 @@
+// ReSharper disable CppUnusedIncludeDirective
+
+#pragma once
+
+#include
+#include
+#include
+#include
+#include
+
+#include
+
+namespace vcdpp {
+
+struct Event {
+ enum class Type : uint8_t {
+ UNSPECIFIED = 0,
+ SECTION = 1,
+ EXPRESSION = 2,
+ LOOK_AT = 3,
+ MOVE_TO = 4,
+ SPEAK = 5,
+ GESTURE = 6,
+ SEQUENCE = 7,
+ FACE = 8,
+ FIRE_TRIGGER = 9,
+ FLEX_ANIMATION = 10,
+ SUBSCENE = 11,
+ LOOP = 12,
+ INTERRUPT = 13,
+ STOP_POINT = 14,
+ PERMIT_RESPONSES = 15,
+ GENERIC = 16,
+ CAMERA = 17,
+ SCRIPT = 18,
+ } type;
+ std::string name;
+ float startTime = 0.f;
+ float endTime = 0.f;
+ std::string param;
+ std::string param2;
+ std::string param3;
+
+ enum Flags : uint8_t {
+ FLAG_NONE = 0,
+ FLAG_RESUME_CONDITION = 1 << 0,
+ FLAG_LOCK_BODY_FACING = 1 << 1,
+ FLAG_FIXED_LENGTH = 1 << 2,
+ FLAG_ACTIVE = 1 << 3,
+ FLAG_FORCE_SHORT_MOVEMENT = 1 << 4,
+ FLAG_PLAY_OVER_SCRIPT = 1 << 5,
+ FLAG_SYNC_TO_FOLLOWING_GESTURE = 1 << 6,
+ } flags = FLAG_ACTIVE;
+
+ float pitch = 0.f;
+ float yaw = 0.f;
+
+ float distanceToTarget = 0.f;
+
+ enum class Interpolate : uint8_t {
+ DEFAULT = 0,
+ CATMULLROM_NORMALIZE_X,
+ EASEIN,
+ EASEOUT,
+ EASEINOUT,
+ BSPLINE,
+ LINEAR_INTERP,
+ KOCHANEK,
+ KOCHANEK_EARLY,
+ KOCHANEK_LATE,
+ SIMPLE_CUBIC,
+ CATMULLROM,
+ CATMULLROM_NORMALIZE,
+ CATMULLROM_TANGENT,
+ EXPONENTIAL_DECAY,
+ HOLD,
+ COUNT,
+ };
+
+ struct Curve {
+ Interpolate from = Interpolate::DEFAULT;
+ Interpolate to = Interpolate::DEFAULT;
+ };
+
+ struct Edge {
+ Curve curve;
+ float time = 0.f;
+ };
+
+ struct Sample {
+ float time = 0.f;
+ float value = 0.f;
+ std::optional curve;
+ };
+
+ struct RampLegacy {
+ float attack = 1.f;
+ float sustain = 1.f;
+ float decay = 1.f;
+ };
+ std::optional eventRampLegacy;
+
+ struct Ramp {
+ std::optional curve;
+ std::optional leftEdge;
+ std::optional rightEdge;
+ std::vector samples;
+ };
+ std::optional eventRamp;
+
+ struct RelativeTagLegacy {
+ std::string name;
+ std::string filename;
+ };
+
+ std::optional relativeTagLegacy;
+
+ struct Tag {
+ std::string name;
+ float value = 0.f;
+ };
+
+ std::vector relativeTags;
+ std::vector absoluteTagsPlaybackTimes;
+ std::vector absoluteTagsShiftedTimes;
+
+ struct FlexTimingTag {
+ Tag tag;
+ bool locked = false;
+ };
+
+ std::vector flexTimingTags;
+
+ struct FlexAnimation {
+ bool samplesUseTime = false;
+ std::optional curve;
+
+ struct Track {
+ std::string name;
+ bool disabled = false;
+ float minRange = 0.f;
+ float maxRange = 1.f;
+ std::optional leftEdge;
+ std::optional rightEdge;
+ std::vector primary;
+ std::optional> secondary;
+ };
+
+ std::vector |