#pragma once
#include "vec2.h"
void bad_arg(const char*);
#ifndef _KERNEL_MODE
#include "rawaccel-error.hpp"
inline void bad_arg(const char* s) {
throw rawaccel::invalid_argument(s);
}
#endif
namespace rawaccel {
/// Struct to hold arguments for an acceleration function.
struct accel_args {
double offset = 0;
double accel = 0;
double limit = 2;
double exponent = 2;
double midpoint = 0;
double power_scale = 1;
double gain_cap = 0;
vec2d weight = { 1, 1 };
};
///
/// Struct to hold common acceleration curve implementation details.
///
struct accel_base {
/// Coefficients applied to acceleration per axis.
vec2d weight = { 1, 1 };
/// Generally, the acceleration ramp rate.
double speed_coeff = 0;
accel_base(const accel_args& args) {
verify(args);
speed_coeff = args.accel;
weight = args.weight;
}
///
/// Default transformation of speed -> acceleration.
///
inline double accelerate(double speed) const {
return speed_coeff * speed;
}
///
/// Default transformation of acceleration -> mouse input multipliers.
///
inline vec2d scale(double accel_val) const {
return {
weight.x * accel_val + 1,
weight.y * accel_val + 1
};
}
///
/// Verifies arguments as valid. Errors if not.
///
/// Arguments to verified.
void verify(const accel_args& args) const {
if (args.accel < 0) bad_arg("accel can not be negative, use a negative weight to compensate");
if (args.gain_cap > 0 && weight.x != weight.y) bad_arg("weight x and y values must be equal with a gain cap");
}
accel_base() = default;
};
}