OgreBase.h 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400
  1. /*
  2. * Copyright (C) 2022 The V-Gears Team
  3. *
  4. * This file is part of V-Gears
  5. *
  6. * V-Gears is free software: you can redistribute it and/or modify it under
  7. * terms of the GNU General Public License as published by the Free Software
  8. * Foundation, version 3.0 (GPLv3) of the License.
  9. *
  10. * V-Gears is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. */
  15. #pragma once
  16. #include <Ogre.h>
  17. #include <OgreTextAreaOverlayElement.h>
  18. #include <OgreOverlay.h>
  19. #include <OgreOverlayManager.h>
  20. #include <Bites/OgreWindowEventUtilities.h>
  21. #include <OIS/OIS.h>
  22. #include "common/FileSystem.h"
  23. #include "Logger.h"
  24. /**
  25. * The Ogre system root component.
  26. */
  27. extern Ogre::Root* root;
  28. /**
  29. * The Ogre render window.
  30. */
  31. extern Ogre::RenderWindow* window;
  32. /**
  33. * List of Ogre entities.
  34. */
  35. extern std::vector<Ogre::Entity*> entities;
  36. /**
  37. * The Ogre camera.
  38. */
  39. extern Ogre::Camera* camera;
  40. class DisplayFrameListener;
  41. /**
  42. * The display frame listener.
  43. */
  44. extern DisplayFrameListener* frame_listener;
  45. /**
  46. * The display frame listener.
  47. *
  48. * It listens and responds to input events, such as window changes or mouse and
  49. * keyboard inputs.
  50. */
  51. class DisplayFrameListener :
  52. public Ogre::FrameListener, public Ogre::WindowEventListener,
  53. public OIS::KeyListener, public OIS::MouseListener
  54. {
  55. public:
  56. // Constructor takes a RenderWindow because it uses that to determine input context
  57. /**
  58. * Constructor.
  59. *
  60. * @param[in] win The render window. Used to determine input context.
  61. */
  62. DisplayFrameListener(Ogre::RenderWindow* win):
  63. window_(win), input_manager_(0), keyboard_(0),
  64. mouse_(0), mouse_rotate_(false), exit_(false)
  65. {
  66. using namespace OIS;
  67. Ogre::LogManager::getSingletonPtr()->logMessage("[OIS] Initializing...");
  68. ParamList pl;
  69. size_t window_hnd = 0; // TODO What does HND stand for?
  70. std::ostringstream window_hnd_str;
  71. win->getCustomAttribute("WINDOW", &window_hnd);
  72. window_hnd_str << window_hnd;
  73. pl.insert(std::make_pair(std::string("WINDOW"), window_hnd_str.str()));
  74. input_manager_ = InputManager::createInputSystem(pl);
  75. keyboard_ = static_cast<Keyboard*>(
  76. input_manager_->createInputObject(OIS::OISKeyboard, true)
  77. );
  78. keyboard_->setEventCallback(this);
  79. mouse_ = static_cast<OIS::Mouse*>(
  80. input_manager_->createInputObject(OIS::OISMouse, true)
  81. );
  82. mouse_->setEventCallback(this);
  83. //Register as a Window listener.
  84. Ogre::WindowEventUtilities::addWindowEventListener(window_, this);
  85. // Debug info.
  86. info_text = new Ogre::TextAreaOverlayElement("DebugText");
  87. info_text->setCaption("");
  88. info_text->setMetricsMode(Ogre::GMM_PIXELS);
  89. info_text->setPosition(5, 5);
  90. // info_text->setFontName("BlueHighway");
  91. info_text->setCharHeight(18);
  92. info_overlay = Ogre::OverlayManager::getSingleton().create("DebugOverlay");
  93. info_overlay->setZOrder(1);
  94. info_overlay->add2D((Ogre::OverlayContainer*) info_text);
  95. info_overlay->show();
  96. }
  97. virtual ~DisplayFrameListener(){
  98. input_manager_->destroyInputObject(keyboard_);
  99. OIS::InputManager::destroyInputSystem(input_manager_);
  100. //Remove self as a Window listener.
  101. Ogre::WindowEventUtilities::removeWindowEventListener(window_, this);
  102. windowClosed(window_);
  103. }
  104. /**
  105. * Called on window closing.
  106. *
  107. * Detaches OIS before window shutdown (very important under Linux).
  108. */
  109. virtual void windowClosed(Ogre::RenderWindow* rw){exit_ = true;}
  110. /**
  111. * Called when a frame is about to begin rendering.
  112. *
  113. * This event happens before any render targets have begun updating.
  114. * It captures input events and checks the state of entities.
  115. *
  116. * @param[in] evt Triggering event. Unused.
  117. * @return True to go ahead, false to abort rendering and drop out of
  118. * the rendering loop.
  119. */
  120. bool frameStarted(const Ogre::FrameEvent& evt){
  121. // TODO: Move implementation to cpp file.
  122. if (exit_ == true) return false;
  123. if (keyboard_) keyboard_->capture();
  124. if (mouse_) mouse_->capture();
  125. for (unsigned int i = 0; i < entities.size(); ++ i){
  126. if (entities[i]->isVisible() == true){
  127. Ogre::AnimationStateIterator animations
  128. = entities[i]->getAllAnimationStates()->getAnimationStateIterator();
  129. while (animations.hasMoreElements() == true){
  130. Ogre::AnimationState* state = animations.getNext();
  131. if (state->getEnabled() == true){
  132. state->addTime(evt.timeSinceLastFrame);
  133. info_text->setCaption(
  134. entities[i]->getName() + ": " + state->getAnimationName()
  135. );
  136. }
  137. }
  138. break;
  139. }
  140. }
  141. if (keyboard_->isKeyDown(OIS::KC_A)){
  142. assert(camera_);
  143. camera_->moveRelative(Ogre::Vector3(-0.005f, 0.0f, 0.0f));
  144. }
  145. if (keyboard_->isKeyDown(OIS::KC_D)){
  146. assert(camera_);
  147. camera_->moveRelative(Ogre::Vector3(0.005f, 0.0f, 0.0f));
  148. }
  149. if (keyboard_->isKeyDown(OIS::KC_W)){
  150. assert(camera_);
  151. camera_->moveRelative(Ogre::Vector3(0.0f, 0.0f, -0.005f));
  152. }
  153. if (keyboard_->isKeyDown(OIS::KC_S)){
  154. assert(camera_);
  155. camera_->moveRelative(Ogre::Vector3(0.0f, 0.0f, 0.005f));
  156. }
  157. if (mouse_rotate_ == true){
  158. assert(camera_);
  159. camera_->yaw(Ogre::Degree(-mouse_move_x_ * 0.13f));
  160. camera_->pitch(Ogre::Degree(-mouse_move_y_ * 0.13f));
  161. mouse_move_x_ = 0;
  162. mouse_move_y_ = 0;
  163. }
  164. return true;
  165. }
  166. /**
  167. * The key listener.
  168. *
  169. * Parses keyboard events.
  170. *
  171. * @param[in] e Triggering event.
  172. * @return Always true
  173. */
  174. bool keyPressed(const OIS::KeyEvent& e){
  175. switch(e.key){
  176. case OIS::KC_RIGHT:
  177. {
  178. bool change = false;
  179. for (unsigned int i = 0; i < entities.size(); ++ i){
  180. if (change == true){
  181. entities[i]->setVisible(true);
  182. break;
  183. }
  184. if (entities[i]->isVisible() == true && (i != entities.size() - 1)){
  185. entities[i]->setVisible(false);
  186. change = true;
  187. }
  188. }
  189. }
  190. break;
  191. case OIS::KC_LEFT:
  192. {
  193. bool change = false;
  194. for(int i = entities.size() - 1; i >= 0; -- i){
  195. if (change == true){
  196. entities[i]->setVisible(true);
  197. break;
  198. }
  199. if (entities[i]->isVisible() == true && i != 0){
  200. entities[i]->setVisible(false);
  201. change = true;
  202. }
  203. }
  204. }
  205. break;
  206. case OIS::KC_UP:
  207. {
  208. bool change = false;
  209. for (unsigned int i = 0; i < entities.size(); ++ i){
  210. if (entities[i]->isVisible() == true){
  211. Ogre::AnimationStateIterator animations
  212. = entities[i]->getAllAnimationStates()
  213. ->getAnimationStateIterator();
  214. Ogre::AnimationState* old_state;
  215. Ogre::AnimationState* new_state = animations.getNext();
  216. while (animations.hasMoreElements() == true){
  217. old_state = new_state;
  218. new_state = animations.getNext();
  219. if (new_state->getEnabled() == true){
  220. new_state->setEnabled(false);
  221. new_state->setLoop(false);
  222. old_state->setEnabled(true);
  223. old_state->setLoop(true);
  224. }
  225. }
  226. break;
  227. }
  228. }
  229. }
  230. break;
  231. case OIS::KC_DOWN:{
  232. bool change = false;
  233. for (unsigned int i = 0; i < entities.size(); ++ i){
  234. if (entities[i]->isVisible() == true){
  235. Ogre::AnimationStateIterator animations
  236. = entities[i]->getAllAnimationStates()->getAnimationStateIterator();
  237. while (animations.hasMoreElements() == true){
  238. Ogre::AnimationState* state = animations.getNext();
  239. if (change == true){
  240. state->setEnabled(true);
  241. state->setLoop(true);
  242. break;
  243. }
  244. if (
  245. state->getEnabled() == true
  246. && animations.hasMoreElements() != false
  247. ){
  248. state->setEnabled(false);
  249. state->setLoop(false);
  250. change = true;
  251. }
  252. }
  253. break;
  254. }
  255. }
  256. }
  257. break;
  258. }
  259. return true;
  260. }
  261. /**
  262. * Handles key releasing events.
  263. *
  264. * It does nothing.
  265. *
  266. * @param[in] e Triggering event.
  267. * @return Always true.
  268. */
  269. bool keyReleased(const OIS::KeyEvent& e){return true;}
  270. /**
  271. * Handles mouse movement events.
  272. *
  273. * @param[in] e Triggering event.
  274. * @return Always true.
  275. */
  276. bool mouseMoved(const OIS::MouseEvent& e){
  277. mouse_move_x_ = float(e.state.X.rel);
  278. mouse_move_y_ = float(e.state.Y.rel);
  279. return true;
  280. }
  281. /**
  282. * Handles mouse button-down events.
  283. *
  284. * @param[in] e Triggering event.
  285. * @param[in] id Button ID.
  286. * @return Always true.
  287. */
  288. bool mousePressed(const OIS::MouseEvent& e, OIS::MouseButtonID id){
  289. if (id == OIS::MB_Right) mouse_rotate_ = true;
  290. return true;
  291. }
  292. /**
  293. * Handles mouse button-up events.
  294. *
  295. * @param[in] e Triggering event.
  296. * @param[in] id Button ID.
  297. * @return Always true.
  298. */
  299. bool mouseReleased(const OIS::MouseEvent& e, OIS::MouseButtonID id){
  300. if (id == OIS::MB_Right) mouse_rotate_ = false;
  301. return true;
  302. }
  303. /**
  304. * The information text.
  305. */
  306. Ogre::TextAreaOverlayElement* info_text;
  307. /**
  308. * The information overlay.
  309. */
  310. Ogre::Overlay* info_overlay;
  311. /**
  312. * Sets the viewport camera
  313. */
  314. virtual void setCamera(Ogre::Camera *camera){camera_ = camera;}
  315. private:
  316. /**
  317. * The render window.
  318. */
  319. Ogre::RenderWindow* window_;
  320. /**
  321. * The OIS input manager.
  322. */
  323. OIS::InputManager* input_manager_;
  324. /**
  325. * The OIS keyboard.
  326. */
  327. OIS::Keyboard* keyboard_;
  328. /**
  329. * The OIS mouse.
  330. */
  331. OIS::Mouse* mouse_;
  332. /**
  333. * The camera.
  334. */
  335. Ogre::Camera *camera_;
  336. /**
  337. * Mouse horizontal movement.
  338. */
  339. float mouse_move_x_;
  340. /**
  341. * Mouse vertical movement.
  342. */
  343. float mouse_move_y_;
  344. /**
  345. * Indicates if the mouse is being rotated.
  346. */
  347. bool mouse_rotate_;
  348. /**
  349. * Flag for application exit.
  350. */
  351. bool exit_;
  352. };
  353. /**
  354. * Initializes the Ogre system.
  355. *
  356. * @param[in] name Application title.
  357. */
  358. void InitializeOgreBase(const Ogre::String& name);
  359. /**
  360. * Destructs the Ogre system.
  361. */
  362. void DeinitializeOgreBase();