Envision, Create, Share

Welcome to HBGames, a leading amateur game development forum and Discord server. All are welcome, and amongst our ranks you will find experts in their field from all aspects of video game design and development.

[REVIEW] Cache Picture with switch1

Hi, thought I'd try my hand at something extremely simple. The title says it all. I'm trying to make a script that shows a picture when Switch 1 is one. I definitely know something is missing. It doesn't work and I'm trying to find out why.

Script:

Code:
class Book

  def initialize

    

  if $game_system.switch_id[1] == true

  $game_system = RPG::Cache.picture("Event1")

else

  return  

end

end

 
 
It's missing lots... :scruff:

1) I'm not a great teacher, so bear/bare with me..

2) class Book

...does not create an object. It only defines the parameters & methods of that object type for when it is created.
Since you want to display an image, you also need to define your class 'based on' or 'inheriting from' a class that handles images (bitmaps). This would be the Window or Sprite class. So, your first line should/could be...

class Book < Sprite

3) The 'initialize' method of a class gets executed once when the object is created. It is used to set up default values for the parameters, and define the 'state' that the object is in when it is created. Your test for the switch belongs in an 'update' method.

4)The object that holds the games switches is $game_switches. so your 'if' statement should read:

if $game_switches[1] == true


But, again this belongs in the update method, which you'll see below

5) $game_system = RPG::Cache.picture("Event1")

$game_system is an existing object with a whole bunch of parameters & methods. The line above overwrites everything in $game_system with an image, and doesn't have any methods to handle images. Images need to be loaded into a Bitmap object, which is a parameter of another object that handles bitmaps (a Sprite or Window).

6) Minor detail, but a good habit. Properly indent your code. It makes it much easier for you & others to read.
Code:
class Book

  def initialize

 

    if $game_system.switch_id[1] == true

      $game_system = RPG::Cache.picture("Event1")

    else

      return  

    end

  end

end

 


7) Here is a "Book" class that works. I copied the Sprite_Timer class, and modified it to display your book. I'll do my best to explain it...

Code:
#==============================================================================

# ** Sprite_Book

#------------------------------------------------------------------------------

#  This sprite is used to display the book.It observes the $game_switches

#  class and automatically changes sprite conditions.

#==============================================================================

 

class Book < Sprite

  #--------------------------------------------------------------------------

  # * Object Initialization

  #--------------------------------------------------------------------------

  def initialize

    super

    self.visible = false

    self.bitmap = RPG::Cache.picture("Parchment")

    self.x = 320 - self.bitmap.width / 2

    self.y = 240 - self.bitmap.height / 2

    self.z = 500

    update

  end

  #--------------------------------------------------------------------------

  # * Dispose

  #--------------------------------------------------------------------------

  def dispose

    if self.bitmap != nil

      self.bitmap.dispose

    end

    super

  end

  #--------------------------------------------------------------------------

  # * Frame Update

  #--------------------------------------------------------------------------

  def update

    super

    if self.visible and $game_switches[1] == false

      self.visible = false

    end

    if self.visible == false and $game_switches[1] == true

      self.visible = true

    end      

  end

end

 

class Spriteset_Map

  alias book_init initialize

  alias book_dispose dispose

  alias book_update update

  

  def initialize

    book_init

    @book = Book.new

  end

  

  def dispose

    @book.dispose

    book_dispose

  end

  

  def update

    book_update

    if @book != nil

      @book.update

    end

  end

end

class Book < Sprite


This object type inherits properties & methods from the Sprite class. We're saying, "Book is a type of Sprite". The property we're most concerned with is "bitmap", which is another object of the Bitmap class.

  def initialize
super


This is the method that gets called when you create a new object of the Book class.
"super" calls the same method in the parent class (Sprite.initialize)

    self.visible = false


'visible' is another property of the Sprite class. We want our sprite invisible to start with, so we set it to false.
we use 'self' to say 'this object'. So self.visible is the visible property of the current object.

    self.bitmap = RPG::Cache.picture("Parchment")


Now we set the bitmap property (which is it's own object) of the sprite to use the file "Parchment"

    self.x = 320 - self.bitmap.width / 2
self.y = 240 - self.bitmap.height / 2
self.z = 500


Set the x & y properties to the upper left corner of the image. (320,240 is the center of the screen). Set the 'z' property so it will be above characters & other map objects.

    update


call the update method. Nothing happens in this class, but update also calls 'super', which is the 'update' method of the parent (Sprite).

  def dispose
if self.bitmap != nil
self.bitmap.dispose
end
super
end


dispose automatically gets called when the object is destroyed or goes out of scope. Since the bitmap is also an object, we need to dispose it first, then call the dispose method of the parent class using 'super'.

  def update
super
if self.visible and $game_switches[1] == false
self.visible = false
end
if self.visible == false and $game_switches[1] == true
self.visible = true
end
end
end


The update method is what we use to check the switch, and change the visibility of the sprite based on the switch setting. We'll call the update method each frame from the same object we use to create the sprite (and dispose it).
'super' calls the update method from the Sprite class.
I used a compound 'if' statement to improve the efficiency. It only changes the visible property if the switch does not agree with the current state of the object (visible or not visible).

class Spriteset_Map


this class already exists, we are just going to add to it. This is the class for all of the images that get created to be used on the map.
We'll use this class to initialize, update, and dispose our "Book" object.

  alias book_init initialize
alias book_dispose dispose
alias book_update update

alias is a cool statement we can use to keep an existing class's methods as they are, but add to the beginning or end of that method.
The first alias means, "rename the old 'initialize' method to 'book_init'." so we can create a new initialize method, but still call the old one.

  def initialize
book_init
@book = Book.new
end


The 'initialize' method of Spriteset_Map is where we will create the new 'Book' object. First we call the old initialize method (in the Spriteset_Map script) using our alias 'book_init'.
Then we create a new object called @book using our Book class as a template. The .new method of Book creates the object and calls it's initialize method. (which we defined above).
The construct above is the same as inserting the line, "@book = Book.new' at the end of the Spriteset_Map script's initialize method. It's just much neater, easier to keep track of, and allows us to write scripts that we can just "Insert above Main".

  def dispose
@book.dispose
book_dispose
end


So, lets do the same thing with the dispose method. This time we'll dispose of our @book object, then call the old 'dispose' method in Spriteset_Map.

  def update
book_update
if @book != nil
@book.update
end
end


Same deal with the update method. We call the old 'update' method, then add our update code. Since 'update' gets called from the initialize method in Spriteset_Map, and we are calling 'book_init' before we create our object, our object does not exist the first time 'update' gets called.
So, we add the if statement, "if @book != nil" to prevent an error on that first update. Once the @book object is created, then @book.update can be called.

Does that help?
 

illy

Member

Code:
 

  #--------------------------------------------------------------------------

  # * Frame Update

  #--------------------------------------------------------------------------

  def update

    super

    if self.visible and !$game_switches[1]

      self.visible = false

    end

    if !self.visible and $game_switches[1]

      self.visible = true

    end      

  end

 

Could this not also work? Not to be nit-picky or anything, but it just seems more consistent to do it this way. Of course, I could be wrong, I'm still a beginner. :shades:
 
Either way works, and I don't think there's a performance difference. Both are making a true / false comparison.

I have a tendency when providing examples to 'spell things out' for clarity. I suppose we could have just said...

Code:
 

if self.visible != $game_switches[1]

   self.visible = !self.visible

end

 

or

Code:
 

if self.visible != $game_switches[1]

   self.visible = $game_switches[1]

end

 

or

Code:
 

self.visible = $game_switches[1] ? true : false

 

or just

Code:
 

self.visible = $game_switches[1]

 

I started out playing around with the RPG::sprite class, and trying to use the 'appear' & 'escape' methods to fade the picture in & out, so I didn't want to change the visibility unless it needed to be changed.

Be Well
 

Thank you for viewing

HBGames is a leading amateur video game development forum and Discord server open to all ability levels. Feel free to have a nosey around!

Discord

Join our growing and active Discord server to discuss all aspects of game making in a relaxed environment. Join Us

Content

  • Our Games
  • Games in Development
  • Emoji by Twemoji.
    Top