#pragma once #include "../quantization/bounded_range.h" #include "../quantization/half_precision.h" #include "../quantization/smallest_three.h" #include "../utility/assert.h" #include "../utility/meta.h" #include "../utility/parameter.h" #include "../stream/serialize_traits.h" #include namespace bitstream { /** * @brief A trait used to serialize a single-precision float as half-precision */ template<> struct serialize_traits { template typename utility::is_writing_t static serialize(Stream& stream, in value) noexcept { uint32_t int_value = half_precision::quantize(value); BS_ASSERT(stream.serialize_bits(int_value, 16)); return true; } template typename utility::is_reading_t static serialize(Stream& stream, out value) noexcept { uint32_t int_value; BS_ASSERT(stream.serialize_bits(int_value, 16)); value = half_precision::dequantize(int_value); return true; } }; /** * @brief A trait used to quantize and serialize a float to be within a given range and precision */ template<> struct serialize_traits { template typename utility::is_writing_t static serialize(Stream& stream, in range, in value) noexcept { uint32_t int_value = range.quantize(value); BS_ASSERT(stream.serialize_bits(int_value, range.get_bits_required())); return true; } template typename utility::is_reading_t static serialize(Stream& stream, in range, out value) noexcept { uint32_t int_value; BS_ASSERT(stream.serialize_bits(int_value, range.get_bits_required())); value = range.dequantize(int_value); return true; } }; /** * @brief A trait used to quantize and serialize quaternions using the smallest-three algorithm */ template struct serialize_traits> { template typename utility::is_writing_t static serialize(Stream& stream, in value) noexcept { quantized_quaternion quantized_quat = smallest_three::quantize(value); BS_ASSERT(stream.serialize_bits(quantized_quat.m, 2)); BS_ASSERT(stream.serialize_bits(quantized_quat.a, BitsPerElement)); BS_ASSERT(stream.serialize_bits(quantized_quat.b, BitsPerElement)); BS_ASSERT(stream.serialize_bits(quantized_quat.c, BitsPerElement)); return true; } template typename utility::is_reading_t static serialize(Stream& stream, out value) noexcept { quantized_quaternion quantized_quat; BS_ASSERT(stream.serialize_bits(quantized_quat.m, 2)); BS_ASSERT(stream.serialize_bits(quantized_quat.a, BitsPerElement)); BS_ASSERT(stream.serialize_bits(quantized_quat.b, BitsPerElement)); BS_ASSERT(stream.serialize_bits(quantized_quat.c, BitsPerElement)); value = smallest_three::dequantize(quantized_quat); return true; } }; }