3 #include "HeroStatus.h"
6 #include "../app/Application.h"
7 #include "../app/Input.h"
8 #include "../common/GameConfig.h"
9 #include "../common/GameState.h"
10 #include "../common/Hero.h"
11 #include "../common/Spell.h"
12 #include "../graphics/Font.h"
13 #include "../graphics/Frame.h"
14 #include "../math/Vector.h"
25 using graphics::Frame;
30 SpellMenu::SpellMenu(PartyMenu *parent, int cursor)
34 , actionMenu(*parent->Res().itemMenuProperties)
35 , spellMenu(*parent->Res().spellMenuProperties) {
36 actionMenu.Add(parent->Res().itemMenuUseText, CHOICE_USE);
37 actionMenu.Add(parent->Res().itemMenuSortText, CHOICE_SORT);
41 void SpellMenu::OnEnterState(SDL_Surface *) {
42 const HeroStatus &status(parent->GetHeroStatus(0));
43 highlight = SDL_CreateRGBSurface(0, status.Width(), status.Height(), 32, 0xFF000000, 0xFF0000, 0xFF00, 0);
44 SDL_FillRect(highlight, 0, SDL_MapRGB(highlight->format, 0xFF, 0xFF, 0xFF));
45 SDL_SetAlpha(highlight, SDL_SRCALPHA|SDL_RLEACCEL, 0x20);
47 actionMenu.SetSelected();
48 actionMenu.StartAnimation(Ctrl());
50 spellMenu.StartAnimation(Ctrl());
53 void SpellMenu::LoadSpells() {
55 // TODO: set to max spells once implementation is changed
56 spellMenu.Reserve(GetHero().Spells().size());
57 for (vector<const Spell *>::const_iterator
58 i = GetHero().Spells().begin(), end = GetHero().Spells().end();
60 const Spell *spell = *i;
61 spellMenu.Add(spell->Name(), spell, spell->CanUseOnStatusScreen(), 0, spell->Cost());
65 const Hero &SpellMenu::GetHero() const {
66 return *parent->Game().state->party[cursor];
69 Hero &SpellMenu::GetHero() {
70 return *parent->Game().state->party[cursor];
73 void SpellMenu::OnExitState(SDL_Surface *) {
74 SDL_FreeSurface(highlight);
77 void SpellMenu::OnResumeState(SDL_Surface *) {
81 void SpellMenu::OnPauseState(SDL_Surface *) {
86 void SpellMenu::OnResize(int width, int height) {
91 void SpellMenu::HandleEvents(const Input &input) {
92 if (actionMenu.IsActive()) {
93 if (input.JustPressed(Input::PAD_LEFT)) {
94 actionMenu.PreviousItem();
96 if (input.JustPressed(Input::PAD_RIGHT)) {
97 actionMenu.NextItem();
100 if (input.JustPressed(Input::PAD_UP)) {
101 spellMenu.PreviousRow();
103 if (input.JustPressed(Input::PAD_RIGHT)) {
104 spellMenu.NextItem();
106 if (input.JustPressed(Input::PAD_DOWN)) {
109 if (input.JustPressed(Input::PAD_LEFT)) {
110 spellMenu.PreviousItem();
114 if (input.JustPressed(Input::ACTION_A)) {
115 if (actionMenu.IsActive()) {
116 if (actionMenu.Selected() == CHOICE_SORT) {
117 std::sort(GetHero().Spells().begin(),
118 GetHero().Spells().end(),
122 actionMenu.SetSelected();
123 spellMenu.SetActive();
125 } else if (spellMenu.IsActive()) {
126 spellMenu.SetDualSelection();
127 } else if (spellMenu.SelectedIndex() == spellMenu.SecondaryIndex()) {
128 if (spellMenu.Selected()->CanUseOnStatusScreen()) {
132 std::swap(GetHero().Spells().at(spellMenu.SelectedIndex()),
133 GetHero().Spells().at(spellMenu.SecondaryIndex()));
134 spellMenu.SwapSelected();
135 spellMenu.SetActive();
139 if (input.JustPressed(Input::ACTION_B)) {
140 if (actionMenu.IsActive()) {
142 } else if (spellMenu.IsActive()) {
143 actionMenu.SetActive();
144 spellMenu.SetInactive();
146 spellMenu.SetActive();
151 void SpellMenu::UpdateWorld(Uint32 deltaT) {
155 void SpellMenu::Render(SDL_Surface *screen) {
156 const Font &font(*parent->Res().normalFont);
157 Vector<int> offset((screen->w - Width()) / 2, (screen->h - Height()) / 2);
158 Vector<int> menuOffset(font.CharWidth(), 13 * font.CharHeight() + font.CharHeight() / 8);
159 Vector<int> spellsOffset(font.CharWidth(), 16 * font.CharHeight() + font.CharHeight() / 8);
161 parent->RenderBackground(screen);
162 RenderHighlight(screen, offset);
163 parent->RenderHeros(screen, offset);
164 RenderMenu(screen, menuOffset + offset);
165 RenderSpells(screen, spellsOffset + offset);
168 int SpellMenu::Width() const {
169 return parent->Width();
172 int SpellMenu::Height() const {
173 return parent->Height();
176 void SpellMenu::RenderHighlight(SDL_Surface *screen, const Vector<int> &offset) const {
177 if (cursor < 0) return;
178 Vector<int> statusOffset(parent->StatusOffset(cursor));
179 statusOffset -= Vector<int>(0, parent->Res().normalFont->CharHeight() / 8);
181 rect.x = statusOffset.X();
182 rect.y = statusOffset.Y();
183 SDL_BlitSurface(highlight, 0, screen, &rect);
186 void SpellMenu::RenderMenu(SDL_Surface *screen, const Vector<int> &offset) const {
187 const Font &font(*parent->Res().normalFont);
188 const Frame &frame(*parent->Res().statusFrame);
190 const Vector<int> labelOffset(2 * font.CharWidth(), font.CharHeight());
191 const Vector<int> menuFrameOffset(offset.X() + 9 * font.CharWidth(), offset.Y());
192 const Vector<int> menuOffset(menuFrameOffset.X() + 3 * font.CharWidth(), menuFrameOffset.Y() + font.CharHeight());
194 frame.Draw(screen, offset, 9 * font.CharWidth(), 3 * font.CharHeight());
195 font.DrawString(parent->Res().mainMenuSpellText, screen, labelOffset + offset);
196 frame.Draw(screen, menuFrameOffset, 21 * font.CharWidth(), 3 * font.CharHeight());
197 actionMenu.Draw(screen, menuOffset);
200 void SpellMenu::RenderSpells(SDL_Surface *screen, const Vector<int> &offset) const {
201 const Font &font(*parent->Res().normalFont);
202 const Frame &frame(*parent->Res().statusFrame);
203 const Vector<int> menuOffset(3 * font.CharWidth(), font.CharHeight() + font.CharHeight() / 4);
205 frame.Draw(screen, offset, 30 * font.CharWidth(), 11 * font.CharHeight());
206 spellMenu.Draw(screen, offset + menuOffset);