100 lines
3.0 KiB
C++
100 lines
3.0 KiB
C++
#pragma once
|
|
|
|
#include <cstdint>
|
|
#include <optional>
|
|
#include <string>
|
|
#include <vector>
|
|
|
|
namespace mbgl::particle {
|
|
|
|
// Provider-neutral description of the canonical field bytes consumed by Core.
|
|
// Provider names, URLs and transport metadata deliberately do not cross this boundary.
|
|
struct ParticleFieldDescriptor {
|
|
std::string fieldID;
|
|
std::string fieldType;
|
|
std::string displayDomain;
|
|
// Assigned by the producer before decoding. The adapter never invents a revision.
|
|
uint64_t generation = 0;
|
|
uint64_t validTime = 0;
|
|
uint32_t width = 0;
|
|
uint32_t height = 0;
|
|
double west = -180.0;
|
|
double south = -85.0;
|
|
double east = 180.0;
|
|
double north = 85.0;
|
|
float noData = -9999.0f;
|
|
uint64_t dataVersion = 0;
|
|
uint64_t byteLength = 0;
|
|
uint32_t stride = 0;
|
|
std::string layout = "interleaved-uv";
|
|
std::string encoding = "float32-le";
|
|
std::string fieldSha256;
|
|
};
|
|
|
|
struct ParticleFieldSnapshot {
|
|
std::string fieldID;
|
|
std::string fieldType;
|
|
std::string displayDomain;
|
|
uint64_t validTime = 0;
|
|
uint32_t width = 0;
|
|
uint32_t height = 0;
|
|
double west = -180.0;
|
|
double south = -85.0;
|
|
double east = 180.0;
|
|
double north = 85.0;
|
|
float noData = -9999.0f;
|
|
uint64_t dataVersion = 0;
|
|
uint64_t generation = 0;
|
|
std::string fieldSha256;
|
|
std::vector<float> velocity;
|
|
std::vector<uint8_t> valid;
|
|
|
|
bool isValid() const;
|
|
bool isTimeInterpolationCompatibleWith(const ParticleFieldSnapshot&) const;
|
|
};
|
|
|
|
inline bool fieldIdentityChanged(const ParticleFieldSnapshot& current, const ParticleFieldSnapshot& next) {
|
|
return current.generation != next.generation || current.fieldID != next.fieldID ||
|
|
current.dataVersion != next.dataVersion;
|
|
}
|
|
|
|
inline bool sameFieldGpuContent(const ParticleFieldSnapshot& current, const ParticleFieldSnapshot& next) {
|
|
return current.fieldID == next.fieldID && current.dataVersion == next.dataVersion &&
|
|
current.fieldSha256 == next.fieldSha256 && current.isTimeInterpolationCompatibleWith(next);
|
|
}
|
|
|
|
struct ParticleFieldTimeWindow {
|
|
ParticleFieldSnapshot t0;
|
|
ParticleFieldSnapshot t1;
|
|
|
|
bool isValid() const { return t0.isValid() && t1.isValid() && t0.isTimeInterpolationCompatibleWith(t1); }
|
|
};
|
|
|
|
enum class ParticleFieldAdapterError : uint8_t {
|
|
None,
|
|
InvalidDescriptor,
|
|
UnsupportedFormat,
|
|
DimensionMismatch,
|
|
PayloadSizeMismatch,
|
|
InvalidTimestampOrIdentity,
|
|
NonFiniteData,
|
|
DecodeValidationFailure,
|
|
};
|
|
|
|
const char* particleFieldAdapterErrorName(ParticleFieldAdapterError);
|
|
|
|
struct ParticleFieldAdapterResult {
|
|
std::optional<ParticleFieldSnapshot> snapshot;
|
|
ParticleFieldAdapterError error = ParticleFieldAdapterError::None;
|
|
std::string message;
|
|
|
|
explicit operator bool() const { return snapshot.has_value(); }
|
|
};
|
|
|
|
class ParticleFieldDataAdapter final {
|
|
public:
|
|
static ParticleFieldAdapterResult decode(const ParticleFieldDescriptor&, const std::vector<char>&, uint64_t generation);
|
|
};
|
|
|
|
} // namespace mbgl::particle
|