This commit is contained in:
Thomas 2022-01-06 17:12:02 +01:00
parent 174f7240a4
commit bdbcd4eec2
No known key found for this signature in database
GPG Key ID: E538821A6CDFDAD7
7 changed files with 73 additions and 49 deletions

View File

@ -37,12 +37,12 @@ private:
unsigned fireCooldown=120;
// basic methods
void updateColumns();
bool updateColumns();
void handleScoreSaving();
Position invIndexToPos(unsigned x, unsigned y) const;
// drawing methods
void display(unsigned fps) const;
void displayAll(unsigned fps) const;
void displayGod() const;
void displayInvader(const Position& basePos, InvaderType type) const;
@ -62,7 +62,7 @@ private:
// god things
void awakeGod();
void manageGod();
bool manageGod();
public:
// in case someone wants to mess with the code, here's a minimal API, costs nothing to us

View File

@ -30,11 +30,8 @@ public:
* (We could copy them every time, but I feel like copying image data every frame isn't great)
*/
nsGui::Sprite background{"assets/bg.si2"};
nsGui::Sprite rightHandOpen{"assets/hand_open.si2"};
nsGui::Sprite rightHandClosed{"assets/hand_closed.si2"};
nsGui::Sprite leftHandOpen{MIRROR(rightHandOpen)};
nsGui::Sprite leftHandClosed{MIRROR(rightHandClosed)};
nsGui::Sprite rightHand{"assets/hand_open.si2"};
nsGui::Sprite leftHand{MIRROR(rightHand)};
explicit PixelManager(MinGL&);
@ -47,7 +44,8 @@ public:
void drawTorpedo(const Position& baseVector, unsigned width, const nsGraphics::RGBAcolor& color) const;
void drawSprite(const nsGui::Sprite& sprite, const Position& pos) const;
void displayButton(const Position& baseVector,const string& text,nsGraphics::RGBAcolor& color);
void displayText(const Position& pos, const string& text,const nsGraphics::RGBAcolor& color = nsGraphics::KWhite) const;
// TODO remove because unused ?
void displayText(const Position& pos, const string& text, const nsGraphics::RGBAcolor& color = nsGraphics::KWhite) const;
void displayMenu(const Position& pos, Menu& currentMenu);
void drawBackground() const;
@ -65,8 +63,9 @@ public:
// y will be negative sometimes, so not unsigned
void drawGodBench(int y) const;
void drawGodRightHand(const Position& pos, bool closed= false) const;
void drawGodLeftHand(const Position& pos, bool closed= false) const;
void drawGodRightHand(const Position& pos) const;
void drawGodLeftHand(const Position& pos) const;
void drawGodFace(int y) const;
private:
// Explanation for choices :

View File

@ -1,9 +1,11 @@
#include <playMode.h>
#include "pixelManager.h"
#include "mingl/gui/text.h"
#include "utils.h"
#include "god.h"
using namespace nsShape;
using namespace nsGui;
PixelManager::PixelManager(MinGL& a) : window(a) {
@ -62,9 +64,9 @@ void PixelManager::drawTorpedo(const Position& baseVector, unsigned width, const
window << Rectangle(baseVector, baseVector + Position(width, width * PROJ_LENGTH_FACTOR), color);
}
void PixelManager::drawSprite(const nsGui::Sprite& sprite, const Position& pos) const {
void PixelManager::drawSprite(const Sprite& sprite, const Position& pos) const {
// see pixelManager.h for the explanation of this hack
const_cast<nsGui::Sprite&>(sprite).setPosition(pos);
const_cast<Sprite&>(sprite).setPosition(pos);
sprite.draw(window);
}
@ -92,30 +94,37 @@ void PixelManager::drawGodBench(int y) const {
window << Rectangle(Position(0, y), Position(getScreenWidth(), y+GOD_BENCH_SIZE), nsGraphics::KGray);
}
void PixelManager::drawGodRightHand(const Position& pos, bool closed) const {
if(closed){
drawSprite(rightHandClosed, pos);
}else{
drawSprite(rightHandOpen, pos);
}
void PixelManager::drawGodRightHand(const Position& pos) const {
drawSprite(rightHand, pos);
}
void PixelManager::drawGodLeftHand(const Position& pos, bool closed) const {
if(closed){
drawSprite(leftHandClosed, pos);
}else{
drawSprite(leftHandOpen, pos);
}
void PixelManager::drawGodLeftHand(const Position& pos) const {
drawSprite(leftHand, pos);
}
void PixelManager::drawGodFace(int y) const {
Text t(
Position(getScreenWidth()/2, y),
".w.", nsGraphics::KBlue,
GlutFont::GlutFonts::BITMAP_TIMES_ROMAN_24,
Text::HorizontalAlignment::ALIGNH_CENTER
);
// computeHeight() returns a height bigger than the actual text size, that's why there's padding above it(
t.setPosition(t.getPosition()+Position(0, t.computeHeight()));
window << t;
}
void PixelManager::displayText(const Position& pos, const string& text,const nsGraphics::RGBAcolor& color) const {
window << nsGui::Text(pos, text, color);
window << Text(pos, text, color);
}
void PixelManager::drawFPS(unsigned fps) const {
window << nsGui::Text(Position(getScreenWidth()-100, 10), "FPS : "+ to_string(fps), nsGraphics::KWhite);
window << Text(Position(getScreenWidth()-100, 10), "FPS : "+ to_string(fps), nsGraphics::KWhite);
}
vector<RGBAcolor>
PixelManager::mirrorData(const vector<nsGraphics::RGBAcolor>& inPixels, unsigned rowSize) {
vector<RGBAcolor> outPixels;

View File

@ -4,7 +4,7 @@
/** Displays the screen once, and returns
* The more important stuff must be drawn last
*/
void Game::display(unsigned fps) const {
void Game::displayAll(unsigned fps) const {
pm.drawBackground();
for (unsigned i = 0; i < this->grid.size(); ++i){
for (unsigned j = 0; j < this->grid[i].size(); ++j){
@ -69,15 +69,16 @@ void Game::displayGod() const {
Position rightHand(pm.getScreenWidth()-GOD_HAND_DISTANCE-GOD_HAND_SIZE, god.counter-GOD_BENCH_SIZE);
pm.drawGodLeftHand(leftHand);
pm.drawGodRightHand(rightHand);
pm.drawGodFace(god.counter - GOD_BENCH_SIZE);
break;
}
case GodState::WAIT:{
pm.drawGodBench(0);
Position leftHand(GOD_HAND_DISTANCE, 0);
Position rightHand(god.getRightHandPos(pm.getScreenWidth()));
pm.drawGodLeftHand(leftHand);
pm.drawGodRightHand(rightHand);
pm.drawGodFace(0);
break;
}
case GodState::RETRIEVE1:
@ -86,6 +87,7 @@ void Game::displayGod() const {
// counter goes [0-100]
pm.drawGodBench(0);
pm.drawGodLeftHand(Position(GOD_HAND_DISTANCE, 0));
pm.drawGodFace(0);
Position pos(god.getRightHandPos(pm.getScreenWidth()));
Position endPos = invIndexToPos(god.thrownInvPosX, god.thrownInvPosY);
@ -107,6 +109,7 @@ void Game::displayGod() const {
case GodState::THROW:{
pm.drawGodBench(0);
pm.drawGodLeftHand(Position(GOD_HAND_DISTANCE, 0));
pm.drawGodFace(0);
// compute start position (not sure if we should store it or compute it each time ?)
Position handPos = god.getRightHandPos(pm.getScreenWidth());

View File

@ -13,15 +13,23 @@ Game::Game() : WININIT, pm(window) {
sm.readFile();
}
void Game::updateColumns(){
while(grid.at(0).hasNoValid()){
grid.erase(grid.begin());
basePos+=confData.invadersSize+confData.invadersDistance;
/**
*
* @return true if there are no more invaders in the grid
*/
bool Game::updateColumns(){
while(true){
if(grid.empty())return true;
if(grid.at(0).hasNoValid()){
grid.erase(grid.begin());
basePos+=confData.invadersSize+confData.invadersDistance;
}else break;
}
while(grid.at(grid.size() - 1).hasNoValid()){
grid.erase(grid.end()-1);
}
return false;
}
void Game::handleScoreSaving(){
@ -119,7 +127,7 @@ WinValue Game::playGame(){ // returns when game is finished
if(checkMissilesAndPlayers())return WinValue::INVADERS;
if(checkTorpedosAndInvaders())return WinValue::PLAYERS;
display(fps);
displayAll(fps);
pm.endFrame();

View File

@ -33,6 +33,7 @@ void Game::managePlayers(){
* @return true if the invaders went down from one line (and we should check lower boundary), else false
*/
bool Game::manageInvaders(){
if(grid.size()==0)return false; // If there are no more invaders we don't need to manage them
// shoot
if(fireCooldown==0) {
fireCooldown = confData.invadersFireCooldown + rand() % 60;
@ -158,6 +159,7 @@ bool Game::checkTorpedosAndInvaders() {
for(;i<grid.size();++i){
unsigned alienIndex = grid[i].getOutterInvader();
if(alienIndex==grid[i].size())continue;
// calculate top-left Position of invader
Position pos = basePos + Position(
confData.invadersSize*i+confData.invadersDistance*i,
@ -177,7 +179,8 @@ bool Game::checkTorpedosAndInvaders() {
torpedos.erase(tor_ite);
grid[i][alienIndex] = InvaderType::NONE;
updateColumns();
if(updateColumns()) return true;
break;
}
}

View File

@ -5,22 +5,25 @@ void Game::awakeGod() {
god.state = GodState::AWAKE;
}
void Game::manageGod() {
/**
* @returns true if we can finish the game
*/
bool Game::manageGod() {
switch (god.state) {
case GodState::NONE: {
break;
return false;
}
case GodState::AWAKE: {
if (god.counter == GOD_BENCH_SIZE) {
god.counter = 0;
god.state = GodState::WAIT;
} else ++god.counter;
break;
return false;
}
case GodState::WAIT: {
if (god.counter < 100) {
++god.counter;
break;
return false;
}
// init throw
god.counter = 0;
@ -31,12 +34,12 @@ void Game::manageGod() {
god.thrownTransition.setX(pm.getScreenWidth() - GOD_HAND_DISTANCE - GOD_HAND_SIZE);
god.thrownTransition.setY(basePos.getY() + INV_GET_POS(god.thrownInvPosY));
break;
return false;
}
case GodState::RETRIEVE1: {
if (god.counter < 100) {
god.counter += 2;
break;
return false;
}
if (grid.size() > god.thrownInvPosY && grid[god.thrownInvPosX][god.thrownInvPosY] != InvaderType::NONE) {
god.thrownInvType = grid[god.thrownInvPosX][god.thrownInvPosY];
@ -44,16 +47,16 @@ void Game::manageGod() {
updateColumns();
}
god.state = GodState::RETRIEVE2;
break;
return false;
}
case GodState::RETRIEVE2: {
if (god.counter > 0) {
god.counter -= 2;
break;
return false;
}
if(god.thrownInvType==InvaderType::NONE){
god.state = GodState::WAIT;
break;
return false;
}
god.state = GodState::THROW;
@ -72,13 +75,12 @@ void Game::manageGod() {
god.thrownVector = playerMiddlePos - invaderMiddlePos;
god.thrownVector = god.thrownVector / (god.thrownVector.computeMagnitude() / 1000.0);
// let's normalize it, but keep it's length big so x and y and non-zero
// We will divide it in display
break;
// We will divide it in displayAll
return false;
}
case GodState::THROW: {
++god.counter;
Position invaderPos = god.getRightHandPos(pm.getScreenWidth());
applyTransformation(invaderPos, GOD_HAND_SIZE, confData.invadersSize);
Position a = god.thrownVector * (god.counter / 100.0);
@ -92,7 +94,7 @@ void Game::manageGod() {
touched = true;
// check player collision
} else if (invaderPos.getY() + confData.invadersSize >= pm.getScreenHeight() - PLAYER_HEIGHT) {
for (Player &p: players) {
for (Player& p: players) {
if (areLinesColliding(
p.x, p.x + confData.playersWidth,
invaderPos.getX(), invaderPos.getX() + confData.invadersSize
@ -112,7 +114,7 @@ void Game::manageGod() {
* When we cycle back between states
*/
}
break;
return false;
}
}