Add simulated npc hamster finish times. Fix some sound effects, remove double drawing. Fix BGM setting not working right.

sigonasr2 3 months ago
parent a618782ca6
commit d92e0b86ae
  1. 2
      assets/PBData
  2. BIN
      assets/highlight_trackselectbutton.png
  3. BIN
      assets/sounds/jet_land.wav
  4. BIN
      assets/trackselectbutton.png
  5. 1
      src/Checkpoint.cpp
  6. 14
      src/Hamster.cpp
  7. 3
      src/Hamster.h
  8. 2
      src/HamsterAI.cpp
  9. 8
      src/HamsterGame.cpp
  10. 7
      src/HamsterGame.h
  11. 1
      src/HamsterJet.cpp
  12. 60
      src/Menu.cpp
  13. 5
      src/Menu.h
  14. 4
      src/olcPGEX_MiniAudio.h
  15. 3
      src/olcPixelGameEngine.h
  16. 1
      src/util.cpp

@ -1 +1 @@
42976 64212 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 0.8 0.6 OneLoneHam Black
41481 54006 53138 73057 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 2147483647 1 0.6 OneLoneHam Black

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.2 KiB

Binary file not shown.

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.0 KiB

@ -109,5 +109,4 @@ const vf2d&Checkpoint::GetPos()const{
void Checkpoint::OnCheckpointCollect(){
collectedByPlayerTimer=2.f;
animation.ChangeState(internal_animState,AnimationState::CHECKPOINT_CYCLING);
if(Hamster::GetPlayer().CollectedAllCheckpoints())HamsterGame::Game().OnPlayerFinishedRace();
}

@ -551,8 +551,10 @@ void Hamster::HandleCollision(){
if(IsPlayerControlled)HamsterAI::OnCheckpointCollected(this->pos);
if(IsPlayerControlled)checkpoint.OnCheckpointCollect();
if(CollectedAllCheckpoints()){
finishedRaceTime=HamsterGame::Game().GetRaceTime();
if(IsPlayerControlled||!GetPlayer().CollectedAllCheckpoints())finishedRaceTime=HamsterGame::Game().GetRaceTime();
else if(!IsPlayerControlled){finishedRaceTime=GetPlayer().GetFinishedTime()+HamsterGame::Game().GetPlayerDifferentialTime();}
if(IsPlayerControlled)HamsterGame::PlaySFX("winneris.ogg");
if(IsPlayerControlled)HamsterGame::Game().OnPlayerFinishedRace();
}else HamsterGame::PlaySFX(pos,"checkpoint_collection.wav");
lastObtainedCheckpointPos=checkpoint.GetPos();
}
@ -739,7 +741,7 @@ void Hamster::SetPos(const vf2d pos){
movedY=true;
}
Terrain::TerrainType terrainAtPos{HamsterGame::Game().GetTerrainTypeAtPos(this->pos)};
if(distanceTravelled-lastFootstep>32.f){
if(state!=FLYING&&distanceTravelled-lastFootstep>32.f){
lastFootstep=distanceTravelled;
if(terrainAtPos==Terrain::ROCK)HamsterGame::PlaySFX(pos,"footsteps_rock.wav");
else if(terrainAtPos==Terrain::SAND||terrainAtPos==Terrain::SWAMP||terrainAtPos==Terrain::FOREST)HamsterGame::PlaySFX(pos,"sfx_movement_footsteps1b.wav");
@ -1040,4 +1042,12 @@ const size_t Hamster::GetCheckpointsCollectedCount()const{
const std::optional<vf2d>Hamster::GetLastCollectedCheckpoint()const{
return lastObtainedCheckpointPos;
}
const int Hamster::GetFinishedTime()const{
return finishedRaceTime.value_or(std::numeric_limits<int>::max());
}
const std::string&Hamster::GetHamsterImage()const{
return colorFilename;
}

@ -101,7 +101,6 @@ class Hamster{
float burnTimer{};
float imgScale{1.f};
Pixel shrinkEffectColor{BLACK};
std::string img;
Animate2D::Animation<AnimationState::AnimationState>animations;
Animate2D::AnimationState internalAnimState;
static std::optional<Hamster*>playerHamster;
@ -193,4 +192,6 @@ public:
const size_t GetCheckpointsCollectedCount()const;
const std::optional<vf2d>GetLastCollectedCheckpoint()const;
PlayerControlled IsPlayerControlled;
const int GetFinishedTime()const;
const std::string&GetHamsterImage()const;
};

@ -133,7 +133,7 @@ void HamsterAI::OnJetBeginLanding(const vi2d pos){
const HamsterAI::ActionOptRef HamsterAI::GetPreviousAction(){
if(actionInd-1>0)return actionsToPerform[actionInd-1];
if(actionInd-1>0&&actionInd-1<actionsToPerform.size())return actionsToPerform[actionInd-1];
if(actionsToPerform.size()>0)return actionsToPerform[actionsToPerform.size()-1];
return {};
}

@ -163,6 +163,8 @@ void HamsterGame::LoadGraphics(){
_LoadImage("highlight_button4.png");
_LoadImage("smallbutton.png");
_LoadImage("smallhighlight_button.png");
_LoadImage("trackselectbutton.png");
_LoadImage("highlight_trackselectbutton.png");
}
void HamsterGame::LoadAnimations(){
@ -613,6 +615,7 @@ void HamsterGame::OnPlayerFinishedRace(){
std::cout<<"Finish Time: "<<result.first<<std::endl;
audio.Stop(HamsterGame::Game().bgm.at(HamsterGame::Game().currentMap.value().GetData().GetBGM()));
if(result.second)HamsterGame::SavePB(GetCurrentMapName(),result.first);
menu.Transition(Menu::TransitionType::SIMPLE,Menu::GAMEPLAY_RESULTS,3.f);
}
void HamsterGame::SaveOptions(){
@ -786,11 +789,16 @@ void HamsterGame::PlaySFX(const std::string&filename){
PlaySFX(Game().camera.GetPosition(),filename);
}
void HamsterGame::PlaySFX(vf2d pos,const std::string&filename){
if(pos!=Game().camera.GetPosition()&&Hamster::GetPlayer().CollectedAllCheckpoints())return;
float distanceFromCamera{geom2d::line<float>(self->camera.GetPosition(),pos).length()};
float Xdiff{pos.x-self->camera.GetPosition().x}; //If it's positive the sound is to our right...
self->audio.Play("assets/sounds/"+filename,std::clamp(1-distanceFromCamera/250.f,0.f,1.f)*self->sfxVol,std::clamp(Xdiff/250.f,-1.f,1.f),util::random_range(0.9f,1.1f));
}
const float HamsterGame::GetPlayerDifferentialTime()const{
return playerDifferentialTime;
}
int main()
{
HamsterGame game("Project Hamster");

@ -129,6 +129,7 @@ public:
std::string hamsterColor{hamsterColorNames[0]};
static void PlaySFX(const std::string&filename);
static void PlaySFX(vf2d pos,const std::string&filename);
const float GetPlayerDifferentialTime()const;
private:
void UpdateGame(const float fElapsedTime);
void DrawGame();
@ -168,6 +169,11 @@ private:
GameMode mode{GameMode::SINGLE_RACE};
HamsterNet net;
float countdownTimer{};
using Points=int;
using HamsterInd=size_t;
using FinishTime=int;
std::vector<std::pair<Points,HamsterInd>>grandPrixPoints;
std::vector<std::pair<FinishTime,HamsterInd>>racerList;
#ifndef __EMSCRIPTEN__
#ifndef __DEBUG__
SplashScreen splash;
@ -210,4 +216,5 @@ private:
float bgmVol{0.7f};
float sfxVol{0.7f};
int lastDigitPlayedSound{};
float playerDifferentialTime{};
};

@ -126,7 +126,6 @@ void HamsterJet::Update(const float fElapsedTime){
case COMPLETE_LANDING:{
z=util::lerp(3.f,0.f,std::pow(timer/3.f,2));
if(timer<=0.f){
HamsterGame::PlaySFX(pos,"jet_land.wav");
hamster.hamsterJet.reset();
return;
}else{

@ -195,6 +195,7 @@ std::vector<Menu::Button>Menu::GetMenuButtons(const MenuType type){
case OPTIONS:{
buttons.emplace_back(HamsterGame::SCREEN_FRAME.size/2+vf2d{0.f,-32.f},std::format("BGM: {}",int(round(HamsterGame::Game().bgmVol*100))),"button2.png","highlight_button2.png",Pixel{114,109,163},Pixel{79,81,128},[this](Button&self){
HamsterGame::Game().bgmVol=((int(round(HamsterGame::Game().bgmVol*100))+10)%110)/100.f;
HamsterGame::Game().audio.SetVolume(HamsterGame::Game().bgm["Trevor Lentz - Guinea Pig Hero.ogg"],HamsterGame::Game().bgmVol);
self.buttonText=std::format("BGM: {}",int(round(HamsterGame::Game().bgmVol*100)));
HamsterGame::Game().emscripten_temp_val=std::to_string(HamsterGame::Game().bgmVol);
#ifdef __EMSCRIPTEN__
@ -252,6 +253,37 @@ std::vector<Menu::Button>Menu::GetMenuButtons(const MenuType type){
});
buttons.emplace_back(vf2d{54.f,HamsterGame::SCREEN_FRAME.size.y-24.f},"< Back","button2.png","highlight_button2.png",Pixel{114,109,163},Pixel{79,81,128},[this](Button&self){Transition(SHIFT_LEFT,MAIN_MENU,0.5f);});
}break;
case GAMEPLAY_RESULTS:{
switch(HamsterGame::Game().GetGameMode()){
case HamsterGame::GameMode::SINGLE_RACE:{
int MAX_SIMULATION_COUNT{10000};
HamsterGame::Game().playerDifferentialTime=0.f;
while(MAX_SIMULATION_COUNT>0){
bool allHamstersFinished{true};
for(Hamster&hamster:Hamster::GetHamsters()){
if(!hamster.CollectedAllCheckpoints())allHamstersFinished=false;
}
if(allHamstersFinished)break;
HamsterGame::Game().SetElapsedTime(1/30.f);
HamsterGame::Game().UpdateGame(1/30.f);
HamsterGame::Game().playerDifferentialTime+=33;
MAX_SIMULATION_COUNT--;
}
HamsterGame::Game().racerList.clear();
for(size_t ind{0};Hamster&hamster:Hamster::GetHamsters()){
HamsterGame::Game().racerList.emplace_back(std::pair<HamsterGame::FinishTime,HamsterGame::HamsterInd>{hamster.GetFinishedTime(),ind});
ind++;
}
std::sort(HamsterGame::Game().racerList.begin(),HamsterGame::Game().racerList.end(),[](const std::pair<HamsterGame::FinishTime,HamsterGame::HamsterInd>&hamster1,const std::pair<HamsterGame::FinishTime,HamsterGame::HamsterInd>&hamster2){return hamster1.first<hamster2.first;});
buttons.emplace_back(HamsterGame::SCREEN_FRAME.size/2+vf2d{0.f,HamsterGame::SCREEN_FRAME.size.y/2-40.f},"Track Select","trackselectbutton.png","highlight_trackselectbutton.png",Pixel{165,208,96},Pixel{37,134,139},[this](Button&self){Transition(FADE_OUT,SINGLE_RACE,1.f);});
buttons.emplace_back(HamsterGame::SCREEN_FRAME.size/2+vf2d{0.f,HamsterGame::SCREEN_FRAME.size.y/2-16.f},"Retry","button.png","highlight_button.png",Pixel{165,208,96},Pixel{37,134,139},[this](Button&self){Transition(FADE_OUT,LOADING,1.f);});
}break;
default:{
//Show the points.
}
}
}break;
}
return buttons;
}
@ -260,10 +292,8 @@ void Menu::OnMenuTransition(){
menuButtons.clear();
newMenuButtons.clear();
menuButtons=GetMenuButtons(currentMenu);
if(currentMenu!=GAMEPLAY&&currentMenu!=GAMEPLAY_RESULTS&&currentMenu!=AFTER_RACE_MENU)HamsterGame::Game().audio.Play(HamsterGame::Game().bgm["Trevor Lentz - Guinea Pig Hero.ogg"]);
switch(currentMenu){
case TITLE_SCREEN:{
HamsterGame::Game().audio.Play(HamsterGame::Game().bgm["Trevor Lentz - Guinea Pig Hero.ogg"]);
}break;
case LOADING:{
colorNumb=util::random()%8+1;
loading=true;
@ -277,6 +307,7 @@ void Menu::OnMenuTransition(){
if(menuButtons.size()>0)selectedButton=0;
}
void Menu::DrawTransition(HamsterGame&game){
if(currentTransition==SIMPLE)return;
if(currentTransition==FADE_OUT){
if(menuTimer>=originalMenuTimer/2){//Fading out from old scene.
game.SetDrawTarget(1U);
@ -349,7 +380,6 @@ void Menu::Draw(HamsterGame&game,const MenuType menu,const vi2d pos){
}break;
case MAIN_MENU:{
game.DrawPartialDecal(vi2d{pos},game.SCREEN_FRAME.size,game.GetGFX("background1.png").Decal(),vf2d{}+int(game.GetRuntime()*4),game.SCREEN_FRAME.size);
game.DrawRotatedDecal(pos,game.GetGFX("button.png").Decal(),0.f,game.GetGFX("button.png").Sprite()->Size()/2);
DrawButtons(pos);
game.border.Draw();
}break;
@ -398,6 +428,21 @@ void Menu::Draw(HamsterGame&game,const MenuType menu,const vi2d pos){
}
}
}break;
case GAMEPLAY_RESULTS:{
for(size_t ind{0};const auto&[finishTime,hamsterInd]:HamsterGame::Game().racerList){
const Hamster&hamster{Hamster::GetHamsters()[hamsterInd]};
game.DrawShadowStringDecal(vf2d{game.SCREEN_FRAME.pos.x+game.SCREEN_FRAME.size.x/2-64.f,game.SCREEN_FRAME.pos.y+game.SCREEN_FRAME.size.y/2-100.f+ind*16},std::format("{}.",ind+1));
game.DrawPartialRotatedDecal(vf2d{game.SCREEN_FRAME.pos.x+game.SCREEN_FRAME.size.x/2-64.f+24.f,game.SCREEN_FRAME.pos.y+game.SCREEN_FRAME.size.y/2-100.f+ind*16+6.f},game.GetGFX(hamster.GetHamsterImage()).Decal(),0.f,{8.f,6.f},{64.f,64.f},{16.f,12.f});
std::string timeStr{util::timerStr(finishTime)};
vf2d timeStrSize{game.GetTextSize(timeStr)};
game.DrawShadowStringDecal(vf2d{game.SCREEN_FRAME.pos.x+game.SCREEN_FRAME.size.x/2+64.f-timeStrSize.x,game.SCREEN_FRAME.pos.y+game.SCREEN_FRAME.size.y/2-100.f+ind*16},timeStr);
ind++;
}
DrawButtons(pos);
}break;
case AFTER_RACE_MENU:{
DrawButtons(pos);
}break;
case OPTIONS:{
game.DrawPartialDecal(vi2d{pos},game.SCREEN_FRAME.size,game.GetGFX("background2.png").Decal(),vf2d{}+int(game.GetRuntime()*4),game.SCREEN_FRAME.size);
DrawButtons(pos);
@ -406,12 +451,6 @@ void Menu::Draw(HamsterGame&game,const MenuType menu,const vi2d pos){
case QUIT:{
game.DrawPartialDecal(vi2d{pos},game.SCREEN_FRAME.size,game.GetGFX("background3.png").Decal(),vf2d{}+int(game.GetRuntime()*4),game.SCREEN_FRAME.size);
}break;
case GAMEPLAY:{
game.DrawGame();
}break;
case GAMEPLAY_RESULTS:{
game.DrawGame();
}break;
case LOADING:{
game.DrawPartialDecal(vi2d{pos},game.SCREEN_FRAME.size,game.GetGFX("background3.png").Decal(),vf2d{}+int(game.GetRuntime()*4),game.SCREEN_FRAME.size);
game.FillRectDecal(pos+vf2d{32.f,game.SCREEN_FRAME.size.y-64.f}+vf2d{2.f,2.f},vf2d{loadingPct*(game.SCREEN_FRAME.size.x-64),32.f},BLACK);
@ -434,6 +473,7 @@ void Menu::OnLevelLoaded(){
Checkpoint::Initialize(HamsterGame::Game().checkpointsTemp);
HamsterGame::Game().audio.SetVolume(HamsterGame::Game().bgm.at(HamsterGame::Game().currentMap.value().GetData().GetBGM()),HamsterGame::Game().bgmVol);
HamsterGame::Game().audio.Stop(HamsterGame::Game().bgm["Trevor Lentz - Guinea Pig Hero.ogg"]);
HamsterGame::Game().audio.Play(HamsterGame::Game().bgm.at(HamsterGame::Game().currentMap.value().GetData().GetBGM()),true);
HamsterGame::Game().net.SetName(HamsterGame::Game().playerName);
HamsterGame::Game().net.SetColor(HamsterGame::Game().hamsterColor);

@ -57,6 +57,7 @@ class Menu{
void OnClick();
void Draw(HamsterGame&game,const vf2d&pos,std::optional<std::reference_wrapper<Button>>selectedButton={})const;
};
public:
enum MenuType{
INITIALIZE,
TITLE_SCREEN,
@ -77,11 +78,13 @@ class Menu{
SHIFT_UP,
SHIFT_DOWN,
FADE_OUT,
SIMPLE,
};
enum MenuState{
NORMAL,
TRANSITIONING,
};
private:
MenuState currentState{NORMAL};
TransitionType currentTransition{FADE_OUT};
MenuType currentMenu{INITIALIZE};
@ -100,7 +103,6 @@ class Menu{
std::string selectedMap{"StageI.tmx"};
std::optional<int>selectedButton;
int lastHovered{};
void Transition(const TransitionType type,const MenuType gotoMenu,const float transitionTime);
void Draw(HamsterGame&game,const MenuType menu,const vi2d pos);
void DrawTransition(HamsterGame&game);
void OnMenuTransition();
@ -112,4 +114,5 @@ public:
void OnLevelLoaded();
void UpdateLoadingProgress(const float pctLoaded);
void OnTextEntryComplete(const std::string&text);
void Transition(const TransitionType type,const MenuType gotoMenu,const float transitionTime);
};

@ -328,7 +328,7 @@ namespace olc
{
if(ma_sound_is_playing(vecSounds.at(id)))
{
ma_sound_seek_to_pcm_frame(vecSounds.at(id), 0);
//ma_sound_seek_to_pcm_frame(vecSounds.at(id), 0);
return;
}
@ -355,7 +355,7 @@ namespace olc
void MiniAudio::Stop(const int id)
{
ma_sound_seek_to_pcm_frame(vecSounds.at(id), 0);
ma_sound_stop_with_fade_in_milliseconds(vecSounds.at(id),300);
ma_sound_stop(vecSounds.at(id));
}
void MiniAudio::Pause(const int id)

@ -1037,6 +1037,7 @@ namespace olc
uint32_t GetFPS() const;
// Gets last update of elapsed time
float GetElapsedTime() const;
void SetElapsedTime(const float fElapsedTime);
// Gets Actual Window size
const olc::vi2d& GetWindowSize() const;
// Gets pixel scale
@ -2154,6 +2155,8 @@ namespace olc
float PixelGameEngine::GetElapsedTime() const
{ return fLastElapsed; }
void PixelGameEngine::SetElapsedTime(const float fElapsedTime)
{ fLastElapsed=fElapsedTime; }
const olc::vi2d& PixelGameEngine::GetWindowSize() const
{ return vWindowSize; }

@ -57,6 +57,7 @@ vf2d olc::util::pointTo(vf2d posFrom,vf2d posTo){
return geom2d::line(posFrom,posTo).vector().norm();
}
std::string olc::util::timerStr(int ms){
if(ms==std::numeric_limits<int>::max())return "DNF";
int millis=ms%1000;
int seconds=ms/1000;
int hours=seconds/3600;

Loading…
Cancel
Save