// generic hud routines
if(!autocvar__hud_configure)
{
- if(!autocvar_hud_panel_strafehud ||
- (spectatee_status == -1 && (autocvar_hud_panel_strafehud == 1 || autocvar_hud_panel_strafehud == 3)) ||
- (autocvar_hud_panel_strafehud == 3 && !MUTATOR_CALLHOOK(HUD_StrafeHUD_showoptional))) { hud_lasttime = time; return; }
+ if(!autocvar_hud_panel_strafehud
+ || (spectatee_status == -1 && (autocvar_hud_panel_strafehud == 1 || autocvar_hud_panel_strafehud == 3))
+ || (autocvar_hud_panel_strafehud == 3 && !MUTATOR_CALLHOOK(HUD_StrafeHUD_showoptional)))
+ {
+ hud_lasttime = time;
+ return;
+ }
}
HUD_Panel_LoadCvars();
strafeplayer = csqcplayer;
}
- if(!csqcplayer || !strafeplayer) { hud_lasttime = time; return; }
+ if(!csqcplayer || !strafeplayer)
+ {
+ hud_lasttime = time;
+ return;
+ }
// draw strafehud
indicator_size.y = max(panel_size.y * min(autocvar_hud_panel_strafehud_switch_line_height, 10), 1);
indicator_size.z = 0;
- float num_dashes = nearbyint(autocvar_hud_panel_strafehud_switch_line);
+ float num_dashes = rint(autocvar_hud_panel_strafehud_switch_line);
bool has_top_arrow = autocvar_hud_panel_strafehud_switch_arrow == 1 || autocvar_hud_panel_strafehud_switch_arrow >= 3;
bool has_bottom_arrow = autocvar_hud_panel_strafehud_switch_arrow >= 2;
indicator_size.y = max(panel_size.y * min(autocvar_hud_panel_strafehud_bestangle_line_height, 10), 1);
indicator_size.z = 0;
- float num_dashes = nearbyint(autocvar_hud_panel_strafehud_bestangle_line);
+ float num_dashes = rint(autocvar_hud_panel_strafehud_bestangle_line);
bool has_top_arrow = autocvar_hud_panel_strafehud_bestangle_arrow == 1 || autocvar_hud_panel_strafehud_bestangle_arrow >= 3;
bool has_bottom_arrow = autocvar_hud_panel_strafehud_bestangle_arrow >= 2;
indicator_size.y = max(panel_size.y * min(autocvar_hud_panel_strafehud_wturn_line_height, 10), 1);
indicator_size.z = 0;
- float num_dashes = nearbyint(autocvar_hud_panel_strafehud_wturn_line);
+ float num_dashes = rint(autocvar_hud_panel_strafehud_wturn_line);
bool has_top_arrow = autocvar_hud_panel_strafehud_wturn_arrow == 1 || autocvar_hud_panel_strafehud_wturn_arrow >= 3;
bool has_bottom_arrow = autocvar_hud_panel_strafehud_wturn_arrow >= 2;
indicator_size.y = max(panel_size.y * min(autocvar_hud_panel_strafehud_angle_line_height, 10), 1);
indicator_size.z = 0;
- float num_dashes = nearbyint(autocvar_hud_panel_strafehud_angle_line);
+ float num_dashes = rint(autocvar_hud_panel_strafehud_angle_line);
bool has_top_arrow = autocvar_hud_panel_strafehud_angle_arrow == 1 || autocvar_hud_panel_strafehud_angle_arrow >= 3;
bool has_bottom_arrow = autocvar_hud_panel_strafehud_angle_arrow >= 2;
#pragma once
#include "../panel.qh"
-#include "strafehud/util.qh"
-#include "strafehud/draw.qh"
-#include "strafehud/core.qh"
-#include "strafehud/extra.qh"
+#include <client/hud/panel/strafehud/_mod.qh>
int autocvar_hud_panel_strafehud = 3;
bool autocvar__hud_panel_strafehud_demo = false;
bool autocvar_hud_panel_strafehud_unit_show = true;
int autocvar_hud_panel_strafehud_onground_mode = 2;
bool autocvar_hud_panel_strafehud_onground_friction = true;
+
+float autocvar_hud_panel_strafehud_timeout_ground = 0.1;
+float autocvar_hud_panel_strafehud_timeout_turn = 0.1;
+float autocvar_hud_panel_strafehud_antiflicker_angle = 0.01;
+float autocvar_hud_panel_strafehud_fps_update = 0.5;
+
bool autocvar_hud_panel_strafehud_bar_preaccel = true;
vector autocvar_hud_panel_strafehud_bar_preaccel_color = '0 1 0';
float autocvar_hud_panel_strafehud_bar_preaccel_alpha = 0.5;
float autocvar_hud_panel_strafehud_bar_accel_alpha = 0.5;
vector autocvar_hud_panel_strafehud_bar_overturn_color = '1 0 1';
float autocvar_hud_panel_strafehud_bar_overturn_alpha = 0.5;
+
float autocvar_hud_panel_strafehud_angle_alpha = 0.8;
vector autocvar_hud_panel_strafehud_angle_preaccel_color = '0 1 1';
vector autocvar_hud_panel_strafehud_angle_neutral_color = '1 1 0';
float autocvar_hud_panel_strafehud_wturn_line_height = 1;
int autocvar_hud_panel_strafehud_wturn_arrow = 1;
float autocvar_hud_panel_strafehud_wturn_arrow_size = 0.5;
+
bool autocvar_hud_panel_strafehud_direction = false;
vector autocvar_hud_panel_strafehud_direction_color = '0 0.5 1';
float autocvar_hud_panel_strafehud_direction_alpha = 1;
float autocvar_hud_panel_strafehud_direction_width = 0.25;
float autocvar_hud_panel_strafehud_direction_length = 0.02;
+
bool autocvar_hud_panel_strafehud_slickdetector = true;
float autocvar_hud_panel_strafehud_slickdetector_range = 200;
int autocvar_hud_panel_strafehud_slickdetector_granularity = 1;
vector autocvar_hud_panel_strafehud_slickdetector_color = '0 1 1';
float autocvar_hud_panel_strafehud_slickdetector_alpha = 0.5;
float autocvar_hud_panel_strafehud_slickdetector_height = 0.125;
+
bool autocvar_hud_panel_strafehud_startspeed = true;
float autocvar_hud_panel_strafehud_startspeed_fade = 4;
vector autocvar_hud_panel_strafehud_startspeed_color = '1 0.75 0';
vector autocvar_hud_panel_strafehud_jumpheight_color = '0 1 0.75';
vector autocvar_hud_panel_strafehud_jumpheight_pos = '0 -2 0';
float autocvar_hud_panel_strafehud_jumpheight_size = 1.5;
-float autocvar_hud_panel_strafehud_timeout_ground = 0.1;
-float autocvar_hud_panel_strafehud_timeout_turn = 0.1;
-float autocvar_hud_panel_strafehud_antiflicker_angle = 0.01;
-float autocvar_hud_panel_strafehud_fps_update = 0.5;
+bool autocvar_hud_panel_strafehud_vangle = false;
+vector autocvar_hud_panel_strafehud_vangle_color = '0.75 0.75 0.75';
+vector autocvar_hud_panel_strafehud_vangle_pos = '-0.25 1 0';
+float autocvar_hud_panel_strafehud_vangle_size = 1;
+bool autocvar_hud_panel_strafehud_strafeefficiency = false;
+vector autocvar_hud_panel_strafehud_strafeefficiency_pos = '0.25 1 0';
+float autocvar_hud_panel_strafehud_strafeefficiency_size = 1;
+int autocvar_hud_panel_strafehud_projection = 0;
+
bool autocvar_hud_panel_strafehud_sonar = false;
string autocvar_hud_panel_strafehud_sonar_audio = "misc/talk";
float autocvar_hud_panel_strafehud_sonar_start = 0.5;
float autocvar_hud_panel_strafehud_sonar_pitch_start = 0.9;
float autocvar_hud_panel_strafehud_sonar_pitch_range = 0.1;
float autocvar_hud_panel_strafehud_sonar_pitch_exponent = 1;
-bool autocvar_hud_panel_strafehud_vangle = false;
-vector autocvar_hud_panel_strafehud_vangle_color = '0.75 0.75 0.75';
-vector autocvar_hud_panel_strafehud_vangle_pos = '-0.25 1 0';
-float autocvar_hud_panel_strafehud_vangle_size = 1;
-bool autocvar_hud_panel_strafehud_strafeefficiency = false;
-vector autocvar_hud_panel_strafehud_strafeefficiency_pos = '0.25 1 0';
-float autocvar_hud_panel_strafehud_strafeefficiency_size = 1;
-int autocvar_hud_panel_strafehud_projection = 0;
const int STRAFEHUD_MODE_VIEW_CENTERED = 0;
const int STRAFEHUD_MODE_VELOCITY_CENTERED = 1;
// genmod.sh autogenerated file; do not modify
-#include <client/hud/panel/strafehud/core.qc>
#include <client/hud/panel/strafehud/draw.qc>
+#include <client/hud/panel/strafehud/draw_core.qc>
#include <client/hud/panel/strafehud/extra.qc>
#include <client/hud/panel/strafehud/util.qc>
// genmod.sh autogenerated file; do not modify
-#include <client/hud/panel/strafehud/core.qh>
#include <client/hud/panel/strafehud/draw.qh>
+#include <client/hud/panel/strafehud/draw_core.qh>
#include <client/hud/panel/strafehud/extra.qh>
#include <client/hud/panel/strafehud/util.qh>
+++ /dev/null
-#include "core.qh"
-
-#include <client/draw.qh>
-
-void StrafeHUD_DrawStrafeMeter(
- float shiftangle, float wishangle, float absolute_bestangle,
- float absolute_prebestangle, float absolute_overturnangle,
- bool moving, float hudangle)
-{
- // the neutral zone fills the whole strafe bar
- if(!moving)
- {
- // draw neutral zone
- if(panel_size.x > 0 && panel_size.y > 0 && autocvar_hud_panel_strafehud_bar_neutral_alpha > 0)
- {
- switch(autocvar_hud_panel_strafehud_style)
- {
- default:
- case STRAFEHUD_STYLE_DRAWFILL:
- drawfill(
- panel_pos, panel_size,
- autocvar_hud_panel_strafehud_bar_neutral_color,
- autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
- break;
-
- case STRAFEHUD_STYLE_PROGRESSBAR:
- HUD_Panel_DrawProgressBar(
- panel_pos, panel_size, "progressbar", 1, 0, 0,
- autocvar_hud_panel_strafehud_bar_neutral_color,
- autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
- }
- }
- }
- else
- {
- // calculate various zones of the strafe-o-meter
- float accelzone_left_startangle;
- float accelzone_right_startangle;
- float preaccelzone_left_startangle;
- float preaccelzone_right_startangle;
- float neutral_startangle;
- float overturn_startangle;
-
- float accelzone_offsetangle = absolute_overturnangle - absolute_bestangle;
- float preaccelzone_offsetangle = fabs(absolute_bestangle - absolute_prebestangle);
- float neutral_offsetangle = 360;
- float overturn_offsetangle = 360 - absolute_overturnangle * 2;
-
- if(!autocvar_hud_panel_strafehud_bar_preaccel)
- preaccelzone_offsetangle = 0;
-
- // assign starting angles and shift the current offset for every element
- float current_startangle = 0;
-
- preaccelzone_right_startangle = current_startangle;
- current_startangle += preaccelzone_offsetangle;
-
- accelzone_right_startangle = current_startangle;
- current_startangle += accelzone_offsetangle;
-
- overturn_startangle = current_startangle;
- current_startangle += overturn_offsetangle;
-
- accelzone_left_startangle = current_startangle;
- current_startangle += accelzone_offsetangle;
-
- preaccelzone_left_startangle = current_startangle;
- current_startangle += preaccelzone_offsetangle;
-
- neutral_startangle = current_startangle;
- neutral_offsetangle = 360 - current_startangle;
-
- // calculate how far off-center the strafe zones currently are
- shiftangle += neutral_offsetangle / 2 - wishangle;
-
- // shift strafe zones into correct place
- neutral_startangle += shiftangle;
- accelzone_left_startangle += shiftangle;
- accelzone_right_startangle += shiftangle;
- preaccelzone_left_startangle += shiftangle;
- preaccelzone_right_startangle += shiftangle;
- overturn_startangle += shiftangle;
-
- // draw left acceleration zone
- if(accelzone_offsetangle > 0)
- StrafeHUD_DrawStrafeHUD(
- accelzone_left_startangle, accelzone_offsetangle,
- autocvar_hud_panel_strafehud_bar_accel_color,
- autocvar_hud_panel_strafehud_bar_accel_alpha * panel_fg_alpha,
- autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_LEFT,
- hudangle);
-
- if(autocvar_hud_panel_strafehud_bar_preaccel && preaccelzone_offsetangle > 0)
- StrafeHUD_DrawStrafeHUD(
- preaccelzone_left_startangle, preaccelzone_offsetangle,
- autocvar_hud_panel_strafehud_bar_preaccel_color,
- autocvar_hud_panel_strafehud_bar_preaccel_alpha * panel_fg_alpha,
- autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_RIGHT,
- hudangle);
-
- // draw right acceleration zone
- if(accelzone_offsetangle > 0)
- StrafeHUD_DrawStrafeHUD(
- accelzone_right_startangle, accelzone_offsetangle,
- autocvar_hud_panel_strafehud_bar_accel_color,
- autocvar_hud_panel_strafehud_bar_accel_alpha * panel_fg_alpha,
- autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_RIGHT,
- hudangle);
-
- if(autocvar_hud_panel_strafehud_bar_preaccel && preaccelzone_offsetangle > 0)
- StrafeHUD_DrawStrafeHUD(
- preaccelzone_right_startangle, preaccelzone_offsetangle,
- autocvar_hud_panel_strafehud_bar_preaccel_color,
- autocvar_hud_panel_strafehud_bar_preaccel_alpha * panel_fg_alpha,
- autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_LEFT,
- hudangle);
-
- // draw overturn zone
- if(overturn_offsetangle > 0)
- StrafeHUD_DrawStrafeHUD(
- overturn_startangle, overturn_offsetangle,
- autocvar_hud_panel_strafehud_bar_overturn_color,
- autocvar_hud_panel_strafehud_bar_overturn_alpha * panel_fg_alpha,
- autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_BOTH,
- hudangle);
-
- // draw neutral zone
- if(neutral_offsetangle > 0)
- StrafeHUD_DrawStrafeHUD(
- neutral_startangle, neutral_offsetangle,
- autocvar_hud_panel_strafehud_bar_neutral_color,
- autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha,
- autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_NONE,
- hudangle);
- }
-}
-
-// draw the actual strafe angle indicator
-void StrafeHUD_DrawAngleIndicator(
- float angle, vector line_size, float arrow_size, int num_dashes,
- bool has_top_arrow, bool has_bottom_arrow, vector color, float alpha, float hudangle)
-{
- if(alpha <= 0) return;
-
- // bound to HUD area
- angle = bound(-hudangle / 2, angle, hudangle / 2);
-
- float offset = StrafeHUD_AngleToOffset(angle, hudangle);
- offset = StrafeHUD_ProjectOffset(offset, hudangle, false);
-
- StrafeHUD_DrawAngleIndicatorLine(line_size, offset, num_dashes, color, alpha);
-
- if(has_top_arrow)
- StrafeHUD_DrawAngleIndicatorArrow(arrow_size, offset, line_size, color, alpha, true);
-
- if(has_bottom_arrow)
- StrafeHUD_DrawAngleIndicatorArrow(arrow_size, offset, line_size, color, alpha, false);
-}
-
-// draw the line of the angle indicator
-void StrafeHUD_DrawAngleIndicatorLine(vector size, float offset, int num_dashes, vector color, float alpha)
-{
- if(num_dashes <= 0 || size.x <= 0 || size.y <= 0) return;
-
- vector segment_size = size;
- segment_size.y = size.y / (bound(1, num_dashes, size.y) * 2 - 1);
-
- for(float i = 0; i < size.y; i += segment_size.y * 2)
- {
- // check if last iteration
- if(i + segment_size.y * 2 >= size.y)
- segment_size.y = size.y - i;
-
- drawfill(
- panel_pos - eY * ((size.y - panel_size.y) / 2 - i) + eX * (offset - segment_size.x / 2),
- segment_size, color, alpha * panel_fg_alpha, DRAWFLAG_NORMAL);
- }
-}
-
-// draw the arrows on the angle indicator
-void StrafeHUD_DrawAngleIndicatorArrow(float size, float offset, vector line_size, vector color, float alpha, bool top)
-{
- if(size <= 0) return;
-
- if(top)
- {
- StrafeHUD_DrawStrafeArrow(
- panel_pos + eY * ((panel_size.y - line_size.y) / 2) + eX * offset,
- size, color, alpha * panel_fg_alpha, true, line_size.x);
- }
- else
- {
- StrafeHUD_DrawStrafeArrow(
- panel_pos + eY * ((panel_size.y - line_size.y) / 2 + line_size.y) + eX * offset,
- size, color, alpha * panel_fg_alpha, false, line_size.x);
- }
-}
-
-// direction indicator
-void StrafeHUD_DrawDirectionIndicator(int direction, bool opposite_direction, bool fwd)
-{
- vector direction_size_vertical;
- direction_size_vertical.x = max(panel_size.y * min(autocvar_hud_panel_strafehud_direction_width, 1), 1);
- direction_size_vertical.y = panel_size.y + direction_size_vertical.x * 2;
- direction_size_vertical.z = 0;
-
- vector direction_size_horizontal;
- direction_size_horizontal.x = panel_size.x * min(autocvar_hud_panel_strafehud_direction_length, .5);
- direction_size_horizontal.y = direction_size_vertical.x;
- direction_size_horizontal.z = 0;
-
- if(direction != STRAFEHUD_DIRECTION_NONE &&
- direction_size_vertical.x > 0 &&
- autocvar_hud_panel_strafehud_direction_alpha > 0)
- {
- bool indicator_direction = direction == STRAFEHUD_DIRECTION_LEFT;
-
- // invert left/right when strafing backwards or when strafing towards the opposite side indicated by the direction variable
- // if both conditions are true then it's inverted twice hence not inverted at all
- if(!fwd != opposite_direction)
- indicator_direction = !indicator_direction;
-
- // draw the direction indicator caps at the sides of the hud
- // vertical line
- if(direction_size_vertical.y > 0)
- drawfill(
- panel_pos - eY * direction_size_horizontal.y + eX * (indicator_direction ? -direction_size_vertical.x : panel_size.x),
- direction_size_vertical, autocvar_hud_panel_strafehud_direction_color,
- autocvar_hud_panel_strafehud_direction_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
-
- // top horizontal line
- drawfill(
- panel_pos + eX * (indicator_direction ? 0 : panel_size.x - direction_size_horizontal.x) - eY * direction_size_horizontal.y,
- direction_size_horizontal, autocvar_hud_panel_strafehud_direction_color,
- autocvar_hud_panel_strafehud_direction_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
-
- // bottom horizontal line
- drawfill(
- panel_pos + eX * (indicator_direction ? 0 : panel_size.x - direction_size_horizontal.x) + eY * panel_size.y,
- direction_size_horizontal, autocvar_hud_panel_strafehud_direction_color,
- autocvar_hud_panel_strafehud_direction_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
- }
-}
+++ /dev/null
-#pragma once
-#include "../strafehud.qh"
-
-void StrafeHUD_DrawStrafeMeter(float, float, float, float, float, bool, float);
-void StrafeHUD_DrawAngleIndicator(float, vector, float, int, bool, bool, vector, float, float);
-void StrafeHUD_DrawAngleIndicatorLine(vector, float, int, vector, float);
-void StrafeHUD_DrawAngleIndicatorArrow(float, float, vector, vector, float, bool);
-void StrafeHUD_DrawDirectionIndicator(int, bool, bool);
// draw the strafe-o-meter bar
// aligns HUD elements perfectly in the hud area
-// also deals with wrapping around on edges, different HUD styles, etc
+// also deals with wrapping around on edges, different HUD styles, etc.
void StrafeHUD_DrawStrafeHUD(float startangle, float offsetangle, vector color, float alpha, int type, int gradient_type, float range)
{
float offset = StrafeHUD_AngleToOffset(startangle % 360, range);
float mirror_offset;
float mirror_width;
- if(StrafeHUD_IsGradient(type) && gradient_type == STRAFEHUD_GRADIENT_NONE)
- type = STRAFEHUD_STYLE_DRAWFILL;
+ if(width <= 0) return;
- if(alpha <= 0 && !StrafeHUD_IsGradient(type) || width <= 0)
- return;
+ if(StrafeHUD_IsGradient(type))
+ {
+ if(gradient_type == STRAFEHUD_GRADIENT_NONE)
+ {
+ type = STRAFEHUD_STYLE_DRAWFILL;
+ if(alpha <= 0) return;
+ }
+ }
+ else if(alpha <= 0) return;
// how much is hidden by the current hud angle
float hidden_width = (360 - range) / range * panel_size.x;
}
// accelerated gradient, does not support non-linear projection of the color and opacity within individual segments
-void StrafeHUD_DrawGradient(vector color1, vector color2, vector size, float original_width, float offset, float alpha, float gradient_offset, int gradient_type, float range)
+void StrafeHUD_DrawGradient(
+ vector color1, vector color2, vector size, float original_width,
+ float offset, float alpha, float gradient_offset, int gradient_type, float range)
{
if(gradient_type == STRAFEHUD_GRADIENT_BOTH)
{
float alpha1 = bound(0, alpha, 1);
float alpha2 = bound(0, autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha, 1);
- if((alpha1 + alpha2) == 0) return;
+ if(alpha1 + alpha2 == 0) return;
float ratio1 = gradient_offset / original_width;
- if(gradient_type == STRAFEHUD_GRADIENT_LEFT)
- ratio1 = 1 - ratio1;
-
float ratio2 = (gradient_offset + size.x) / original_width;
if(gradient_type == STRAFEHUD_GRADIENT_LEFT)
+ {
+ ratio1 = 1 - ratio1;
ratio2 = 1 - ratio2;
+ }
vector origin = HUD_Shift(panel_pos);
gradient_start.x = HUD_ScaleX(gradient_start.x);
}
// more expensive gradient rendering which does not rely on vertex gradients (required to properly render the color/opacity of individual segments in non-linear projection modes)
-void StrafeHUD_DrawSoftGradient(vector color1, vector color2, vector size, float original_width, float offset, float original_offset, float alpha, float gradient_offset, int gradient_type, float range)
+void StrafeHUD_DrawSoftGradient(
+ vector color1, vector color2, vector size, float original_width, float offset, float original_offset,
+ float alpha, float gradient_offset, int gradient_type, float range)
{
float alpha1 = bound(0, alpha, 1);
float alpha2 = bound(0, autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha, 1);
// draw the strafe arrows (inspired by drawspritearrow() in common/mutators/mutator/waypoints/waypointsprites.qc)
void StrafeHUD_DrawStrafeArrow(vector origin, float size, vector color, float alpha, bool flipped, float connection_width)
{
+ // alpha and size already checked
+
origin = HUD_Shift(origin);
- float width = HUD_ScaleX(size * 2 + connection_width);
+ float width = HUD_ScaleX(size * 2 + connection_width);
float height = HUD_ScaleY(size);
if(flipped) origin.y -= size;
R_BeginPolygon("", DRAWFLAG_NORMAL, true);
R_EndPolygon();
}
-// draw a fading text indicator above or below the strafe meter, return true if something was displayed
-void StrafeHUD_DrawTextIndicator(string text, float height, vector color, float fadetime, float lasttime, vector pos, float offset_top, float offset_bottom)
+// draw a fading text indicator above or below the strafe meter
+void StrafeHUD_DrawTextIndicator(
+ string text, float height, vector color, float fadetime, float lasttime,
+ vector pos, float offset_top, float offset_bottom)
{
- if((height <= 0) || (lasttime <= 0) || (fadetime <= 0) || ((time - lasttime) >= fadetime))
+ float time_frac = (time - lasttime) / fadetime;
+ if(height <= 0 || lasttime <= 0 || fadetime <= 0 || time_frac > 1)
return;
- float alpha = cos(((time - lasttime) / fadetime) * M_PI_2); // fade non-linear like the physics panel does
+ float alpha = cos(time_frac * M_PI_2); // fade non-linear like the physics panel does
vector size = panel_size;
size.y = height;
if(pos.y >= 1)
{
- pos.y--; // for calculations the position should not start at +1
+ --pos.y; // for calculations the position should not start at +1
pos = StrafeHUD_CalculateTextIndicatorPosition(pos);
pos.y += size.y + offset_top;
pos.y *= -1; // it's more intuitive for up to be positive
}
else if(pos.y <= -1)
{
- pos.y++; // for calculations the position should not start at -1
+ ++pos.y; // for calculations the position should not start at -1
pos = StrafeHUD_CalculateTextIndicatorPosition(pos);
pos.y *= -1; // it's more intuitive for down to be negative
pos.y += panel_size.y + offset_bottom;
drawstring_aspect(panel_pos + pos, text, size, color, alpha * panel_fg_alpha, DRAWFLAG_NORMAL);
}
-vector StrafeHUD_CalculateTextIndicatorPosition(vector pos)
-{
- pos.x *= panel_size.x / 2; // more intuitive since we start in the middle, this turns the range from -0.5 to +0.5 into -1 to +1
- pos.y *= panel_size.y;
- pos.z = 0;
-
- return pos;
-}
-
bool StrafeHUD_IsGradient(int style)
{
return style == STRAFEHUD_STYLE_GRADIENT || style == STRAFEHUD_STYLE_SOFT_GRADIENT;
void StrafeHUD_DrawSoftGradient(vector, vector, vector, float, float, float, float, float, int, float);
void StrafeHUD_DrawStrafeArrow(vector, float, vector, float, bool, float);
void StrafeHUD_DrawTextIndicator(string, float, vector, float, float, vector, float, float);
-vector StrafeHUD_CalculateTextIndicatorPosition(vector);
bool StrafeHUD_IsGradient(int);
--- /dev/null
+#include "draw_core.qh"
+
+#include <client/draw.qh>
+
+void StrafeHUD_DrawStrafeMeter(
+ float shiftangle, float wishangle, float absolute_bestangle,
+ float absolute_prebestangle, float absolute_overturnangle,
+ bool moving, float hudangle)
+{
+ // the neutral zone fills the whole strafe bar
+ if(!moving)
+ {
+ // draw neutral zone
+ if(panel_size.x > 0 && panel_size.y > 0 && autocvar_hud_panel_strafehud_bar_neutral_alpha > 0)
+ {
+ switch(autocvar_hud_panel_strafehud_style)
+ {
+ default:
+ case STRAFEHUD_STYLE_DRAWFILL:
+ drawfill(
+ panel_pos, panel_size,
+ autocvar_hud_panel_strafehud_bar_neutral_color,
+ autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha,
+ DRAWFLAG_NORMAL);
+ break;
+
+ case STRAFEHUD_STYLE_PROGRESSBAR:
+ HUD_Panel_DrawProgressBar(
+ panel_pos, panel_size, "progressbar", 1, 0, 0,
+ autocvar_hud_panel_strafehud_bar_neutral_color,
+ autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha,
+ DRAWFLAG_NORMAL);
+ }
+ }
+ }
+ else
+ {
+ // calculate various zones of the strafe-o-meter
+ float accelzone_left_startangle;
+ float accelzone_right_startangle;
+ float preaccelzone_left_startangle;
+ float preaccelzone_right_startangle;
+ float neutral_startangle;
+ float overturn_startangle;
+
+ float accelzone_offsetangle = absolute_overturnangle - absolute_bestangle;
+ float preaccelzone_offsetangle = fabs(absolute_bestangle - absolute_prebestangle);
+ float neutral_offsetangle = 360;
+ float overturn_offsetangle = 360 - absolute_overturnangle * 2;
+
+ if(!autocvar_hud_panel_strafehud_bar_preaccel)
+ preaccelzone_offsetangle = 0;
+
+ // assign starting angles and shift the current offset for every element
+ float current_startangle = 0;
+
+ preaccelzone_right_startangle = current_startangle;
+ current_startangle += preaccelzone_offsetangle;
+
+ accelzone_right_startangle = current_startangle;
+ current_startangle += accelzone_offsetangle;
+
+ overturn_startangle = current_startangle;
+ current_startangle += overturn_offsetangle;
+
+ accelzone_left_startangle = current_startangle;
+ current_startangle += accelzone_offsetangle;
+
+ preaccelzone_left_startangle = current_startangle;
+ current_startangle += preaccelzone_offsetangle;
+
+ neutral_startangle = current_startangle;
+ neutral_offsetangle = 360 - current_startangle;
+
+ // calculate how far off-center the strafe zones currently are
+ shiftangle += neutral_offsetangle / 2 - wishangle;
+
+ // shift strafe zones into correct place
+ neutral_startangle += shiftangle;
+ accelzone_left_startangle += shiftangle;
+ accelzone_right_startangle += shiftangle;
+ preaccelzone_left_startangle += shiftangle;
+ preaccelzone_right_startangle += shiftangle;
+ overturn_startangle += shiftangle;
+
+ // draw left acceleration zone
+ if(accelzone_offsetangle > 0)
+ StrafeHUD_DrawStrafeHUD(
+ accelzone_left_startangle, accelzone_offsetangle,
+ autocvar_hud_panel_strafehud_bar_accel_color,
+ autocvar_hud_panel_strafehud_bar_accel_alpha * panel_fg_alpha,
+ autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_LEFT,
+ hudangle);
+
+ if(autocvar_hud_panel_strafehud_bar_preaccel && preaccelzone_offsetangle > 0)
+ StrafeHUD_DrawStrafeHUD(
+ preaccelzone_left_startangle, preaccelzone_offsetangle,
+ autocvar_hud_panel_strafehud_bar_preaccel_color,
+ autocvar_hud_panel_strafehud_bar_preaccel_alpha * panel_fg_alpha,
+ autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_RIGHT,
+ hudangle);
+
+ // draw right acceleration zone
+ if(accelzone_offsetangle > 0)
+ StrafeHUD_DrawStrafeHUD(
+ accelzone_right_startangle, accelzone_offsetangle,
+ autocvar_hud_panel_strafehud_bar_accel_color,
+ autocvar_hud_panel_strafehud_bar_accel_alpha * panel_fg_alpha,
+ autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_RIGHT,
+ hudangle);
+
+ if(autocvar_hud_panel_strafehud_bar_preaccel && preaccelzone_offsetangle > 0)
+ StrafeHUD_DrawStrafeHUD(
+ preaccelzone_right_startangle, preaccelzone_offsetangle,
+ autocvar_hud_panel_strafehud_bar_preaccel_color,
+ autocvar_hud_panel_strafehud_bar_preaccel_alpha * panel_fg_alpha,
+ autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_LEFT,
+ hudangle);
+
+ // draw overturn zone
+ if(overturn_offsetangle > 0)
+ StrafeHUD_DrawStrafeHUD(
+ overturn_startangle, overturn_offsetangle,
+ autocvar_hud_panel_strafehud_bar_overturn_color,
+ autocvar_hud_panel_strafehud_bar_overturn_alpha * panel_fg_alpha,
+ autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_BOTH,
+ hudangle);
+
+ // draw neutral zone
+ if(neutral_offsetangle > 0)
+ StrafeHUD_DrawStrafeHUD(
+ neutral_startangle, neutral_offsetangle,
+ autocvar_hud_panel_strafehud_bar_neutral_color,
+ autocvar_hud_panel_strafehud_bar_neutral_alpha * panel_fg_alpha,
+ autocvar_hud_panel_strafehud_style, STRAFEHUD_GRADIENT_NONE,
+ hudangle);
+ }
+}
+
+// draw the actual strafe angle indicator
+void StrafeHUD_DrawAngleIndicator(
+ float angle, vector line_size, float arrow_size, int num_dashes,
+ bool has_top_arrow, bool has_bottom_arrow, vector color, float alpha, float hudangle)
+{
+ if(alpha <= 0) return;
+
+ // bound to HUD area
+ angle = bound(-hudangle / 2, angle, hudangle / 2);
+
+ float offset = StrafeHUD_AngleToOffset(angle, hudangle);
+ offset = StrafeHUD_ProjectOffset(offset, hudangle, false);
+
+ StrafeHUD_DrawAngleIndicatorLine(line_size, offset, num_dashes, color, alpha);
+
+ if(has_top_arrow)
+ StrafeHUD_DrawAngleIndicatorArrow(arrow_size, offset, line_size, color, alpha, true);
+
+ if(has_bottom_arrow)
+ StrafeHUD_DrawAngleIndicatorArrow(arrow_size, offset, line_size, color, alpha, false);
+}
+
+// draw the line of the angle indicator
+void StrafeHUD_DrawAngleIndicatorLine(vector size, float offset, int num_dashes, vector color, float alpha)
+{
+ if(num_dashes <= 0 || size.x <= 0 || size.y <= 0) return;
+
+ vector segment_size = size;
+ segment_size.y = size.y / (bound(1, num_dashes, size.y) * 2 - 1);
+
+ for(float i = 0; i < size.y; i += segment_size.y * 2)
+ {
+ // check if last iteration
+ if(i + segment_size.y * 2 >= size.y)
+ segment_size.y = size.y - i;
+
+ drawfill(
+ panel_pos - eY * ((size.y - panel_size.y) / 2 - i) + eX * (offset - segment_size.x / 2),
+ segment_size, color, alpha * panel_fg_alpha, DRAWFLAG_NORMAL);
+ }
+}
+
+// draw the arrows on the angle indicator
+void StrafeHUD_DrawAngleIndicatorArrow(float size, float offset, vector line_size, vector color, float alpha, bool top)
+{
+ if(size <= 0) return;
+
+ if(top)
+ {
+ StrafeHUD_DrawStrafeArrow(
+ panel_pos + eY * ((panel_size.y - line_size.y) / 2) + eX * offset,
+ size, color, alpha * panel_fg_alpha, true, line_size.x);
+ }
+ else
+ {
+ StrafeHUD_DrawStrafeArrow(
+ panel_pos + eY * ((panel_size.y - line_size.y) / 2 + line_size.y) + eX * offset,
+ size, color, alpha * panel_fg_alpha, false, line_size.x);
+ }
+}
+
+// direction indicator
+void StrafeHUD_DrawDirectionIndicator(int direction, bool opposite_direction, bool fwd)
+{
+ vector direction_size_vertical;
+ direction_size_vertical.x = max(panel_size.y * min(autocvar_hud_panel_strafehud_direction_width, 1), 1);
+ direction_size_vertical.y = panel_size.y + direction_size_vertical.x * 2;
+ direction_size_vertical.z = 0;
+
+ vector direction_size_horizontal;
+ direction_size_horizontal.x = panel_size.x * min(autocvar_hud_panel_strafehud_direction_length, .5);
+ direction_size_horizontal.y = direction_size_vertical.x;
+ direction_size_horizontal.z = 0;
+
+ if(direction != STRAFEHUD_DIRECTION_NONE &&
+ direction_size_vertical.x > 0 &&
+ autocvar_hud_panel_strafehud_direction_alpha > 0)
+ {
+ bool indicator_direction = direction == STRAFEHUD_DIRECTION_LEFT;
+
+ // invert left/right when strafing backwards or when strafing towards the opposite side indicated by the direction variable
+ // if both conditions are true then it's inverted twice hence not inverted at all
+ if(!fwd != opposite_direction)
+ indicator_direction = !indicator_direction;
+
+ // draw the direction indicator caps at the sides of the hud
+ // vertical line
+ if(direction_size_vertical.y > 0)
+ drawfill(
+ panel_pos - eY * direction_size_horizontal.y + eX * (indicator_direction ? -direction_size_vertical.x : panel_size.x),
+ direction_size_vertical, autocvar_hud_panel_strafehud_direction_color,
+ autocvar_hud_panel_strafehud_direction_alpha * panel_fg_alpha,
+ DRAWFLAG_NORMAL);
+
+ // top horizontal line
+ drawfill(
+ panel_pos + eX * (indicator_direction ? 0 : panel_size.x - direction_size_horizontal.x) - eY * direction_size_horizontal.y,
+ direction_size_horizontal, autocvar_hud_panel_strafehud_direction_color,
+ autocvar_hud_panel_strafehud_direction_alpha * panel_fg_alpha,
+ DRAWFLAG_NORMAL);
+
+ // bottom horizontal line
+ drawfill(
+ panel_pos + eX * (indicator_direction ? 0 : panel_size.x - direction_size_horizontal.x) + eY * panel_size.y,
+ direction_size_horizontal, autocvar_hud_panel_strafehud_direction_color,
+ autocvar_hud_panel_strafehud_direction_alpha * panel_fg_alpha,
+ DRAWFLAG_NORMAL);
+ }
+}
--- /dev/null
+#pragma once
+#include "../strafehud.qh"
+
+void StrafeHUD_DrawStrafeMeter(float, float, float, float, float, bool, float);
+void StrafeHUD_DrawAngleIndicator(float, vector, float, int, bool, bool, vector, float, float);
+void StrafeHUD_DrawAngleIndicatorLine(vector, float, int, vector, float);
+void StrafeHUD_DrawAngleIndicatorArrow(float, float, vector, vector, float, bool);
+void StrafeHUD_DrawDirectionIndicator(int, bool, bool);
vector slickdetector_size = panel_size;
slickdetector_size.y = slickdetector_height;
- // top horizontal line
- drawfill(
- panel_pos - eY * slickdetector_size.y, slickdetector_size,
- autocvar_hud_panel_strafehud_slickdetector_color,
- autocvar_hud_panel_strafehud_slickdetector_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
-
- // bottom horizontal line
- drawfill(
- panel_pos + eY * panel_size.y,
- slickdetector_size, autocvar_hud_panel_strafehud_slickdetector_color,
- autocvar_hud_panel_strafehud_slickdetector_alpha * panel_fg_alpha,
- DRAWFLAG_NORMAL);
+ // horizontal lines
+ for(int i = 0; i <= 1; ++i)
+ {
+ float y_offset = (i == 0)
+ ? -slickdetector_size.y // top
+ : panel_size.y; // bottom
+ drawfill(
+ panel_pos + eY * y_offset,
+ slickdetector_size, autocvar_hud_panel_strafehud_slickdetector_color,
+ autocvar_hud_panel_strafehud_slickdetector_alpha * panel_fg_alpha,
+ DRAWFLAG_NORMAL);
+ }
}
return slickdetector_height;
// vertical angle for weapon jumps
void StrafeHUD_DrawVerticalAngle(entity e, float text_offset_top, float text_offset_bottom)
{
- if(autocvar_hud_panel_strafehud_vangle)
+ if(!autocvar_hud_panel_strafehud_vangle) return;
+
+ float vangle = -PHYS_INPUT_ANGLES(e).x;
+ float vangle_height = autocvar_hud_panel_strafehud_vangle_size * panel_size.y;
+ string vangle_text = strcat(ftos_decimals(vangle, 2), "°");
+
+ StrafeHUD_DrawTextIndicator(
+ vangle_text, vangle_height,
+ autocvar_hud_panel_strafehud_vangle_color, 1,
+ time, autocvar_hud_panel_strafehud_vangle_pos,
+ text_offset_top, text_offset_bottom);
+}
+
+// show height achieved by a single jump
+// FIXME: checking z position differences is unreliable (warpzones, teleporter, kill, etc), use velocity to calculate jump height instead
+// FIXME: move capturing the jump height value out of the HUD
+void StrafeHUD_DrawJumpHeight(entity e, bool onground, bool swimming, float text_offset_top, float text_offset_bottom)
+{
+ float length_conversion_factor = StrafeHUD_GetLengthUnitFactor(autocvar_hud_speed_unit);
+ static float height_min = 0, height_max = 0; // ground and peak of jump z coordinates
+ static float jumpheight = 0, jumptime = 0; // displayed value and timestamp for fade out
+
+ // tries to catch kill and spectate but those are not reliable
+ if((e.velocity.z <= 0) || onground || swimming || IS_DEAD(e) || !IS_PLAYER(e))
{
- float vangle = -PHYS_INPUT_ANGLES(e).x;
- float vangle_height = autocvar_hud_panel_strafehud_vangle_size * panel_size.y;
- string vangle_text = strcat(ftos_decimals(vangle, 2), "°");
-
- StrafeHUD_DrawTextIndicator(
- vangle_text, vangle_height,
- autocvar_hud_panel_strafehud_vangle_color, 1,
- time, autocvar_hud_panel_strafehud_vangle_pos,
- text_offset_top, text_offset_bottom);
+ height_min = height_max = e.origin.z;
}
+ else if(e.origin.z > height_max)
+ {
+ height_max = e.origin.z;
+ float jumpheight_new = height_max - height_min;
+
+ if((jumpheight_new * length_conversion_factor) > max(autocvar_hud_panel_strafehud_jumpheight_min, 0))
+ {
+ jumpheight = jumpheight_new;
+ jumptime = time;
+ }
+ }
+
+ if(!autocvar_hud_panel_strafehud_jumpheight) return;
+
+ // use more decimals when displaying km or miles
+ int length_decimals = autocvar_hud_speed_unit >= 3 && autocvar_hud_speed_unit <= 5 ? 6 : 2;
+
+ float jumpheight_height = autocvar_hud_panel_strafehud_jumpheight_size * panel_size.y;
+ string jumpheight_text = ftos_decimals(jumpheight * length_conversion_factor, length_decimals);
+ if(autocvar_hud_panel_strafehud_unit_show)
+ jumpheight_text = strcat(jumpheight_text, StrafeHUD_GetLengthUnit(autocvar_hud_speed_unit));
+
+ StrafeHUD_DrawTextIndicator(
+ jumpheight_text, jumpheight_height,
+ autocvar_hud_panel_strafehud_jumpheight_color,
+ autocvar_hud_panel_strafehud_jumpheight_fade,
+ jumptime, autocvar_hud_panel_strafehud_jumpheight_pos,
+ text_offset_top, text_offset_bottom);
+}
+
+// strafe efficiency, percentage of how far away the current angle is from the optimal angle
+// the percentage changes linearly with angular distance
+void StrafeHUD_DrawStrafeEfficiency(float strafe_ratio, float text_offset_top, float text_offset_bottom)
+{
+ if(!autocvar_hud_panel_strafehud_strafeefficiency) return;
+
+ float strafeeff_height = autocvar_hud_panel_strafehud_strafeefficiency_size * panel_size.y;
+ string strafeeff_text = strcat(ftos_decimals(strafe_ratio * 100, 2), "%");
+ vector strafeeff_color = StrafeHUD_MixColors('1 1 1', (strafe_ratio > 0 ? '0 1 0' : '1 0 0'), fabs(strafe_ratio));
+
+ StrafeHUD_DrawTextIndicator(
+ strafeeff_text, strafeeff_height,
+ strafeeff_color, 1,
+ time, autocvar_hud_panel_strafehud_strafeefficiency_pos,
+ text_offset_top, text_offset_bottom);
+}
+
+// show speed when crossing the start trigger
+// FIXME: move capturing the race start speed value out of the HUD
+void StrafeHUD_DrawStartSpeed(float speed, float text_offset_top, float text_offset_bottom)
+{
+ static float startspeed = 0, starttime = 0; // displayed value and timestamp for fade out
+
+ // check if the start trigger was hit (will also trigger if the finish trigger was hit if those have the same ID)
+ if((race_nextcheckpoint == 1) || (race_checkpoint == 254 && race_nextcheckpoint == 255))
+ {
+ if((race_checkpointtime > 0) && (starttime != race_checkpointtime))
+ {
+ starttime = race_checkpointtime;
+ startspeed = speed;
+ }
+ }
+
+ if(!autocvar_hud_panel_strafehud_startspeed) return;
+
+ float speed_conversion_factor = GetSpeedUnitFactor(autocvar_hud_speed_unit);
+ float startspeed_height = autocvar_hud_panel_strafehud_startspeed_size * panel_size.y;
+ string startspeed_text = ftos_decimals(startspeed * speed_conversion_factor, 2);
+ if(autocvar_hud_panel_strafehud_unit_show)
+ startspeed_text = strcat(startspeed_text, GetSpeedUnit(autocvar_hud_speed_unit));
+
+ StrafeHUD_DrawTextIndicator(
+ startspeed_text, startspeed_height,
+ autocvar_hud_panel_strafehud_startspeed_color,
+ autocvar_hud_panel_strafehud_startspeed_fade,
+ starttime, autocvar_hud_panel_strafehud_startspeed_pos,
+ text_offset_top, text_offset_bottom);
}
// strafe sonar for audible feedback when strafing
return sonarsound;
}
-
-// show height achieved by a single jump
-// FIXME: checking z position differences is unreliable (warpzones, teleporter, kill, etc), use velocity to calculate jump height instead
-// FIXME: move capturing the jump height value out of the HUD
-void StrafeHUD_DrawJumpHeight(entity e, bool onground, bool swimming, float text_offset_top, float text_offset_bottom)
-{
- float length_conversion_factor = StrafeHUD_GetLengthUnitFactor(autocvar_hud_speed_unit);
- static float height_min = 0, height_max = 0; // ground and peak of jump z coordinates
- static float jumpheight = 0, jumptime = 0; // displayed value and timestamp for fade out
-
- // tries to catch kill and spectate but those are not reliable
- if((e.velocity.z <= 0) || onground || swimming || IS_DEAD(e) || !IS_PLAYER(e))
- {
- height_min = height_max = e.origin.z;
- }
- else if(e.origin.z > height_max)
- {
- height_max = e.origin.z;
- float jumpheight_new = height_max - height_min;
-
- if((jumpheight_new * length_conversion_factor) > max(autocvar_hud_panel_strafehud_jumpheight_min, 0))
- {
- jumpheight = jumpheight_new;
- jumptime = time;
- }
- }
-
- if(autocvar_hud_panel_strafehud_jumpheight)
- {
- // use more decimals when displaying km or miles
- int length_decimals = autocvar_hud_speed_unit >= 3 && autocvar_hud_speed_unit <= 5 ? 6 : 2;
-
- float jumpheight_height = autocvar_hud_panel_strafehud_jumpheight_size * panel_size.y;
- string jumpheight_text = ftos_decimals(jumpheight * length_conversion_factor, length_decimals);
- if(autocvar_hud_panel_strafehud_unit_show)
- jumpheight_text = strcat(jumpheight_text, StrafeHUD_GetLengthUnit(autocvar_hud_speed_unit));
-
- StrafeHUD_DrawTextIndicator(
- jumpheight_text, jumpheight_height,
- autocvar_hud_panel_strafehud_jumpheight_color,
- autocvar_hud_panel_strafehud_jumpheight_fade,
- jumptime, autocvar_hud_panel_strafehud_jumpheight_pos,
- text_offset_top, text_offset_bottom);
- }
-}
-
-// strafe efficiency, percentage of how far away the current angle is from the optimal angle
-// the percentage changes linearly with angular distance
-void StrafeHUD_DrawStrafeEfficiency(float strafe_ratio, float text_offset_top, float text_offset_bottom)
-{
- if(autocvar_hud_panel_strafehud_strafeefficiency)
- {
- float strafeeff_height = autocvar_hud_panel_strafehud_strafeefficiency_size * panel_size.y;
- string strafeeff_text = strcat(ftos_decimals(strafe_ratio * 100, 2), "%");
- vector strafeeff_color = '1 1 1' - (strafe_ratio > 0 ? '1 0 1' : '0 1 1') * fabs(strafe_ratio);
-
- StrafeHUD_DrawTextIndicator(
- strafeeff_text, strafeeff_height,
- strafeeff_color, 1,
- time, autocvar_hud_panel_strafehud_strafeefficiency_pos,
- text_offset_top, text_offset_bottom);
- }
-}
-
-// show speed when crossing the start trigger
-// FIXME: move capturing the race start speed value out of the HUD
-void StrafeHUD_DrawStartSpeed(float speed, float text_offset_top, float text_offset_bottom)
-{
- static float startspeed = 0, starttime = 0; // displayed value and timestamp for fade out
-
- // check if the start trigger was hit (will also trigger if the finish trigger was hit if those have the same ID)
- if((race_nextcheckpoint == 1) || (race_checkpoint == 254 && race_nextcheckpoint == 255))
- {
- if((race_checkpointtime > 0) && (starttime != race_checkpointtime))
- {
- starttime = race_checkpointtime;
- startspeed = speed;
- }
- }
-
- if(autocvar_hud_panel_strafehud_startspeed)
- {
- float speed_conversion_factor = GetSpeedUnitFactor(autocvar_hud_speed_unit);
- float startspeed_height = autocvar_hud_panel_strafehud_startspeed_size * panel_size.y;
- string startspeed_text = ftos_decimals(startspeed * speed_conversion_factor, 2);
- if(autocvar_hud_panel_strafehud_unit_show)
- startspeed_text = strcat(startspeed_text, GetSpeedUnit(autocvar_hud_speed_unit));
-
- StrafeHUD_DrawTextIndicator(
- startspeed_text, startspeed_height,
- autocvar_hud_panel_strafehud_startspeed_color,
- autocvar_hud_panel_strafehud_startspeed_fade,
- starttime, autocvar_hud_panel_strafehud_startspeed_pos,
- text_offset_top, text_offset_bottom);
- }
-}
#include "../strafehud.qh"
float StrafeHUD_DrawSlickDetector(entity, bool);
+
void StrafeHUD_DrawVerticalAngle(entity, float, float);
-void StrafeHUD_Sonar(float, string);
-string StrafeHUD_UpdateSonarSound();
void StrafeHUD_DrawJumpHeight(entity, bool, bool, float, float);
void StrafeHUD_DrawStrafeEfficiency(float, float, float);
void StrafeHUD_DrawStartSpeed(float, float, float);
+
+void StrafeHUD_Sonar(float, string);
+string StrafeHUD_UpdateSonarSound();
if(dt_client > .05) // server splits frames longer than 50 ms into two moves (DarkPlaces behaviour)
dt_client /= 2; // does not ensure frames are smaller than 50 ms, just splits large frames in half, matches server behaviour
- // calculate average frametime
- // calculated using a weighted arithmetic mean, where the weighting is equal to the frametime itself
- // for example, given a 1 ms frame and a 9 ms frame we have:
- // a total time of 10 ms
- // a weighted sum of 1 ms * 1 ms + 9 ms * 9 ms = 82 ms^2
- // the final result is 82 ms^2 / 10 ms = 8.2 ms
+ /* calculate average frametime
+ * calculated using a weighted arithmetic mean, where the weighting is equal to the frametime itself
+ * for example, given a 1 ms frame and a 9 ms frame we have:
+ * a total time of 10 ms
+ * a weighted sum of 1 ms * 1 ms + 9 ms * 9 ms = 82 ms^2
+ * the final result is 82 ms^2 / 10 ms = 8.2 ms
+ */
dt_sum += dt_client * dt_client; // weighted sum of all frametimes (mean numerator)
dt_time += dt_client; // time spent averaging (mean denominator)
float wishangle;
if(is_local) // if entity is local player
{
- if(movement.x == 0)
- {
- if(movement.y < 0)
- wishangle = -90;
- else if(movement.y > 0)
- wishangle = 90;
- else
- wishangle = 0;
- }
+ if(movement.y == 0)
+ wishangle = 0;
else
{
- if(movement.y == 0)
- {
- wishangle = 0;
- }
- else
+ wishangle = RAD2DEG * atan2(movement.y, movement.x);
+ // wrap the wish angle if it exceeds ±90°
+ if(fabs(wishangle) > 90)
{
- wishangle = RAD2DEG * atan2(movement.y, movement.x);
- // wrap the wish angle if it exceeds ±90°
- if(fabs(wishangle) > 90)
- {
- if(wishangle < 0)
- wishangle += 180;
- else
- wishangle -= 180;
-
- wishangle *= -1;
- }
+ if(wishangle < 0)
+ wishangle += 180;
+ else
+ wishangle -= 180;
+
+ wishangle *= -1;
}
}
}
float StrafeHUD_DetermineDirection(float angle, float wishangle, float antiflicker_angle)
{
if(wishangle > 0)
- {
return STRAFEHUD_DIRECTION_RIGHT;
- }
else if(wishangle < 0)
- {
return STRAFEHUD_DIRECTION_LEFT;
- }
else
{
if(angle > antiflicker_angle && angle < (180 - antiflicker_angle))
if(ratio >= 1) return color2;
return color1 + (color2 - color1) * ratio;
}
+
+vector StrafeHUD_CalculateTextIndicatorPosition(vector pos)
+{
+ pos.x *= panel_size.x / 2; // more intuitive since we start in the middle, this turns the range from -0.5 to +0.5 into -1 to +1
+ pos.y *= panel_size.y;
+ pos.z = 0;
+
+ return pos;
+}
float StrafeHUD_Project(float, float, bool);
float StrafeHUD_ProjectOffset(float, float, bool);
float StrafeHUD_ProjectWidth(float, float, float);
+
float StrafeHUD_GetLengthUnitFactor(int);
string StrafeHUD_GetLengthUnit(int);
+
float StrafeHUD_DetermineWaterLevel(entity);
float StrafeHUD_DetermineFrameTime();
float StrafeHUD_DetermineWishAngle(vector, int, bool);
float StrafeHUD_DetermineHudAngle(float, float, float);
float StrafeHUD_DetermineDirection(float, float, float);
bool StrafeHUD_DetermineJumpHeld(entity, int, bool);
+
vector StrafeHUD_MixColors(vector, vector, float);
+
+vector StrafeHUD_CalculateTextIndicatorPosition(vector);