diff --git a/rts/Lua/LuaWeaponDefs.cpp b/rts/Lua/LuaWeaponDefs.cpp index cecdc9b18be..ad06a3557f8 100644 --- a/rts/Lua/LuaWeaponDefs.cpp +++ b/rts/Lua/LuaWeaponDefs.cpp @@ -552,9 +552,11 @@ static bool InitParamMap() ADD_FLOAT("shieldGoodColorR", wd.shieldGoodColor.x); ADD_FLOAT("shieldGoodColorG", wd.shieldGoodColor.y); ADD_FLOAT("shieldGoodColorB", wd.shieldGoodColor.z); + ADD_FLOAT("shieldGoodColorA", wd.shieldGoodColor.w); ADD_FLOAT("shieldBadColorR", wd.shieldBadColor.x); ADD_FLOAT("shieldBadColorG", wd.shieldBadColor.y); ADD_FLOAT("shieldBadColorB", wd.shieldBadColor.z); + ADD_FLOAT("shieldBadColorA", wd.shieldBadColor.w); ADD_FLOAT("shieldAlpha", wd.shieldAlpha); ADD_INT("shieldInterceptType", wd.shieldInterceptType); diff --git a/rts/Rendering/Env/Particles/Classes/RepulseGfx.cpp b/rts/Rendering/Env/Particles/Classes/RepulseGfx.cpp index 53b3e295429..c7dce96457a 100644 --- a/rts/Rendering/Env/Particles/Classes/RepulseGfx.cpp +++ b/rts/Rendering/Env/Particles/Classes/RepulseGfx.cpp @@ -13,28 +13,27 @@ CR_BIND_DERIVED_POOL(CRepulseGfx, CProjectile, , projMemPool.alloc, projMemPool. CR_REG_METADATA(CRepulseGfx,( CR_MEMBER(repulsed), - CR_MEMBER(sqMaxDist), + CR_MEMBER(sqMaxOwnerDist), CR_MEMBER(age), CR_MEMBER(color), - CR_MEMBER(difs) + CR_MEMBER(vertexDists) )) -CRepulseGfx::CRepulseGfx(CUnit* owner, CProjectile* repulsed, float maxDist, const float3& color): - CProjectile(repulsed? repulsed->pos: ZeroVector, repulsed? repulsed->speed: ZeroVector, owner, false, false, false), - repulsed(repulsed), - sqMaxDist((maxDist * maxDist) + 100), +CRepulseGfx::CRepulseGfx(CUnit* owner, CProjectile* repulsee, float maxOwnerDist, const float4& gfxColor): + CProjectile((repulsee != nullptr)? repulsed->pos: ZeroVector, (repulsee != nullptr)? repulsee->speed: ZeroVector, owner, false, false, false), + repulsed(repulsee), age(0), - color(color) + sqMaxOwnerDist((maxOwnerDist * maxOwnerDist) + 100.0f), + color(gfxColor) { - if (repulsed) { + if (repulsed != nullptr) AddDeathDependence(repulsed, DEPENDENCE_REPULSE); - } checkCol = false; useAirLos = true; - SetRadiusAndHeight(maxDist, 0.0f); + SetRadiusAndHeight(maxOwnerDist, 0.0f); for (int y = 0; y < 5; ++y) { float yp = (y / 4.0f - 0.5f); @@ -42,10 +41,11 @@ CRepulseGfx::CRepulseGfx(CUnit* owner, CProjectile* repulsed, float maxDist, con for (int x = 0; x < 5; ++x) { float xp = (x / 4.0f - 0.5f); float d = 0; - if (xp != 0 || yp != 0) { + + if (xp != 0 || yp != 0) d = fastmath::apxsqrt2(xp * xp + yp * yp); - } - difs[y * 5 + x] = (1 - fastmath::cos(d * 2)) * 20; + + vertexDists[y * 5 + x] = (1.0f - fastmath::cos(d * 2.0f)) * 20.0f; } } } @@ -53,10 +53,11 @@ CRepulseGfx::CRepulseGfx(CUnit* owner, CProjectile* repulsed, float maxDist, con void CRepulseGfx::DependentDied(CObject* o) { - if (o == repulsed) { - repulsed = nullptr; - deleteMe = true; - } + if (o != repulsed) + return; + + repulsed = nullptr; + deleteMe = true; } void CRepulseGfx::Draw(CVertexArray* va) @@ -77,12 +78,14 @@ void CRepulseGfx::Draw(CVertexArray* va) float drawsize = 10.0f; float alpha = std::min(255.0f, age * 10.0f); + unsigned char col[4] = { - (unsigned char) (color.x * alpha), - (unsigned char) (color.y * alpha), - (unsigned char) (color.z * alpha), - (unsigned char) (0.2f * alpha), + (unsigned char) (color.x * alpha ), + (unsigned char) (color.y * alpha ), + (unsigned char) (color.z * alpha ), + (unsigned char) (color.w * alpha * 0.2f), }; + constexpr unsigned char col2[4] = {0, 0, 0, 0}; xdirDS = xdir * drawsize; ydirDS = ydir * drawsize; @@ -93,8 +96,8 @@ void CRepulseGfx::Draw(CVertexArray* va) const float txs = et->xend - et->xstart; const float tys = et->yend - et->ystart; - static const int loopCountY = 4; - static const int loopCountX = 4; + static constexpr int loopCountY = 4; + static constexpr int loopCountX = 4; va->EnlargeArrays(loopCountY * loopCountX * 4 + 16, 0, VA_SIZE_TC); @@ -106,60 +109,52 @@ void CRepulseGfx::Draw(CVertexArray* va) const float dx = x - 2.00f; const float rx = x * 0.25f; - va->AddVertexQTC(pos + xdirDS * (dx + 0) + ydirDS * (dy + 0) + zdir * difs[(y ) * 5 + x ], txo + (ry ) * txs, tyo + (rx ) * tys, col); - va->AddVertexQTC(pos + xdirDS * (dx + 0) + ydirDS * (dy + 1) + zdir * difs[(y + 1) * 5 + x ], txo + (ry + 0.25f) * txs, tyo + (rx ) * tys, col); - va->AddVertexQTC(pos + xdirDS * (dx + 1) + ydirDS * (dy + 1) + zdir * difs[(y + 1) * 5 + x + 1], txo + (ry + 0.25f) * txs, tyo + (rx + 0.25f) * tys, col); - va->AddVertexQTC(pos + xdirDS * (dx + 1) + ydirDS * (dy + 0) + zdir * difs[(y ) * 5 + x + 1], txo + (ry ) * txs, tyo + (rx + 0.25f) * tys, col); + va->AddVertexQTC(pos + xdirDS * (dx + 0) + ydirDS * (dy + 0) + zdir * vertexDists[(y ) * 5 + x ], txo + (ry ) * txs, tyo + (rx ) * tys, col); + va->AddVertexQTC(pos + xdirDS * (dx + 0) + ydirDS * (dy + 1) + zdir * vertexDists[(y + 1) * 5 + x ], txo + (ry + 0.25f) * txs, tyo + (rx ) * tys, col); + va->AddVertexQTC(pos + xdirDS * (dx + 1) + ydirDS * (dy + 1) + zdir * vertexDists[(y + 1) * 5 + x + 1], txo + (ry + 0.25f) * txs, tyo + (rx + 0.25f) * tys, col); + va->AddVertexQTC(pos + xdirDS * (dx + 1) + ydirDS * (dy + 0) + zdir * vertexDists[(y ) * 5 + x + 1], txo + (ry ) * txs, tyo + (rx + 0.25f) * tys, col); } } drawsize = 7.0f; alpha = std::min(10.0f, age / 2.0f); - col[0] = (unsigned char) (color.x * alpha); - col[1] = (unsigned char) (color.y * alpha); - col[2] = (unsigned char) (color.z * alpha); - col[3] = (unsigned char) (alpha * 0.4f); + + col[0] = (unsigned char) (color.x * alpha ); + col[1] = (unsigned char) (color.y * alpha ); + col[2] = (unsigned char) (color.z * alpha ); + col[3] = (unsigned char) (color.w * alpha * 0.4f); const AtlasedTexture* ct = projectileDrawer->repulsegfxtex; const float tx = (ct->xend + ct->xstart) * 0.5f; const float ty = (ct->yend + ct->ystart) * 0.5f; - static const unsigned char col2[4] = {0, 0, 0, 0}; - xdirDS = xdir * drawsize; ydirDS = ydir * drawsize; va->AddVertexQTC(owner->pos + (-xdir + ydir) * drawsize * 0.2f, tx, ty, col2); va->AddVertexQTC(owner->pos + ( xdir + ydir) * drawsize * 0.2f, tx, ty, col2); - va->AddVertexQTC( pos + xdirDS + ydirDS + zdir * difs[6], tx, ty, col); - va->AddVertexQTC( pos - xdirDS + ydirDS + zdir * difs[6], tx, ty, col); + va->AddVertexQTC( pos + xdirDS + ydirDS + zdir * vertexDists[6], tx, ty, col ); + va->AddVertexQTC( pos - xdirDS + ydirDS + zdir * vertexDists[6], tx, ty, col ); va->AddVertexQTC(owner->pos + (-xdir - ydir) * drawsize * 0.2f, tx, ty, col2); va->AddVertexQTC(owner->pos + ( xdir - ydir) * drawsize * 0.2f, tx, ty, col2); - va->AddVertexQTC( pos + xdirDS - ydirDS + zdir * difs[6], tx, ty, col); - va->AddVertexQTC( pos - xdirDS - ydirDS + zdir * difs[6], tx, ty, col); + va->AddVertexQTC( pos + xdirDS - ydirDS + zdir * vertexDists[6], tx, ty, col ); + va->AddVertexQTC( pos - xdirDS - ydirDS + zdir * vertexDists[6], tx, ty, col ); va->AddVertexQTC(owner->pos + (xdir - ydir) * drawsize * 0.2f, tx, ty, col2); va->AddVertexQTC(owner->pos + (xdir + ydir) * drawsize * 0.2f, tx, ty, col2); - va->AddVertexQTC( pos + xdirDS + ydirDS + zdir * difs[6], tx, ty, col); - va->AddVertexQTC( pos + xdirDS - ydirDS + zdir * difs[6], tx, ty, col); + va->AddVertexQTC( pos + xdirDS + ydirDS + zdir * vertexDists[6], tx, ty, col ); + va->AddVertexQTC( pos + xdirDS - ydirDS + zdir * vertexDists[6], tx, ty, col ); va->AddVertexQTC(owner->pos + (-xdir - ydir) * drawsize * 0.2f, tx, ty, col2); va->AddVertexQTC(owner->pos + (-xdir + ydir) * drawsize * 0.2f, tx, ty, col2); - va->AddVertexQTC( pos - xdirDS + ydirDS + zdir * difs[6], tx, ty, col); - va->AddVertexQTC( pos - xdirDS - ydirDS + zdir * difs[6], tx, ty, col); + va->AddVertexQTC( pos - xdirDS + ydirDS + zdir * vertexDists[6], tx, ty, col ); + va->AddVertexQTC( pos - xdirDS - ydirDS + zdir * vertexDists[6], tx, ty, col ); } void CRepulseGfx::Update() { - age++; - - if (repulsed && owner() && (repulsed->pos - owner()->pos).SqLength() > sqMaxDist) { - deleteMe = true; - } + age += 1; + deleteMe |= (repulsed != nullptr && owner() != nullptr && (repulsed->pos - owner()->pos).SqLength() > sqMaxOwnerDist); } -int CRepulseGfx::GetProjectilesCount() const -{ - return 20; -} diff --git a/rts/Rendering/Env/Particles/Classes/RepulseGfx.h b/rts/Rendering/Env/Particles/Classes/RepulseGfx.h index c9fed5db4a0..141dabd0d0e 100644 --- a/rts/Rendering/Env/Particles/Classes/RepulseGfx.h +++ b/rts/Rendering/Env/Particles/Classes/RepulseGfx.h @@ -14,25 +14,27 @@ class CRepulseGfx : public CProjectile CRepulseGfx() { } CRepulseGfx( CUnit* owner, - CProjectile* repulsed, - float maxDist, - const float3& color + CProjectile* repulsee, + float maxOwnerDist, + const float4& gfxColor ); void Draw(CVertexArray* va) override; void Update() override; - int GetProjectilesCount() const override; + int GetProjectilesCount() const override { return 20; } void DependentDied(CObject* o) override; private: CProjectile* repulsed; - float sqMaxDist; + int age; - float3 color; - float difs[25]; + float sqMaxOwnerDist; + float vertexDists[25]; + + float4 color; }; #endif // REPULSE_GFX_H diff --git a/rts/Rendering/Env/Particles/Classes/ShieldSegmentProjectile.cpp b/rts/Rendering/Env/Particles/Classes/ShieldSegmentProjectile.cpp index 655feeee889..6e247620558 100644 --- a/rts/Rendering/Env/Particles/Classes/ShieldSegmentProjectile.cpp +++ b/rts/Rendering/Env/Particles/Classes/ShieldSegmentProjectile.cpp @@ -122,7 +122,7 @@ bool ShieldSegmentCollection::AllowDrawing() //FIXME if Lua wants to draw the shield itself, we should draw all GL_QUADS in the `va` vertexArray first. // but doing so for each shield might reduce the performance. - // so might use a branch-predicion? -> save last return value and if it is true draw `va` before calling eventHandler.DrawShield() ??FIXME + // so might use a branch-predicion? -> save last return value and if it is true draw `va` before calling eventHandler.DrawShield() if (eventHandler.DrawShield(shield->owner, shield)) return allowDrawing; @@ -142,9 +142,9 @@ void ShieldSegmentCollection::UpdateColor() const WeaponDef* shieldDef = shield->weaponDef; // lerp between badColor and goodColor based on shield's current power - const float colorMix = std::min(1.0f, shield->GetCurPower() / std::max(1.0f, shieldDef->shieldPower)); + const float relPower = shield->GetCurPower() / std::max(1.0f, shieldDef->shieldPower); + const float lrpColor = std::min(1.0f, relPower); - const float3 colorf = mix(shieldDef->shieldBadColor, shieldDef->shieldGoodColor, colorMix); float alpha = shieldDef->visibleShield * shieldDef->shieldAlpha; if (shield->GetHitFrames() > 0 && shieldDef->visibleShieldHitFrames > 0) { @@ -154,12 +154,7 @@ void ShieldSegmentCollection::UpdateColor() alpha = std::min(alpha, 1.0f); } - color = SColor( - colorf.x * alpha, - colorf.y * alpha, - colorf.z * alpha, - alpha - ); + color = SColor(mix(shieldDef->shieldBadColor, shieldDef->shieldGoodColor, lrpColor) * alpha); } diff --git a/rts/Rendering/Env/Particles/Classes/SmokeProjectile2.cpp b/rts/Rendering/Env/Particles/Classes/SmokeProjectile2.cpp index dd735099772..d0c7aa64e66 100644 --- a/rts/Rendering/Env/Particles/Classes/SmokeProjectile2.cpp +++ b/rts/Rendering/Env/Particles/Classes/SmokeProjectile2.cpp @@ -67,9 +67,8 @@ CSmokeProjectile2::CSmokeProjectile2( ageSpeed = 1 / ttl; checkCol = false; castShadow = true; - if ((pos.y - CGround::GetApproximateHeight(pos.x, pos.z, false)) > 10) { - useAirLos = true; - } + useAirLos |= ((pos.y - CGround::GetApproximateHeight(pos.x, pos.z, false)) > 10.0f); + glowFalloff = 4.5f + guRNG.NextFloat() * 6; textureNum = (int)(guRNG.NextInt(projectileDrawer->smoketex.size())); } @@ -78,11 +77,8 @@ CSmokeProjectile2::CSmokeProjectile2( void CSmokeProjectile2::Init(const CUnit* owner, const float3& offset) { - if (offset.y - CGround::GetApproximateHeight(offset.x, offset.z, false) > 10) - useAirLos = true; - - if (!owner) - alwaysVisible = true; + useAirLos |= (offset.y - CGround::GetApproximateHeight(offset.x, offset.z, false) > 10.0f); + alwaysVisible |= (owner == nullptr); wantedPos += offset; diff --git a/rts/Rendering/ShadowHandler.cpp b/rts/Rendering/ShadowHandler.cpp index bee2aa172db..a96224409b8 100644 --- a/rts/Rendering/ShadowHandler.cpp +++ b/rts/Rendering/ShadowHandler.cpp @@ -421,7 +421,7 @@ static CMatrix44f ComposeLightMatrix(const ISkyLight* light) CMatrix44f lightMatrix; // sun direction is in world-space, invert it - lightMatrix.SetZ(-(light->GetLightDir())); + lightMatrix.SetZ(-float3(light->GetLightDir())); lightMatrix.SetX(((lightMatrix.GetZ()).cross( UpVector )).ANormalize()); lightMatrix.SetY(((lightMatrix.GetX()).cross(lightMatrix.GetZ())).ANormalize()); diff --git a/rts/Sim/Weapons/PlasmaRepulser.cpp b/rts/Sim/Weapons/PlasmaRepulser.cpp index 9a1608e4b17..a76c59a75b1 100644 --- a/rts/Sim/Weapons/PlasmaRepulser.cpp +++ b/rts/Sim/Weapons/PlasmaRepulser.cpp @@ -143,28 +143,22 @@ bool CPlasmaRepulser::IncomingProjectile(CWeaponProjectile* p, const float3& hit if (weaponDef->shieldRepulser) { // bounce the projectile - const int type = p->ShieldRepulse(weaponMuzzlePos, - weaponDef->shieldForce, - weaponDef->shieldMaxSpeed); - - if (type == 0) { - return false; - } else if (type == 1) { - owner->UseEnergy(weaponDef->shieldEnergyUse); - - if (weaponDef->shieldPower != 0) { - curPower -= shieldDamage; - } - } else { - //FIXME why do all weapons except LASERs do only (1 / GAME_SPEED) damage??? - // because they go inside and take time to get pushed back - // during that time they deal damage every frame - // so in total they do their nominal damage each second - // on the other hand lasers get insta-bounced in 1 frame - // regardless of shield pushing power - owner->UseEnergy(weaponDef->shieldEnergyUse / GAME_SPEED); - - curPower -= ((shieldDamage / GAME_SPEED) * (weaponDef->shieldPower != 0.0f)); + switch (p->ShieldRepulse(weaponMuzzlePos, weaponDef->shieldForce, weaponDef->shieldMaxSpeed)) { + case 0: { return false; } break; + case 1: { + owner->UseEnergy(weaponDef->shieldEnergyUse); + + curPower -= (shieldDamage * (weaponDef->shieldPower != 0.0f)); + } break; + default: { + // NOTE: + // all weapons except Lasers do only (1 / GAME_SPEED) damage + // (Lasers are insta-bounced, others spend time "inside" the + // shield dealing damage every frame) + owner->UseEnergy(weaponDef->shieldEnergyUse / GAME_SPEED); + + curPower -= ((shieldDamage / GAME_SPEED) * (weaponDef->shieldPower != 0.0f)); + } break; } if (spring::VectorInsertUnique(repulsedProjectiles, p, true)) { @@ -172,30 +166,29 @@ bool CPlasmaRepulser::IncomingProjectile(CWeaponProjectile* p, const float3& hit AddDeathDependence(p, DEPENDENCE_REPULSED); if (weaponDef->visibleShieldRepulse) { - const float colorMix = std::min(1.0f, curPower / std::max(1.0f, weaponDef->shieldPower)); - const float3 color = - (weaponDef->shieldGoodColor * colorMix) + - (weaponDef->shieldBadColor * (1.0f - colorMix)); + const float relPower = curPower / std::max(1.0f, weaponDef->shieldPower); + const float lrpColor = std::min(1.0f, relPower); - projMemPool.alloc(owner, p, radius, color); + projMemPool.alloc(owner, p, radius, mix(weaponDef->shieldBadColor, weaponDef->shieldGoodColor, lrpColor)); } } if (defHitFrames > 0) hitFrames = defHitFrames; - } else { - // kill the projectile - if (owner->UseEnergy(weaponDef->shieldEnergyUse)) { - curPower -= (shieldDamage * (weaponDef->shieldPower != 0.0f)); + return false; + } - p->Collision(); + // kill the projectile + if (owner->UseEnergy(weaponDef->shieldEnergyUse)) { + curPower -= (shieldDamage * (weaponDef->shieldPower != 0.0f)); - if (defHitFrames > 0) - hitFrames = defHitFrames; + p->Collision(); - return true; - } + if (defHitFrames > 0) + hitFrames = defHitFrames; + + return true; } return false; diff --git a/rts/Sim/Weapons/WeaponDef.cpp b/rts/Sim/Weapons/WeaponDef.cpp index fe2d096d7c7..8326f7cd881 100644 --- a/rts/Sim/Weapons/WeaponDef.cpp +++ b/rts/Sim/Weapons/WeaponDef.cpp @@ -189,10 +189,10 @@ WEAPONTAG(bool, visibleShieldRepulse).externalName("shield.visibleRepulse").fall .defaultValue(false).description("Is the (hard-coded) repulse effect rendered or not?"); WEAPONTAG(int, visibleShieldHitFrames).externalName("shield.visibleHitFrames").fallbackName("visibleShieldHitFrames") .defaultValue(0).description("The number of frames a shield becomes visible for when hit."); -WEAPONTAG(float3, shieldBadColor).externalName("shield.badColor").fallbackName("shieldBadColor") - .defaultValue(float3(1.0f, 0.5f, 0.5f)).description("The RGB colour the shield transitions to as its hit-points are reduced towards 0."); -WEAPONTAG(float3, shieldGoodColor).externalName("shield.goodColor").fallbackName("shieldGoodColor") - .defaultValue(float3(0.5f, 0.5f, 1.0f)).description("The RGB colour the shield transitions to as its hit-points are regenerated towards its maximum power."); +WEAPONTAG(float4, shieldBadColor).externalName("shield.badColor").fallbackName("shieldBadColor") + .defaultValue(float4(1.0f, 0.5f, 0.5f, 1.0f)).description("The RGBA colour the shield transitions to as its hit-points are reduced towards 0."); +WEAPONTAG(float4, shieldGoodColor).externalName("shield.goodColor").fallbackName("shieldGoodColor") + .defaultValue(float4(0.5f, 0.5f, 1.0f, 1.0f)).description("The RGBA colour the shield transitions to as its hit-points are regenerated towards its maximum power."); WEAPONTAG(float, shieldAlpha).externalName("shield.alpha").fallbackName("shieldAlpha") .defaultValue(0.2f).description("The alpha transparency of the shield whilst it is visible."); WEAPONTAG(std::string, shieldArmorTypeName).externalName("shield.armorType").fallbackName("shieldArmorType") diff --git a/rts/Sim/Weapons/WeaponDef.h b/rts/Sim/Weapons/WeaponDef.h index 5d8d01d422a..79c3b5cc8e9 100644 --- a/rts/Sim/Weapons/WeaponDef.h +++ b/rts/Sim/Weapons/WeaponDef.h @@ -6,7 +6,7 @@ #include "Sim/Misc/DamageArray.h" #include "Sim/Misc/GuiSoundSet.h" #include "Sim/Projectiles/WeaponProjectiles/WeaponProjectileTypes.h" -#include "System/float3.h" +#include "System/float4.h" #include "System/UnorderedMap.hpp" struct AtlasedTexture; @@ -171,8 +171,8 @@ struct WeaponDef float shieldPowerRegenEnergy; // how much energy is needed to regenerate power per second float shieldStartingPower; // how much power the shield has when first created int shieldRechargeDelay; // number of frames to delay recharging by after each hit - float3 shieldGoodColor; // color when shield at full power - float3 shieldBadColor; // color when shield is empty + float4 shieldGoodColor; // color when shield at full power + float4 shieldBadColor; // color when shield is empty float shieldAlpha; // shield alpha value int shieldArmorType; // armor type for the damage table std::string shieldArmorTypeName; // name of the armor type diff --git a/rts/System/float4.h b/rts/System/float4.h index dc954ea283e..ee267e2e503 100644 --- a/rts/System/float4.h +++ b/rts/System/float4.h @@ -26,43 +26,44 @@ struct float4 : public float3 float4(const float* f): float3(f[0], f[1], f[2]), w(f[3]) {} float4(const float x, const float y, const float z, const float w = 0.0f): float3(x, y, z), w(w) {} - inline float4& operator= (const float f[4]) { + float4 operator * (const float4& f) const { return {x * f.x, y * f.y, z * f.z, w * f.w}; } + float4 operator + (const float4& f) const { return {x + f.x, y + f.y, z + f.z, w + f.w}; } + float4 operator - (const float4& f) const { return {x - f.x, y - f.y, z - f.z, w - f.w}; } + + float4 operator * (float s) const { return {x * s, y * s, z * s, w * s}; } + float4 operator / (float s) const { return ((*this) * (1.0f / s)); } + + float4& operator = (const float f[4]) { x = f[0]; y = f[1]; z = f[2]; w = f[3]; return *this; } - inline void fromFloat3 (const float f[3]) { - x = f[0]; - y = f[1]; - z = f[2]; - } - - inline float4& operator= (const float3& f) { + float4& operator = (const float3& f) { x = f.x; y = f.y; z = f.z; return *this; } - inline float4& operator += (const float4& f) { + float4& operator += (const float4& f) { x += f.x; y += f.y; z += f.z; w += f.w; return *this; } - inline float4& operator -= (const float4& f) { + float4& operator -= (const float4& f) { x -= f.x; y -= f.y; z -= f.z; w -= f.w; return *this; } - inline float4& operator *= (const float4& f) { + float4& operator *= (const float4& f) { x *= f.x; y *= f.y; z *= f.z; w *= f.w; return *this; } #if 0 - inline float4 operator + (const float3& f) const { return float4(x + f.x, y + f.y, z + f.z, w); } - inline float4 operator - (const float3& f) const { return float4(x - f.x, y - f.y, z - f.z, w); } + float4 operator + (const float3& f) const { return float4(x + f.x, y + f.y, z + f.z, w); } + float4 operator - (const float3& f) const { return float4(x - f.x, y - f.y, z - f.z, w); } inline float4& operator += (const float3& f) { x += f.x; @@ -79,23 +80,26 @@ struct float4 : public float3 #endif // (in)equality tests between float4 and float3 ignore the w-component - inline bool operator == (const float3& f) const { return (this->float3::operator == (f)); } - inline bool operator != (const float3& f) const { return (this->float3::operator != (f)); } + bool operator == (const float3& f) const { return (this->float3::operator == (f)); } + bool operator != (const float3& f) const { return (this->float3::operator != (f)); } bool operator == (const float4& f) const; + bool operator != (const float4& f) const { return !(*this == f); } - inline bool operator != (const float4& f) const { - return !(*this == f); + float4& fromFloat3(const float f[3]) { + x = f[0]; + y = f[1]; + z = f[2]; + return *this; } - - inline float dot4(const float4& f) const { + float dot4(const float4& f) const { return (x * f.x) + (y * f.y) + (z * f.z) + (w * f.w); } /// Allows implicit conversion to float* (for passing to gl functions) operator const float* () const { return reinterpret_cast(&x); } - operator float* () { return reinterpret_cast(&x); } + operator float* () { return reinterpret_cast< float*>(&x); } }; #endif /* FLOAT4_H */