Event Wrapper

Tsukihime

Veteran
Veteran
Joined
Jun 30, 2012
Messages
8,564
Reaction score
3,846
First Language
English
Event Wrapper

-Tsukihime

Overview

This script provides a wrapper for the RPG::Event object. It adds additional methods to allow you to create event commands directly without having to go through the event editor, and provides intuitive names that are based on the command names available on the event editor.

This is mainly a scripting tool, and is not intended to replace the event editor.

If something can be achieved using the event editor, use it.

Features

  • Easily create events using scripts
  • An Event Builder that helps you create your list of command events
  • Use the Event Builder to mix scripting with event commands to create all sorts of event processing
  • Create move routes using a Move Builder, using the same syntax as the Event Builder with intuitive move commands and some custom move commands for convenience (eg: move strings)

Downloads

Script: http://db.tt/QiaEiAN2

Demo: http://db.tt/TavscwIB

If you are not sure where to start, I've provided some examples in the demo.

Usage

Currently, your scripted events are just scripts, so they are not very accessible. You must have an event on the map to be able to use a script call to create more events, though after that your custom events can create their own events provided that you've written the logic into their command list.

You can choose to write methods in Game_Interpreter or just a custom module. As long as you can call the methods that will create the event.



Code:
class Game_Interpreter

   def make_my_event
      # your event building code
   end
end


Creating an event is simple.

1. Instantiate an Event object, passing in x,y coordinates



Code:
event = Event.new(2, 4)
2. Set some page properties. For a list of properties, refer to the help manual, or look through the Event class. You can either access the properties directly, or use some convenience methods defined in the Event class. So for example, assuming we are on page 0,



Code:
event.page[0].character_name = "actor1"
event.character_name = "actor1"
Both do the same thing.

Some common properties you might set are



Code:
event.priority_type = 1    # 1 is "same as characters". You can choose 0, 1, or 2
event.trigger = 2    # 2 is "event touch". It goes from 0 to 4, same order as in the editor
event.direction_fix = true
Note that the convenience methods always operate on the "current" page.

When you first initialize a new event, the "current" page is 0.

You can change the page by calling



Code:
event.set_page(n)
For some integer n. Thus, you may want to work on one page a time, as such:



Code:
event.set_page(0)
#do stuff for page 0

event.set_page(1)
# do stuff for page 1

event.set_page(2)
# do stuff for page 2
3. Set some page conditions. Refer to the Event_Condition class for details.



Code:
event.condition.switch1_id = 2   # this means switch 2 must be ON
event.condition.switch2_id = 3   # remember that the event supports two switches
event.condition.actor_id = 4     # actor 4 must be in party
4. Add the event to the map



Code:
$game_map.add_event(event)
That should create an event on the map at the designated x,y coords when we make a script call to create this event, but it's not very useful. We want to add some event commands.

I've provided an "Event Builder" that allows you to use a custom syntax to create your events in addition to regular ruby syntax.

I have written a set of methods that essentially alias Game_Interpreter methods, except instead of using command codes, I use the common editor names to identify what the command is. All of the methods are available in the EventCommands class. So for example, let's write an event that will display a simple message



Code:
event = Event.new(3, 3)
event.character_name = "actor1"
event.character_index = 2
event.build {
  show_text("actor1", 2)
  add_message("Hello World")
}
$game_map.add_event(event)
When you create this event, you can talk to it and it will say "Hello World"



Note that `add_message` can take multiple strings. Each string will be treated as a new line.



Code:
event.build {
  show_text("actor1", 2)
  add_message("Hello World", "Goodbye")
}
The event builder supports branching, which is used in various commands such as showing a list of choices, conditional branching, and other things.



Code:
event.build {
   show_text("actor1", 1)
   add_message("What do you like?")
   show_choices(["Health", "Mana"], 0)
   choice_branch(0) {
      show_text("actor1", 1)
      add_message("So you prefer health")
   }
   choice_branch(1) {
      show_text("actor1", 1)
      add_message("Mana is ok too")
   }
}
This example demonstrates how to using branching to create a list of choices that the player can select from, and how to define the commands that should be executed depending on the choice.

Naturally, you can provide an unlimited number of branches, though the choice window is not designed for that (meaning, you might have choices that are drawn outside the screen if there are just too many)



It is also possible to use typical ruby syntax when building your commands.

You know, take advantage of loops and variables.



Code:
event = Event.new(x, y)
event.character_name = "actor2"
event.character_index = 5

event.build {
  show_text("actor2", 5)
  add_message("Which party member do you wish to view?")
  actors = $game_party.members.collect {|actor| actor.name }
  show_choices(actors, 0)

  $game_party.members.each_with_index { |actor, i|
    choice_branch(i) {
      show_text(actor.face_name, actor.face_index)
      add_message("%s is a level %d %s" %[actor.name, actor.level, actor.class.name])
    }
  }
}
$game_map.add_event(event)
This example demonstrates how you would write an event that will go through all of the actors in your party, display their names in a choice list, and then when you select an actor, it will display information about the actor in a text box.





However, note that because this code is run only when the event is created, the event commands have already been hardcoded into the event. It is no different from manually creating an event and writing your own choice branches and such.

One of the goals of this script is to eventually allow you to create completely dynamic events whose commands may change at any time.

I am currently working on a way for you to specify that an event should be "rebuilt" everytime you enter the map, or your refresh the event. By rebuilding the event, you are basically clearing out the command list and re-running the script, which will correctly reflect the current state of the game.

Reference

The objects of interest are

RPG::Event

RPG::Event::page

RPG::Event::page::Condition

RPG::Event::page::Graphic

RPG::EventCommand

RPG::MoveRoute

RPG::MoveCommand

All of these are described in the help manual under RGSS Reference Manual -> Game Library -> RPGVXAce Data Structures.
 
Last edited by a moderator:

RyanA

Happy Cat
Veteran
Joined
Jun 28, 2012
Messages
2,423
Reaction score
230
First Language
English
Primarily Uses
Looks pretty nifty! Thanks! :3
 

Tsukihime

Veteran
Veteran
Joined
Jun 30, 2012
Messages
8,564
Reaction score
3,846
First Language
English
It is now easy to create move routes for events (same as the set_move_route command in the event editor)

The syntax is the same as the event builder:



Code:
route = MoveRoute.new
route.repeat = false
route.skippable = true
route.build {
   move_up
   move_down(2)
   move("2L2R3U10D")  # 2 left, 2 right, 3 up, 10 down
   turn_random(10)
}
Once you have your route, you can then add it to the event



Code:
event.build {
   set_move_route(-1, route)
}
-1 means the player will follow that move route.

0 means "this event" will follow that move route

Other integers means the event with that ID will follow that move route.

Now you can dynamically create events with full movements.

If you are familiar with the event editor, you will know that the event page can have its own move route.



While setting up the event, you have the option of assigning a route to each page.

You must make sure that the move_type for the page is set to 3 (custom movement in editor)



Code:
event = Event.new(x, y)
route = MoveRoute.new
route.repeat = false
route.skippable = true
route.build {
   move_up
   move_down(2)
   move("2L2R")
   turn_random(10)
}

event.move_type = 3
event.move_route = route 

event.build {
   set_move_route(-1, route)
}

$game_map.add_event(event)
 
Last edited by a moderator:

Tsukihime

Veteran
Veteran
Joined
Jun 30, 2012
Messages
8,564
Reaction score
3,846
First Language
English
Script updated.

I have finally decided on how to implement conditional branches, and I basically decided to take the easy way out.

All conditions are just regular script conditions (eg: ruby statements)

For example,



Code:
def make_condition_event(x, y)
    event = Event.new(x, y)
    event.character_name = "actor1"
    event.character_index = 2
    event.build {
      cond_if("$game_actors[1].level > 5") {
        show_text("actor1", 2)
        add_message("Hello World")
        change_followers(true)
      }
      cond_else {
        show_text("actor1", 2)
        add_message("Your level is below 5")
      }
    }
    $game_map.add_event(event)
  end
You just pass in a string as your script call.

I don't really want to bother with having a dozen different cases for every possible condition when you could just script it directly.

My assumption is that if you're already writing scripted events, then you should be familiar enough with ruby to be able to write if/else conditions.
 

Tsukihime

Veteran
Veteran
Joined
Jun 30, 2012
Messages
8,564
Reaction score
3,846
First Language
English
I've implemented a new way to work with the Event builder.

It was a bad idea to make everything static variables and methods, because it just means you only have one command list stored in the builder at anytime. Of course, each command list is unique, so you didn't have to worry about different events holding references to the same array of event commands.

I've made it so that you can now instantiate an EventBuilder object. This was primarily to allow me to combine different event builders together. It allows you to easily re-use event lists and allows for more modular code.

Here is an example:



Code:
module Quick
  def self.test_list
    return EventBuilder.new {
      show_text
      add_message("intercept")
    }
  end

  def self.test
    event = Event.new(1, 1)
    eb = EventBuilder.new {
      process_method(Quick, :test_list)
      show_text
      add_message("What do you want to do?")
    }

    # we need to explicitly grab the builder's list
    event.list = eb.list
  end
end
I have one method that simply shows the message "intercept"

I have another method that actually builds an event. I would like to re-use my intercept message inside the event, so I use the `process_method` command to tell the event builder to call another method.

`process method` requires the target method to return an EventBuilder object, and I combine the two command lists into one.

You can still use the original



Code:
event.list = EventBuilder.build {
   stuff
}
but keep in mind that if you use the static method, you won't be able to pass your event builder around.
 
Last edited by a moderator:

Archduke

Jack of all Trades
Veteran
Joined
Jul 1, 2012
Messages
292
Reaction score
80
First Language
English
Primarily Uses
This is pretty neat; I can see a thousand and one uses with such a script!
 

DisturbedInside

Villager
Member
Joined
Jul 21, 2012
Messages
11
Reaction score
0
First Language
English
Primarily Uses
Code:
  # not sure, maybe a cancel branch?
  def end_choices
    add_command(404)	  #<===   lol command not found
  end
 

DeadElf79

Villager
Member
Joined
Oct 21, 2014
Messages
5
Reaction score
1
First Language
Russian
Primarily Uses
Can you explain how to get a reason why an event wasn't created? I made a mistake and don't know what kind of, but no event was added to $game_map.events

-----------

Problem solved with this correction:

Code:
def add_event(event)    return unless event    puts "event valid"    # find an available index    if $game_temp.queued_add_events.empty?      index = @events.empty? ? 1 : @events.keys.max + 1    else      index = $game_temp.queued_add_events.keys.max + 1    end    event.id = index    puts "\tevent.id:#{event.id}"    # need to store this custom event somewhere    $game_system.add_custom_event(@map_id, event)        # CORRECTION HERE    # from 10.6.12 version    @events[index] = Game_Event.new(@map_id, event)    SceneManager.scene.refresh_spriteset if SceneManager.scene_is?(Scene_Map)  end
 
Last edited by a moderator:

Users Who Are Viewing This Thread (Users: 0, Guests: 1)

Latest Threads

Latest Posts

Latest Profile Posts

Couple hours of work. Might use in my game as a secret find or something. Not sure. Fancy though no? :D
Holy stink, where have I been? Well, I started my temporary job this week. So less time to spend on game design... :(
Cartoonier cloud cover that better fits the art style, as well as (slightly) improved blending/fading... fading clouds when there are larger patterns is still somewhat abrupt for some reason.
Do you Find Tilesetting or Looking for Tilesets/Plugins more fun? Personally I like making my tileset for my Game (Cretaceous Park TM) xD
How many parameters is 'too many'??

Forum statistics

Threads
105,867
Messages
1,017,061
Members
137,575
Latest member
akekaphol101
Top