updated stars in game play grid
This commit is contained in:
@ -23,6 +23,22 @@ void Starfield3D::resize(int w, int h) {
|
|||||||
centerY = height * 0.5f;
|
centerY = height * 0.5f;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Starfield3D::setMagnetTarget(float localX, float localY, float strength) {
|
||||||
|
if (strength <= 0.0f) {
|
||||||
|
clearMagnetTarget();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
magnetActive = true;
|
||||||
|
magnetStrength = strength;
|
||||||
|
magnetX = std::clamp(localX, 0.0f, static_cast<float>(width));
|
||||||
|
magnetY = std::clamp(localY, 0.0f, static_cast<float>(height));
|
||||||
|
}
|
||||||
|
|
||||||
|
void Starfield3D::clearMagnetTarget() {
|
||||||
|
magnetActive = false;
|
||||||
|
magnetStrength = 0.0f;
|
||||||
|
}
|
||||||
|
|
||||||
float Starfield3D::randomFloat(float min, float max) {
|
float Starfield3D::randomFloat(float min, float max) {
|
||||||
std::uniform_real_distribution<float> dist(min, max);
|
std::uniform_real_distribution<float> dist(min, max);
|
||||||
return dist(rng);
|
return dist(rng);
|
||||||
@ -147,13 +163,24 @@ void Starfield3D::drawStar(SDL_Renderer* renderer, float x, float y, SDL_Color c
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Starfield3D::draw(SDL_Renderer* renderer, float offsetX, float offsetY, float alphaScale, bool grayscale) {
|
void Starfield3D::draw(SDL_Renderer* renderer, float offsetX, float offsetY, float alphaScale, bool grayscale) {
|
||||||
|
const bool useMagnet = magnetActive && magnetStrength > 0.0f;
|
||||||
for (const Star3D& star : stars) {
|
for (const Star3D& star : stars) {
|
||||||
// Calculate perspective projection factor
|
// Calculate perspective projection factor
|
||||||
const float k = DEPTH_FACTOR / star.z;
|
const float k = DEPTH_FACTOR / star.z;
|
||||||
|
|
||||||
// Calculate screen position with perspective
|
// Calculate screen position with perspective
|
||||||
const float px = star.x * k + centerX;
|
float px = star.x * k + centerX;
|
||||||
const float py = star.y * k + centerY;
|
float py = star.y * k + centerY;
|
||||||
|
|
||||||
|
if (useMagnet) {
|
||||||
|
float dx = magnetX - px;
|
||||||
|
float dy = magnetY - py;
|
||||||
|
float dist = std::sqrt(dx * dx + dy * dy);
|
||||||
|
float pull = magnetStrength / (magnetStrength + dist + 1.0f);
|
||||||
|
pull = std::clamp(pull, 0.0f, 0.35f);
|
||||||
|
px += dx * pull;
|
||||||
|
py += dy * pull;
|
||||||
|
}
|
||||||
|
|
||||||
// Only draw stars that are within the viewport
|
// Only draw stars that are within the viewport
|
||||||
if (px >= 0.0f && px <= static_cast<float>(width) &&
|
if (px >= 0.0f && px <= static_cast<float>(width) &&
|
||||||
|
|||||||
@ -15,6 +15,8 @@ public:
|
|||||||
void update(float deltaTime);
|
void update(float deltaTime);
|
||||||
void draw(SDL_Renderer* renderer, float offsetX = 0.0f, float offsetY = 0.0f, float alphaScale = 1.0f, bool grayscale = false);
|
void draw(SDL_Renderer* renderer, float offsetX = 0.0f, float offsetY = 0.0f, float alphaScale = 1.0f, bool grayscale = false);
|
||||||
void resize(int width, int height);
|
void resize(int width, int height);
|
||||||
|
void setMagnetTarget(float localX, float localY, float strength);
|
||||||
|
void clearMagnetTarget();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
struct Star3D {
|
struct Star3D {
|
||||||
@ -37,6 +39,10 @@ private:
|
|||||||
std::vector<Star3D> stars;
|
std::vector<Star3D> stars;
|
||||||
int width{0}, height{0};
|
int width{0}, height{0};
|
||||||
float centerX{0}, centerY{0};
|
float centerX{0}, centerY{0};
|
||||||
|
bool magnetActive{false};
|
||||||
|
float magnetX{0.0f};
|
||||||
|
float magnetY{0.0f};
|
||||||
|
float magnetStrength{0.0f};
|
||||||
|
|
||||||
// Random number generator
|
// Random number generator
|
||||||
std::mt19937 rng;
|
std::mt19937 rng;
|
||||||
|
|||||||
@ -265,6 +265,39 @@ void GameRenderer::renderPlayingState(
|
|||||||
const float deltaSeconds = std::clamp(static_cast<float>(sparkDeltaMs) / 1000.0f, 0.0f, 0.033f);
|
const float deltaSeconds = std::clamp(static_cast<float>(sparkDeltaMs) / 1000.0f, 0.0f, 0.033f);
|
||||||
s_inGridStarfield.update(deltaSeconds);
|
s_inGridStarfield.update(deltaSeconds);
|
||||||
|
|
||||||
|
bool appliedMagnet = false;
|
||||||
|
if (game) {
|
||||||
|
const Game::Piece& activePiece = game->current();
|
||||||
|
const int pieceType = static_cast<int>(activePiece.type);
|
||||||
|
if (pieceType >= 0 && pieceType < PIECE_COUNT) {
|
||||||
|
float sumLocalX = 0.0f;
|
||||||
|
float sumLocalY = 0.0f;
|
||||||
|
int filledCells = 0;
|
||||||
|
for (int cy = 0; cy < 4; ++cy) {
|
||||||
|
for (int cx = 0; cx < 4; ++cx) {
|
||||||
|
if (!Game::cellFilled(activePiece, cx, cy)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
sumLocalX += (activePiece.x + cx + 0.5f) * finalBlockSize;
|
||||||
|
sumLocalY += (activePiece.y + cy + 0.5f) * finalBlockSize;
|
||||||
|
++filledCells;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (filledCells > 0) {
|
||||||
|
float magnetLocalX = sumLocalX / static_cast<float>(filledCells);
|
||||||
|
float magnetLocalY = sumLocalY / static_cast<float>(filledCells);
|
||||||
|
magnetLocalX = std::clamp(magnetLocalX, 0.0f, GRID_W);
|
||||||
|
magnetLocalY = std::clamp(magnetLocalY, 0.0f, GRID_H);
|
||||||
|
const float magnetStrength = finalBlockSize * 2.2f;
|
||||||
|
s_inGridStarfield.setMagnetTarget(magnetLocalX, magnetLocalY, magnetStrength);
|
||||||
|
appliedMagnet = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!appliedMagnet) {
|
||||||
|
s_inGridStarfield.clearMagnetTarget();
|
||||||
|
}
|
||||||
|
|
||||||
SDL_BlendMode oldBlend = SDL_BLENDMODE_NONE;
|
SDL_BlendMode oldBlend = SDL_BLENDMODE_NONE;
|
||||||
SDL_GetRenderDrawBlendMode(renderer, &oldBlend);
|
SDL_GetRenderDrawBlendMode(renderer, &oldBlend);
|
||||||
SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_BLEND);
|
SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_BLEND);
|
||||||
|
|||||||
Reference in New Issue
Block a user