From 20d6d71ec97c1f7bc4b95ed6c98375b47dff6646 Mon Sep 17 00:00:00 2001 From: Ľubomír Remák Date: Sun, 8 Jul 2018 17:06:41 +0200 Subject: MUTATIONOFJB: Basic conversation support. --- engines/mutationofjb/assets.cpp | 45 +++++++++++ engines/mutationofjb/assets.h | 53 +++++++++++++ engines/mutationofjb/commands/ifitemcommand.h | 2 +- engines/mutationofjb/commands/talkcommand.cpp | 76 ++++++++++++++++++ engines/mutationofjb/commands/talkcommand.h | 57 ++++++++++++++ engines/mutationofjb/conversationlinelist.cpp | 91 ++++++++++++++++++++++ engines/mutationofjb/conversationlinelist.h | 58 ++++++++++++++ engines/mutationofjb/game.cpp | 20 ++--- engines/mutationofjb/game.h | 15 ++-- engines/mutationofjb/gamedata.h | 3 +- engines/mutationofjb/gui.cpp | 12 ++- engines/mutationofjb/module.mk | 5 ++ engines/mutationofjb/script.cpp | 2 + engines/mutationofjb/tasks/conversationtask.cpp | 83 ++++++++++++++++++++ engines/mutationofjb/tasks/conversationtask.h | 45 +++++++++++ engines/mutationofjb/tasks/task.h | 56 +++++++++++++ engines/mutationofjb/tasks/taskmanager.cpp | 47 +++++++++++ engines/mutationofjb/tasks/taskmanager.h | 51 ++++++++++++ engines/mutationofjb/util.cpp | 22 ++++++ engines/mutationofjb/util.h | 5 ++ .../mutationofjb/widgets/conversationwidget.cpp | 27 ++++++- engines/mutationofjb/widgets/conversationwidget.h | 15 +++- 22 files changed, 765 insertions(+), 25 deletions(-) create mode 100644 engines/mutationofjb/assets.cpp create mode 100644 engines/mutationofjb/assets.h create mode 100644 engines/mutationofjb/commands/talkcommand.cpp create mode 100644 engines/mutationofjb/commands/talkcommand.h create mode 100644 engines/mutationofjb/conversationlinelist.cpp create mode 100644 engines/mutationofjb/conversationlinelist.h create mode 100644 engines/mutationofjb/tasks/conversationtask.cpp create mode 100644 engines/mutationofjb/tasks/conversationtask.h create mode 100644 engines/mutationofjb/tasks/task.h create mode 100644 engines/mutationofjb/tasks/taskmanager.cpp create mode 100644 engines/mutationofjb/tasks/taskmanager.h (limited to 'engines') diff --git a/engines/mutationofjb/assets.cpp b/engines/mutationofjb/assets.cpp new file mode 100644 index 0000000000..d532469e87 --- /dev/null +++ b/engines/mutationofjb/assets.cpp @@ -0,0 +1,45 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "mutationofjb/assets.h" + +namespace MutationOfJB { + +Assets::Assets(Game &game) : _game(game), _toSayList("tosay.ger"), _responseList("response.ger") {} + +Font& Assets::getSystemFont() { + return _systemFont; +} + +Font& Assets::getSpeechFont() { + return _speechFont; +} + +ConversationLineList &Assets::getToSayList() { + return _toSayList; +} + +ConversationLineList &Assets::getResponseList() { + return _responseList; +} + +} diff --git a/engines/mutationofjb/assets.h b/engines/mutationofjb/assets.h new file mode 100644 index 0000000000..1d47641a03 --- /dev/null +++ b/engines/mutationofjb/assets.h @@ -0,0 +1,53 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#ifndef MUTATIONOFJB_ASSETS_H +#define MUTATIONOFJB_ASSETS_H + +#include "mutationofjb/font.h" +#include "mutationofjb/conversationlinelist.h" + +namespace MutationOfJB { + +class Game; + +class Assets { +public: + Assets(Game &game); + + Font& getSystemFont(); + Font& getSpeechFont(); + + ConversationLineList& getToSayList(); + ConversationLineList& getResponseList(); + +private: + Game &_game; + SystemFont _systemFont; + SpeechFont _speechFont; + ConversationLineList _toSayList; + ConversationLineList _responseList; +}; + +} + +#endif diff --git a/engines/mutationofjb/commands/ifitemcommand.h b/engines/mutationofjb/commands/ifitemcommand.h index f11ba7cbfb..df073b9fa4 100644 --- a/engines/mutationofjb/commands/ifitemcommand.h +++ b/engines/mutationofjb/commands/ifitemcommand.h @@ -33,7 +33,7 @@ class ScriptParseContext; class IfItemCommandParser : public ConditionalCommandParser { public: - virtual bool parse(const Common::String &line, ScriptParseContext &parseCtx, Command *&command); + virtual bool parse(const Common::String &line, ScriptParseContext &parseCtx, Command *&command) override; }; class IfItemCommand : public ConditionalCommand { diff --git a/engines/mutationofjb/commands/talkcommand.cpp b/engines/mutationofjb/commands/talkcommand.cpp new file mode 100644 index 0000000000..d0775e481f --- /dev/null +++ b/engines/mutationofjb/commands/talkcommand.cpp @@ -0,0 +1,76 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "mutationofjb/commands/talkcommand.h" +#include "mutationofjb/tasks/conversationtask.h" +#include "mutationofjb/script.h" +#include "mutationofjb/game.h" +#include "common/str.h" + +namespace MutationOfJB { + +bool TalkCommandParser::parse(const Common::String &line, ScriptParseContext &, Command *&command) { + if (line.size() < 11 || !line.hasPrefix("TALK TO HIM")) { + return false; + } + + int modeInt = 0; + + if (line.size() >= 13) { + modeInt = atoi(line.c_str() + 12); + } + + TalkCommand::Mode mode = TalkCommand::NORMAL_MODE; + + if (modeInt == 1) { + mode = TalkCommand::RAY_AND_BUTTLEG_MODE; + } else if (modeInt == 3) { + mode = TalkCommand::CARNIVAL_TICKET_SELLER_MODE; + } + + command = new TalkCommand(mode); + return true; +} + +Command::ExecuteResult TalkCommand::execute(ScriptExecutionContext &scriptExeCtx) { + if (!_task) { + _task = new ConversationTask(scriptExeCtx.getGame().getGameData()._conversationInfo); + scriptExeCtx.getGame().getTaskManager().addTask(_task); + } + + if (_task->getState() == Task::FINISHED) { + scriptExeCtx.getGame().getTaskManager().removeTask(_task); + delete _task; + _task = nullptr; + + return Command::Finished; + } + + return Command::InProgress; +} + +Common::String TalkCommand::debugString() const { + const char * modes[] = {"NORMAL", "RAY_AND_BUTTLEG", "CARNIVAL_TICKET_SELLER"}; + return Common::String::format("TALK %s", modes[(int) _mode]); +} + +} diff --git a/engines/mutationofjb/commands/talkcommand.h b/engines/mutationofjb/commands/talkcommand.h new file mode 100644 index 0000000000..09424b2f06 --- /dev/null +++ b/engines/mutationofjb/commands/talkcommand.h @@ -0,0 +1,57 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#ifndef MUTATIONOFJB_TALKCOMMAND_H +#define MUTATIONOFJB_TALKCOMMAND_H + +#include "mutationofjb/commands/seqcommand.h" +#include "common/scummsys.h" + +namespace MutationOfJB { + +class ConversationTask; + +class TalkCommandParser : public SeqCommandParser { +public: + virtual bool parse(const Common::String &line, ScriptParseContext &parseCtx, Command *&command) override; +}; + +class TalkCommand : public SeqCommand { +public: + enum Mode { + NORMAL_MODE, + RAY_AND_BUTTLEG_MODE, + CARNIVAL_TICKET_SELLER_MODE + }; + + TalkCommand(Mode mode) : _mode(mode), _task(nullptr) {} + virtual ExecuteResult execute(ScriptExecutionContext &scriptExecCtx) override; + virtual Common::String debugString() const; + +private: + Mode _mode; + ConversationTask *_task; +}; + +} + +#endif diff --git a/engines/mutationofjb/conversationlinelist.cpp b/engines/mutationofjb/conversationlinelist.cpp new file mode 100644 index 0000000000..562c2d0e39 --- /dev/null +++ b/engines/mutationofjb/conversationlinelist.cpp @@ -0,0 +1,91 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "mutationofjb/conversationlinelist.h" +#include "mutationofjb/encryptedfile.h" +#include "mutationofjb/util.h" + +namespace MutationOfJB { + +ConversationLineList::ConversationLineList(const Common::String &fileName) { + parseFile(fileName); +} + +const ConversationLineList::Line *ConversationLineList::getLine(uint index) const { + if (index > _lines.size()) { + return nullptr; + } + + return &_lines[index - 1]; +} + +bool ConversationLineList::parseFile(const Common::String &fileName) { + EncryptedFile file; + file.open(fileName); + if (!file.isOpen()) { + reportFileMissingError(fileName.c_str()); + return false; + } + + while (!file.eos()) { + Common::String lineStr = file.readLine(); + if (lineStr.empty()) { + continue; + } + + Line line; + + Common::String::iterator endIt = Common::find(lineStr.begin(), lineStr.end(), '|'); + if (endIt != lineStr.end()) { + Common::String extra = lineStr + endIt; + if (*endIt == 'X') { + line._extra = Common::String(endIt + 1, lineStr.end()); // Skip 'X' char. + } + } + + Common::String::iterator startSpeechIt = lineStr.begin(); + Common::String::iterator endSpeechIt = startSpeechIt; + + while (startSpeechIt < endIt) { + endSpeechIt = Common::find(startSpeechIt, endIt, '\\'); + Common::String::iterator voiceFileIt = Common::find(startSpeechIt, endSpeechIt, '<'); + Speech speech; + + if (voiceFileIt != endSpeechIt) { + if (*voiceFileIt == 'S') { + speech._voiceFile = Common::String(voiceFileIt + 1, endSpeechIt); + } + } + + speech._text = Common::String(startSpeechIt, voiceFileIt); + line._speeches.push_back(speech); + + startSpeechIt = endSpeechIt + 1; + } + + _lines.push_back(line); + } + + return true; +} + +} diff --git a/engines/mutationofjb/conversationlinelist.h b/engines/mutationofjb/conversationlinelist.h new file mode 100644 index 0000000000..9ec446e4b4 --- /dev/null +++ b/engines/mutationofjb/conversationlinelist.h @@ -0,0 +1,58 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#ifndef MUTATIONOFJB_CONVERSATIONLINELIST_H +#define MUTATIONOFJB_CONVERSATIONLINELIST_H + +#include "common/str.h" +#include "common/array.h" + +namespace MutationOfJB { + +class ConversationLineList { +public: + struct Speech { + Common::String _text; + Common::String _voiceFile; + + bool isRepeating() const { return _text.firstChar() == '*'; } + bool isFirstSpeaker() const { return _text.firstChar() == '~'; } + bool isSecondSpeaker() const { return _text.firstChar() == '`'; } + }; + + struct Line { + Common::Array _speeches; + Common::String _extra; + }; + + ConversationLineList(const Common::String &fileName); + const Line *getLine(uint index) const; + +private: + bool parseFile(const Common::String &fileName); + + Common::Array _lines; +}; + +} + +#endif diff --git a/engines/mutationofjb/game.cpp b/engines/mutationofjb/game.cpp index a0f85b49b8..24159254df 100644 --- a/engines/mutationofjb/game.cpp +++ b/engines/mutationofjb/game.cpp @@ -39,7 +39,9 @@ Game::Game(MutationOfJBEngine *vm) _delayedLocalScript(nullptr), _gui(*this, _vm->getScreen()), _scriptExecCtx(*this), - _currentAction(ActionInfo::Walk) { + _currentAction(ActionInfo::Walk), + _taskManager(*this), + _assets(*this) { _gameData = new GameData; loadGameData(false); @@ -192,14 +194,6 @@ void Game::setCurrentAction(ActionInfo::Action action) { _currentAction = action; } -Font& Game::getSystemFont() { - return _systemFont; -} - -Font& Game::getSpeechFont() { - return _speechFont; -} - uint8 Game::colorFromString(const char *colorStr) { struct { const char *str; @@ -225,4 +219,12 @@ uint8 Game::colorFromString(const char *colorStr) { return 0x00; } +TaskManager& Game::getTaskManager() { + return _taskManager; +} + +Assets& Game::getAssets() { + return _assets; +} + } diff --git a/engines/mutationofjb/game.h b/engines/mutationofjb/game.h index 4985a884d7..33527ae441 100644 --- a/engines/mutationofjb/game.h +++ b/engines/mutationofjb/game.h @@ -24,9 +24,10 @@ #define MUTATIONOFJB_GAME_H #include "common/scummsys.h" -#include "mutationofjb/script.h" -#include "mutationofjb/font.h" +#include "mutationofjb/assets.h" #include "mutationofjb/gui.h" +#include "mutationofjb/script.h" +#include "mutationofjb/tasks/taskmanager.h" namespace Common { class String; @@ -65,11 +66,11 @@ public: ActionInfo::Action getCurrentAction() const; void setCurrentAction(ActionInfo::Action); - Font& getSystemFont(); - Font& getSpeechFont(); - static uint8 colorFromString(const char *colorStr); + TaskManager& getTaskManager(); + Assets &getAssets(); + private: bool loadGameData(bool partB); void runActiveCommand(); @@ -88,8 +89,8 @@ private: ScriptExecutionContext _scriptExecCtx; - SystemFont _systemFont; - SpeechFont _speechFont; + TaskManager _taskManager; + Assets _assets; }; } diff --git a/engines/mutationofjb/gamedata.h b/engines/mutationofjb/gamedata.h index 22be9dd273..d1bbc546b3 100644 --- a/engines/mutationofjb/gamedata.h +++ b/engines/mutationofjb/gamedata.h @@ -168,8 +168,9 @@ struct ConversationInfo { uint8 _nextLineIndex; }; + typedef Common::Array Items; struct Line { - Common::Array _items; + Items _items; }; Common::Array _lines; diff --git a/engines/mutationofjb/gui.cpp b/engines/mutationofjb/gui.cpp index 7102407c99..3c8cc66aa8 100644 --- a/engines/mutationofjb/gui.cpp +++ b/engines/mutationofjb/gui.cpp @@ -132,19 +132,25 @@ bool Gui::init() { void Gui::markDirty() { for (Common::Array::iterator it = _widgets.begin(); it != _widgets.end(); ++it) { - (*it)->markDirty(); + if ((*it)->isVisible()) { + (*it)->markDirty(); + } } } void Gui::handleEvent(const Common::Event &event) { for (Common::Array::iterator it = _widgets.begin(); it != _widgets.end(); ++it) { - (*it)->handleEvent(event); + if ((*it)->isVisible()) { + (*it)->handleEvent(event); + } } } void Gui::update() { for (Common::Array::iterator it = _widgets.begin(); it != _widgets.end(); ++it) { - (*it)->update(*_screen); + if ((*it)->isVisible()) { + (*it)->update(*_screen); + } } } diff --git a/engines/mutationofjb/module.mk b/engines/mutationofjb/module.mk index 507ae39402..89da245dd4 100644 --- a/engines/mutationofjb/module.mk +++ b/engines/mutationofjb/module.mk @@ -20,12 +20,17 @@ MODULE_OBJS := \ commands/renamecommand.o \ commands/saycommand.o \ commands/seqcommand.o \ + commands/talkcommand.o \ + tasks/conversationtask.o \ + tasks/taskmanager.o \ widgets/buttonwidget.o \ widgets/conversationwidget.o \ widgets/imagewidget.o \ widgets/inventorywidget.o \ widgets/widget.o \ animationdecoder.o \ + assets.o \ + conversationlinelist.o \ debug.o \ detection.o \ encryptedfile.o \ diff --git a/engines/mutationofjb/script.cpp b/engines/mutationofjb/script.cpp index 321a5ba79d..90146f64c6 100644 --- a/engines/mutationofjb/script.cpp +++ b/engines/mutationofjb/script.cpp @@ -44,6 +44,7 @@ #include "mutationofjb/commands/newroomcommand.h" #include "mutationofjb/commands/renamecommand.h" #include "mutationofjb/commands/definestructcommand.h" +#include "mutationofjb/commands/talkcommand.h" #include "mutationofjb/game.h" namespace MutationOfJB { @@ -62,6 +63,7 @@ static CommandParser **getParsers() { new ChangeSceneCommandParser, new DefineStructCommandParser, new SayCommandParser, + new TalkCommandParser, new AddItemCommandParser, new RemoveItemCommandParser, new RemoveAllItemsCommandParser, diff --git a/engines/mutationofjb/tasks/conversationtask.cpp b/engines/mutationofjb/tasks/conversationtask.cpp new file mode 100644 index 0000000000..75d850465b --- /dev/null +++ b/engines/mutationofjb/tasks/conversationtask.cpp @@ -0,0 +1,83 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "mutationofjb/tasks/conversationtask.h" +#include "mutationofjb/tasks/taskmanager.h" +#include "mutationofjb/assets.h" +#include "mutationofjb/game.h" +#include "mutationofjb/gamedata.h" +#include "mutationofjb/gui.h" +#include "mutationofjb/util.h" +#include "mutationofjb/widgets/conversationwidget.h" + +namespace MutationOfJB { + +void ConversationTask::start() { + Game &game = getTaskManager()->getGame(); + ConversationWidget &widget = game.getGui().getConversationWidget(); + + widget.setCallback(this); + widget.setVisible(true); + + updateWidget(); +} + +void ConversationTask::update() { +} + +void ConversationTask::onResponseClicked(ConversationWidget *, int response) { + + uint8 nextLineIndex = _convInfo._lines[_currentLine]._items[response]._nextLineIndex; + if (nextLineIndex == 0) { + setState(FINISHED); + Game &game = getTaskManager()->getGame(); + ConversationWidget &widget = game.getGui().getConversationWidget(); + widget.setVisible(false); + game.getGui().markDirty(); // TODO: Handle automatically when changing visibility. + return; + } + + _currentLine = nextLineIndex - 1; + updateWidget(); +} + +void ConversationTask::updateWidget() { + Game &game = getTaskManager()->getGame(); + ConversationWidget &widget = game.getGui().getConversationWidget(); + + const ConversationLineList& toSayList = game.getAssets().getToSayList(); + + const ConversationInfo::Line &convLine = _convInfo._lines[_currentLine]; + + for (ConversationInfo::Items::size_type i = 0; i < convLine._items.size(); ++i) { + Common::String widgetText; + const uint8 question = convLine._items[i]._question; + if (question != 0) { + const ConversationLineList::Line *line = toSayList.getLine(convLine._items[i]._question); + widgetText = toUpperCP895(line->_speeches[0]._text); + } + + widget.setLine(i, widgetText); + } +} + +} diff --git a/engines/mutationofjb/tasks/conversationtask.h b/engines/mutationofjb/tasks/conversationtask.h new file mode 100644 index 0000000000..5cc0e5f49f --- /dev/null +++ b/engines/mutationofjb/tasks/conversationtask.h @@ -0,0 +1,45 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "mutationofjb/tasks/task.h" +#include "mutationofjb/gamedata.h" +#include "mutationofjb/widgets/conversationwidget.h" + +namespace MutationOfJB { + +class ConversationTask : public Task, public ConversationWidgetCallback { +public: + ConversationTask(const ConversationInfo& convInfo) : _convInfo(convInfo), _currentLine(0) {} + virtual ~ConversationTask() {} + + virtual void start() override; + virtual void update() override; + + virtual void onResponseClicked(ConversationWidget *, int response) override; +private: + void updateWidget(); + + const ConversationInfo &_convInfo; + uint _currentLine; +}; + +} diff --git a/engines/mutationofjb/tasks/task.h b/engines/mutationofjb/tasks/task.h new file mode 100644 index 0000000000..7b43868269 --- /dev/null +++ b/engines/mutationofjb/tasks/task.h @@ -0,0 +1,56 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "common/scummsys.h" + +namespace MutationOfJB { + +class TaskManager; + +class Task { +public: + enum State { + IDLE, + RUNNING, + FINISHED + }; + + Task() : _taskManager(nullptr) {} + virtual ~Task() {} + + virtual void start() = 0; + virtual void update() = 0; + + void setTaskManager(TaskManager *taskMan) { _taskManager = taskMan; } + TaskManager *getTaskManager() { return _taskManager; } + + State getState() const { return _state; } + +protected: + void setState(State state) { _state = state; } + +private: + TaskManager *_taskManager; + State _state; +}; + +} diff --git a/engines/mutationofjb/tasks/taskmanager.cpp b/engines/mutationofjb/tasks/taskmanager.cpp new file mode 100644 index 0000000000..981654981f --- /dev/null +++ b/engines/mutationofjb/tasks/taskmanager.cpp @@ -0,0 +1,47 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "mutationofjb/tasks/taskmanager.h" +#include "mutationofjb/tasks/task.h" + +namespace MutationOfJB { + +void TaskManager::addTask(Task *task) { + _tasks.push_back(task); + task->setTaskManager(this); + task->start(); +} + +void TaskManager::removeTask(Task *task) { + Tasks::iterator it = Common::find(_tasks.begin(), _tasks.end(), task); + if (it != _tasks.end()) { + _tasks.erase(it); + } +} + +void TaskManager::update() { + for (Tasks::const_iterator it = _tasks.begin(); it != _tasks.end(); ++it) { + (*it)->update(); + } +} + +} diff --git a/engines/mutationofjb/tasks/taskmanager.h b/engines/mutationofjb/tasks/taskmanager.h new file mode 100644 index 0000000000..1f6be36ced --- /dev/null +++ b/engines/mutationofjb/tasks/taskmanager.h @@ -0,0 +1,51 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#ifndef MUTATIONOFJB_TASKMANAGER_H +#define MUTATIONOFJB_TASKMANAGER_H + +#include "common/array.h" + +namespace MutationOfJB { + +class Game; +class Task; + +class TaskManager { +public: + TaskManager(Game &game) : _game(game) {} + + void addTask(Task *task); + void removeTask(Task *task); + void update(); + + Game &getGame() { return _game; } + +private: + typedef Common::Array Tasks; + Tasks _tasks; + Game &_game; +}; + +} + +#endif diff --git a/engines/mutationofjb/util.cpp b/engines/mutationofjb/util.cpp index 1a56a62af6..6d7c02a293 100644 --- a/engines/mutationofjb/util.cpp +++ b/engines/mutationofjb/util.cpp @@ -33,5 +33,27 @@ void reportFileMissingError(const char *fileName) { warning("%s", errorMessage.c_str()); } +Common::String toUpperCP895(const Common::String &str) { + static const byte conversionTable[] = { + 0x00, 0x9A, 0x90, 0x85, 0x8E, 0x00, 0x00, 0x80, 0x89, 0x00, 0x00, 0x00, 0x9C, 0x8A, 0x00, 0x00, /* 0x80-0x8F */ + 0x00, 0x92, 0x00, 0xA7, 0x99, 0x00, 0xA6, 0x00, 0x9D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x86, /* 0x90-0x9F */ + 0x8F, 0x8B, 0x95, 0x97, 0xA5, 0x00, 0x00, 0x00, 0x9B, 0x9E, 0xAB, 0x00 /* 0xA0-0xAB */ + }; + + Common::String ret = str; + for (Common::String::iterator it = ret.begin(); it != ret.end(); ++it) { + const byte cp895Byte = reinterpret_cast(*it); + if (cp895Byte < 0x80) { + *it = static_cast(toupper(*it)); + } else if (cp895Byte <= 0xAB) { + byte newChar = conversionTable[cp895Byte - 0x80]; + if (newChar != 0) { + reinterpret_cast(*it) = newChar; + } + } + } + return ret; +} + } diff --git a/engines/mutationofjb/util.h b/engines/mutationofjb/util.h index 95a896d336..86ee10f82e 100644 --- a/engines/mutationofjb/util.h +++ b/engines/mutationofjb/util.h @@ -23,9 +23,14 @@ #ifndef MUTATIONOFJB_UTIL_H #define MUTATIONOFJB_UTIL_H +namespace Common { +class String; +} + namespace MutationOfJB { void reportFileMissingError(const char *fileName); +Common::String toUpperCP895(const Common::String &str); } diff --git a/engines/mutationofjb/widgets/conversationwidget.cpp b/engines/mutationofjb/widgets/conversationwidget.cpp index c609fb4bfc..71a3483b75 100644 --- a/engines/mutationofjb/widgets/conversationwidget.cpp +++ b/engines/mutationofjb/widgets/conversationwidget.cpp @@ -25,6 +25,7 @@ #include "mutationofjb/gamedata.h" #include "mutationofjb/gui.h" #include "mutationofjb/font.h" +#include "common/events.h" namespace MutationOfJB { @@ -36,7 +37,8 @@ enum { ConversationWidget::ConversationWidget(Gui &gui, const Common::Rect &area, const Graphics::Surface &surface) : Widget(gui, area), - _surface(surface) {} + _surface(surface), + _callback(nullptr) {} void ConversationWidget::setLine(int lineNo, const Common::String &str) { @@ -58,7 +60,28 @@ void ConversationWidget::_draw(Graphics::ManagedSurface &surface) { } // TODO: Active line should be WHITE. - _gui.getGame().getSystemFont().drawString(line, LIGHTGRAY, CONVERSATION_LINES_X, CONVERSATION_LINES_Y + i * CONVERSATION_LINE_HEIGHT, surface); + _gui.getGame().getAssets().getSystemFont().drawString(line, LIGHTGRAY, CONVERSATION_LINES_X, CONVERSATION_LINES_Y + i * CONVERSATION_LINE_HEIGHT, surface); + } +} + +void ConversationWidget::handleEvent(const Common::Event &event) { + switch(event.type) { + case Common::EVENT_LBUTTONDOWN: + { + const int16 x = event.mouse.x; + const int16 y = event.mouse.y; + if (_area.contains(x, y)) { + if (_callback) { + int lineNum = (y - CONVERSATION_LINES_Y) / CONVERSATION_LINE_HEIGHT; + if (!_lines[lineNum].empty()) { + _callback->onResponseClicked(this, lineNum); + } + } + } + break; + } + default: + break; } } diff --git a/engines/mutationofjb/widgets/conversationwidget.h b/engines/mutationofjb/widgets/conversationwidget.h index 0f26a99d3f..b404abc198 100644 --- a/engines/mutationofjb/widgets/conversationwidget.h +++ b/engines/mutationofjb/widgets/conversationwidget.h @@ -28,21 +28,32 @@ namespace MutationOfJB { +class ConversationWidget; + +class ConversationWidgetCallback { +public: + virtual ~ConversationWidgetCallback() {} + virtual void onResponseClicked(ConversationWidget *, int response) = 0; +}; + class ConversationWidget : public Widget { public: enum { CONVERSATION_LINES = 4 }; ConversationWidget(Gui &gui, const Common::Rect &area, const Graphics::Surface &surface); + void setCallback(ConversationWidgetCallback *callback) { _callback = callback; } void setLine(int lineNo, const Common::String &str); + virtual void handleEvent(const Common::Event &event) override; + protected: - void _draw(Graphics::ManagedSurface &surface); + virtual void _draw(Graphics::ManagedSurface &surface) override; private: - Graphics::Surface _surface; Common::String _lines[CONVERSATION_LINES]; + ConversationWidgetCallback *_callback; }; } -- cgit v1.2.3