- Added a new script command to display text files
authorMatthias Braun <matze@braunis.de>
Thu, 12 May 2005 15:13:55 +0000 (15:13 +0000)
committerMatthias Braun <matze@braunis.de>
Thu, 12 May 2005 15:13:55 +0000 (15:13 +0000)
- Refactored ScriptingInterpreter a small bit
- Added the possibility to starts scripts for worldmap intro and level extro

SVN-Revision: 2475

14 files changed:
data/levels/world1/de.po
data/levels/world1/worldmap.stwm
src/badguy/yeti.cpp
src/game_session.cpp
src/game_session.h
src/scripting/functions.cpp
src/scripting/functions.h
src/scripting/script_interpreter.cpp
src/scripting/script_interpreter.h
src/scripting/wrapper.cpp
src/sector.cpp
src/trigger/scripttrigger.cpp
src/worldmap.cpp
src/worldmap.h

index 91a252b..9fcf9de 100644 (file)
@@ -43,7 +43,7 @@ msgid ""
 msgstr ""
 "-Penny ist verschwunden!\n"
 "\n"
-"#Tux und Penny sassen gemtlich beim Picknick\n"
+"#Tux und Penny sassen gemütlich beim Picknick\n"
 "#in den eisigen Ebenen der Antarktis.\n"
 "#Plötzlich sprang eine dunkle Kreatur hinter\n"
 "#einem Felsen hervor. Tux sah einen grellen\n"
@@ -54,7 +54,7 @@ msgstr ""
 "#hatte lag jetzt ein Zettel:\n"
 "\n"
 "#\"Tux, mein Erzfeind!\n"
-"#Ich habe deine Freundinn Penny entfhrt und\n"
+"#Ich habe deine Freundinn Penny entführt und\n"
 "#halte sie in meiner Festung gefangen. Den Weg\n"
 "#dorthin bewachen meine finsteren Kreaturen!\n"
 "#Versuche gar nicht erst sie zu retten, du\n"
index 8934bc9..6475086 100644 (file)
@@ -2,9 +2,11 @@
 (supertux-worldmap
   (properties 
     (name (_ "Icyisland"))
-    (intro-filename "intro.txt")
     (music "salcon.mod")
   )
+  (intro-script "
+display_text_file(\"intro.txt\")
+")
   (spawnpoint
     (name "main")
     (x 4)
     (level
       (x 7)
       (y 20)
-      (extro-filename "extro.txt")
+      (extro-script "
+display_text_file(\"extro.txt\")
+")
       (name "level26.stl")
       (quit-worldmap #t))
 )
index b0d022c..c38c3ac 100644 (file)
@@ -25,6 +25,7 @@
 #include "object/camera.h"
 #include "yeti_stalactite.h"
 #include "bouncing_snowball.h"
+#include "game_session.h"
 #include "scripting/script_interpreter.h"
 
 static const float JUMP_VEL1 = 250;
@@ -146,7 +147,8 @@ Yeti::collision_squished(Player& player)
     if(dead_script != "") {
       try {
         ScriptInterpreter* interpreter 
-          = new ScriptInterpreter(Sector::current());
+          = new ScriptInterpreter(GameSession::current()->get_working_directory());
+        interpreter->register_sector(Sector::current());
         std::istringstream in(dead_script);
         interpreter->load_script(in, "Yeti - dead-script");
         interpreter->start_script();
index 1402e64..2ef554d 100644 (file)
@@ -64,6 +64,7 @@
 #include "control/codecontroller.h"
 #include "control/joystickkeyboardcontroller.h"
 #include "main.h"
+#include "file_system.h"
 #include "gameconfig.h"
 #include "gettext.h"
 
@@ -648,6 +649,12 @@ GameSession::set_reset_point(const std::string& sector, const Vector& pos)
   reset_pos = pos;
 }
 
+std::string
+GameSession::get_working_directory()
+{
+  return FileSystem::dirname(levelfile);
+}
+
 void
 GameSession::display_info_box(const std::string& text)
 {
index eb31ed4..59023b3 100644 (file)
@@ -89,6 +89,12 @@ public:
   void start_sequence(const std::string& sequencename);
   /// called by JoystickKeyboardController after an ascii key has been pressed
   void try_cheats();
+
+  /** returns the "working directory" usually this is the directory where the
+   * currently played level resides. This is used when locating additional
+   * resources for the current level/world
+   */
+  std::string get_working_directory();
   
 private:
   void restart_level();
index 5b24c92..a3c211a 100644 (file)
@@ -1,9 +1,11 @@
 #include <stdio.h>
 #include <string>
 #include <squirrel.h>
+#include "textscroller.h"
 #include "functions.h"
 #include "script_interpreter.h"
 #include "tinygettext/tinygettext.h"
+#include "resources.h"
 #include "gettext.h"
 
 namespace Scripting
@@ -19,5 +21,12 @@ std::string translate(const std::string& text)
   return dictionary_manager.get_dictionary().translate(text);
 }
 
+void display_text_file(const std::string& filename)
+{
+  std::string file 
+    = ScriptInterpreter::current()->get_working_directory() + filename;
+  ::display_text_file(file);
+}
+
 }
 
index f7c8f5c..2f4d6c8 100644 (file)
@@ -4,6 +4,8 @@
 namespace Scripting
 {
 
+/** displays a text file and scrolls it over the screen */
+void display_text_file(const std::string& filename);
 /** Suspends the script execution for the specified number of seconds */
 void set_wakeup_time(float seconds);
 /** translates a give text into the users language (by looking it up in the .po
index 095c6af..13e9494 100644 (file)
@@ -15,6 +15,8 @@
 #include "wrapper.h"
 #include "wrapper_util.h"
 #include "sector.h"
+#include "file_system.h"
+#include "game_session.h"
 #include "object/text_object.h"
 #include "object/scripted_object.h"
 #include "object/display_effect.h"
@@ -32,8 +34,8 @@ static void printfunc(HSQUIRRELVM, const char* str, ...)
 
 ScriptInterpreter* ScriptInterpreter::_current = 0;
 
-ScriptInterpreter::ScriptInterpreter(Sector* sector)
-  : sound(0), level(0)
+ScriptInterpreter::ScriptInterpreter(const std::string& new_working_directory)
+  : working_directory(new_working_directory), sound(0), level(0)
 {
   v = sq_open(1024);
   if(v == 0)
@@ -59,8 +61,19 @@ ScriptInterpreter::ScriptInterpreter(Sector* sector)
   
   // register supertux API
   register_functions(v, supertux_global_functions);
-  register_classes(v, supertux_classes);  
+  register_classes(v, supertux_classes);
 
+  // expose some "global" objects
+  sound = new Scripting::Sound();
+  expose_object(sound, "Sound", "Sound");  
+  
+  level = new Scripting::Level();
+  expose_object(level, "Level", "Level");
+}
+
+void
+ScriptInterpreter::register_sector(Sector* sector)
+{
   // expose ScriptedObjects to the script
   for(Sector::GameObjects::iterator i = sector->gameobjects.begin();
       i != sector->gameobjects.end(); ++i) {
@@ -73,12 +86,6 @@ ScriptInterpreter::ScriptInterpreter(Sector* sector)
     expose_object(scripted_object, scripted_object->get_name(), 
         "ScriptedObject");
   }
-  // expose some "global" objects
-  sound = new Scripting::Sound();
-  expose_object(sound, "Sound", "Sound");
-  
-  level = new Scripting::Level();
-  expose_object(level, "Level", "Level");
   
   TextObject* text_object = new TextObject();
   sector->add_object(text_object);
index df00032..c4ecabc 100644 (file)
@@ -13,9 +13,11 @@ class Sector;
 class ScriptInterpreter : public GameObject
 {
 public:
-  ScriptInterpreter(Sector* sector);
+  ScriptInterpreter(const std::string& working_dir);
   ~ScriptInterpreter();
 
+  void register_sector(Sector* sector);
+
   void draw(DrawingContext& );
   void update(float );
 
@@ -32,11 +34,18 @@ public:
     return _current;
   }
 
+  const std::string& get_working_directory() const
+  {
+      return working_directory;
+  }
+
 private:
   HSQUIRRELVM v;
   static ScriptInterpreter* _current;
   Timer wakeup_timer;
 
+  /// this directory is used as base for all filenames used in scripts
+  std::string working_directory;
   Scripting::Sound* sound;
   Scripting::Level* level;
 };
index dbde0ec..f675e99 100644 (file)
@@ -354,6 +354,16 @@ static int Text_set_visible_wrapper(HSQUIRRELVM v)
   return 0;
 }
 
+static int display_text_file_wrapper(HSQUIRRELVM v)
+{
+  const char* arg0;
+  sq_getstring(v, 2, &arg0);
+  
+  Scripting::display_text_file(arg0);
+  
+  return 0;
+}
+
 static int set_wakeup_time_wrapper(HSQUIRRELVM v)
 {
   float arg0;
@@ -376,6 +386,7 @@ static int translate_wrapper(HSQUIRRELVM v)
 }
 
 WrappedFunction supertux_global_functions[] = {
+  { "display_text_file", &display_text_file_wrapper },
   { "set_wakeup_time", &set_wakeup_time_wrapper },
   { "translate", &translate_wrapper },
   { 0, 0 }
index 11957a4..8a53d05 100644 (file)
@@ -418,7 +418,9 @@ Sector::activate(const std::string& spawnpoint)
   // Run init script
   if(init_script != "") {
     try {
-      ScriptInterpreter* interpreter = new ScriptInterpreter(this);
+      ScriptInterpreter* interpreter 
+        = new ScriptInterpreter(GameSession::current()->get_working_directory());
+      interpreter->register_sector(this);
       std::string sourcename = std::string("Sector(") + name + ") - init";
       std::istringstream in(init_script);
       interpreter->load_script(in, sourcename);
index 7a7c27a..1e576cc 100644 (file)
@@ -85,7 +85,9 @@ ScriptTrigger::event(Player& , EventType type)
     {\r
       try\r
       {\r
-        ScriptInterpreter* interpreter = new ScriptInterpreter(Sector::current());\r
+        ScriptInterpreter* interpreter \r
+          = new ScriptInterpreter(GameSession::current()->get_working_directory());\r
+        interpreter->register_sector(Sector::current());\r
         std::istringstream in(script);\r
         interpreter->load_script(in, "trigger-script");\r
         interpreter->start_script();\r
index e193b0f..872c285 100644 (file)
@@ -51,6 +51,7 @@
 #include "control/joystickkeyboardcontroller.h"
 #include "object/background.h"
 #include "object/tilemap.h"
+#include "scripting/script_interpreter.h"
 
 Menu* worldmap_menu  = 0;
 
@@ -432,7 +433,8 @@ WorldMap::load_map()
         const lisp::Lisp* props = iter.lisp();
         props->get("name", name);
         props->get("music", music);
-        props->get("intro-filename", intro_filename);
+      } else if(iter.item() == "intro-script") {
+        iter.value()->get(intro_script);
       } else if(iter.item() == "spawnpoint") {
         SpawnPoint* sp = new SpawnPoint(iter.lisp());
         spawn_points.push_back(sp);
@@ -519,7 +521,7 @@ WorldMap::parse_level_tile(const lisp::Lisp* level_lisp)
   level.south = true;
   level.west  = true;
 
-  level_lisp->get("extro-filename", level.extro_filename);
+  level_lisp->get("extro-script", level.extro_script);
   level_lisp->get("next-worldmap", level.next_worldmap);
 
   level.quit_worldmap = false;
@@ -840,10 +842,12 @@ WorldMap::update(float delta)
       /* The porpose of the next checking is that if the player lost
          the level (in case there is one), don't show anything */
       if(level_finished) {
-        if (!level->extro_filename.empty()) {
-          // Display a text file
-          std::string filename = levels_path + level->extro_filename;
-          display_text_file(filename);
+        if (level->extro_script != "") {
+          ScriptInterpreter* interpreter = new ScriptInterpreter(levels_path);
+          std::istringstream in(level->extro_script);
+          interpreter->load_script(in, "level-extro-script");
+          interpreter->start_script();
+          add_object(interpreter);
         }
 
         if (!level->next_worldmap.empty())
@@ -986,9 +990,13 @@ WorldMap::display()
   song = sound_manager->load_music(datadir +  "/music/" + music);
   sound_manager->play_music(song);
 
-  if(!intro_displayed && intro_filename != "") {
-    std::string filename = levels_path + intro_filename;
-    display_text_file(filename);
+  if(!intro_displayed && intro_script != "") {
+    ScriptInterpreter* interpreter = new ScriptInterpreter(levels_path);
+    std::istringstream in(intro_script);
+    interpreter->load_script(in, "worldmap-intro-script");
+    interpreter->start_script();
+    add_object(interpreter);
+                                           
     intro_displayed = true;
   }
 
index 0894d28..fa71bbc 100644 (file)
@@ -158,9 +158,8 @@ public:
     /** Check if this level should be vertically flipped */
     bool vertical_flip;
 
-    /** Filename of the extro text to show once the level is
-        successfully completed */
-    std::string extro_filename;
+    /** Script that is run when the level is successfully finished */
+    std::string extro_script;
 
     /** Go to this world */
     std::string next_worldmap;
@@ -198,7 +197,7 @@ private:
   Vector offset;
   std::string savegame_file;
   
-  std::string intro_filename;
+  std::string intro_script;
   bool intro_displayed;
 
   void get_level_title(Level& level);