[Carte]Ombres dinamiques

La section pour les scripts de RPG Maker XP !

[Carte]Ombres dinamiques

Message par Amathlog » 18 Juin 2007, 21:03

Vient de la factory
Auteur : rataime

Bon, comme on aime tous avoir des effets qui tuent dans nos jeux, j'avais suivi le tuto de Genzai Kawakami http://genzaik.suidzer0.org/?p=22&t=ombres sur la création d'ombres. En gros, ça permet d'avoir une ombre qui suit le héros et d'autres event au choix. J'avais envie de me mettre au Ruby, donc j'ai essayé d'adapter le scrîpt pour faire des ombres dynamiques. Petit apercu du résultat :
http://arthur.porre.free.fr/gwen/ombres.gif


Il y a 1 fichier à modifier, et un à créer :

Sprite_Character :
Code : Tout sélectionner
#==============================================================================
# ¦ Sprite_Character modifié (voir Sprite_Ombre)
#------------------------------------------------------------------------------
#  ??????????????????Game_Character ???????????
# ????????????????????????
#==============================================================================

class Sprite_Character < RPG::Sprite
  #--------------------------------------------------------------------------
  # ? ??????????
  #--------------------------------------------------------------------------
  attr_accessor :character                # ??????
  #--------------------------------------------------------------------------
  # ? ?????????
  #     viewport  : ??????
  #     character : ?????? (Game_Character)
  #--------------------------------------------------------------------------
  def initialize(viewport, character = nil)
    super(viewport)
    @character = character
    @ombrelist=[]
    if (character.is_a?(Game_Event) and character.list!=nil and character.list[0].code == 108 and character.list[0].parameters == ["s"])
      if (character.list[1]!=nil and character.list[1].code == 108)
        @anglemin=character.list[1].parameters.to_s
      end
      if (character.list[2]!=nil and character.list[2].code == 108)
        @anglemax=character.list[2].parameters.to_s
      end
      if (character.list[3]!=nil and character.list[3].code == 108)
        @distancemax=character.list[3].parameters.to_s
      end 
     for i in $game_map.events.keys.sort
      if ($game_map.events[i].is_a?(Game_Event) and $game_map.events[i].list!=nil and $game_map.events[i].list[0].code == 108 and $game_map.events[i].list[0].parameters == ["o"])
        @ombrelist[i+1] = Sprite_Ombre.new(viewport, $game_map.events[i],self,@anglemin,@anglemax,@distancemax)
      end
    end
    @ombrelist[1] = Sprite_Ombre.new(viewport, $game_player,self,@anglemin,@anglemax,@distancemax)
    end
    update
  end
  #--------------------------------------------------------------------------
  # ? ??????
  #--------------------------------------------------------------------------
  def update
    super
    # ??? ID?????????????????????????
    if @tile_id != @character.tile_id or
       @character_name != @character.character_name or
       @character_hue != @character.character_hue
      # ??? ID ????????????
      @tile_id = @character.tile_id
      @character_name = @character.character_name
      @character_hue = @character.character_hue
      # ??? ID ????????
      if @tile_id >= 384
        self.bitmap = RPG::Cache.tile($game_map.tileset_name,
          @tile_id, @character.character_hue)
        self.src_rect.set(0, 0, 32, 32)
        self.ox = 16
        self.oy = 32
      # ??? ID ????????
      else
        self.bitmap = RPG::Cache.character(@character.character_name,
          @character.character_hue)
        @cw = bitmap.width / 4
        @ch = bitmap.height / 4
        self.ox = @cw / 2
        self.oy = @ch
      end
    end
    # ???????
    self.visible = (not @character.transparent)
    # ????????????????
    if @tile_id == 0
      # ?????????
      sx = @character.pattern * @cw
      sy = (@character.direction - 2) / 2 * @ch
      self.src_rect.set(sx, sy, @cw, @ch)
    end
    # ???????????
    self.x = @character.screen_x
    self.y = @character.screen_y
    self.z = @character.screen_z(@ch)
    # ?????????????????
    self.opacity = @character.opacity
    self.blend_type = @character.blend_type
    self.bush_depth = @character.bush_depth
    # ???????
    if @character.animation_id != 0
      animation = $data_animations[@character.animation_id]
      animation(animation, true)
      @character.animation_id = 0
    end
    if @ombrelist!=[]
    for i in 1..@ombrelist.size
    if @ombrelist[i]!=nil
        @ombrelist[i].update
    end
    end
    end
  end
end


Puis créer un scrîpt Sprite_Ombre (juste en dessous du précédent par exemple):
Code : Tout sélectionner
#==============================================================================
# ¦ Sprite_Ombre
# Base par Genzai Kawakami, dynamisme par Rataime, améliorations par Boushy
#------------------------------------------------------------------------------
#  ??????????????????Game_Character ???????????
# ????????????????????????
#==============================================================================

class Sprite_Ombre < RPG::Sprite
  #--------------------------------------------------------------------------
  # ? ??????????
  #--------------------------------------------------------------------------
  attr_accessor :character                # ??????
  #--------------------------------------------------------------------------
  # ? ?????????
  #     viewport  : ??????
  #     character : ?????? (Game_Character)
  #--------------------------------------------------------------------------
  def initialize(viewport, character = nil,source = nil,anglemin=0,anglemax=0,distancemax=0)
    super(viewport)
    @anglemin=anglemin.to_f
    @anglemax=anglemax.to_f
    @distancemax=distancemax.to_f
    @character = character
    @source = source
    update
  end
  #--------------------------------------------------------------------------
  # ? ??????
  #--------------------------------------------------------------------------
  def update
    super
    # ??? ID?????????????????????????
    if @tile_id != @character.tile_id or
       @character_name != @character.character_name or
       @character_hue != @character.character_hue
      # ??? ID ????????????
      @tile_id = @character.tile_id
      @character_name = @character.character_name
      @character_hue = @character.character_hue
      # ??? ID ????????
      if @tile_id >= 384
        self.bitmap = RPG::Cache.tile($game_map.tileset_name,
          @tile_id, @character.character_hue)
        self.src_rect.set(0, 0, 32, 32)
        self.ox = 16
        self.oy = 32
      # ??? ID ????????
      else
        self.bitmap = RPG::Cache.character(@character.character_name,
          @character.character_hue)
        @cw = bitmap.width / 4
        @ch = bitmap.height / 4
        self.ox = @cw / 2
        self.oy = @ch
      end
    end
    # ???????
    self.visible = (not @character.transparent)
    # ????????????????
    if @tile_id == 0
      # ?????????
      sx = @character.pattern * @cw
     @direct=@character.direction
     
      if self.angle>90 or angle<-90
   
        if @direct== 6
               sy = ( 4- 2) / 2 * @ch#@character.direction
      end
      if @direct== 4
               sy = ( 6- 2) / 2 * @ch
        end
        if @direct != 4 and @direct !=6
        sy = (@character.direction - 2) / 2 * @ch
          end
        else
     sy = (@character.direction - 2) / 2 * @ch
     end
       self.src_rect.set(sx, sy, @cw, @ch)
    end
    # ???????????
    self.x = @character.screen_x
    self.y = @character.screen_y-5
    self.z = @character.screen_z(@ch)-1
    # ?????????????????
    self.opacity = @character.opacity
    self.blend_type = @character.blend_type
    self.bush_depth = @character.bush_depth
    # ???????
    if @character.animation_id != 0
      animation = $data_animations[@character.animation_id]
      animation(animation, true)
      @character.animation_id = 0
    end
    @deltax=@source.x-self.x
    @deltay= @source.y-self.y
    self.angle = 57.3*Math.atan2(@deltax, @deltay )
    @angle_trigo=self.angle+90
    if @angle_trigo<0
      @angle_trigo=360+@angle_trigo
    end
    self.color = Color.new(0, 0, 0)
    @distance = ((@deltax ** 2) + (@deltay ** 2))
    self.opacity = 1200000/(@distance+6000)
    @distance = @distance ** 0.5
    if @distancemax !=0 and @distance>=@distancemax
      self.opacity=0
    end
    if @anglemin !=0 or @anglemax !=0
       if @angle_trigo<@anglemin or @angle_trigo>@anglemax
         self.opacity=0
       end         
    end
  end
end


Le mode d'emploi est pas compliqué :
- Pour creer une source, mettez comme premiere ligne d'un event un commentaire avec la lettre s
- Pour ombrer un event, mettez comme premiere ligne de celui ci un commentaire avec la lettre o

D'après ce que j'ai vu, ça bouffe même pas trop de mémoire

NB : La version FR de RmXP contient une version buguée de la librairie du jeu (problèmes de superposition des events).
Solution : http://www.enterbrain.co.jp/tkool/rpgxp/RGSS100a.EXE à extraire et à rempacer dans c:\windows\system32 (ou \system pour les windows <XP). Vous devez fermer RmXP avant de remplacer le dll.
Au passage, c'est ce qui faisait que l'ombre foirait aux alentours de 180° dans la version originale

Reste à faire :
- retourner l'ombre du perso quand l'angle > +-90°. Si quelqu'un connait la commande...Parce que là l'ombre regarde dans le sens inverse du perso. Pas tres crédible !

Voilà, et que ça servent de leçon à ceux qui hésitent à se lancer dans le scripting : y'a 5 jours, je savais pas ce qu'était le Ruby icon_biggrin

Et encore merci à Genzai Kawakami pour l'idée originale !

EDIT : Version 1.1 !
Changelog :
- Sens de l'ombre fixée (boushy)
- Grosse amélioration de l'evolution de l'opacité en fonction de la distance (rataime
- Ajout d'angle min et max facultatifs, à spécifier dans un 2eme commentaire (min) et 3eme commentaire(max) (boushy)
Ces angles suivent le sens trigo en degré (pour les nuls : pareil qu'un rapporteur lu de droite à gauche)
- Ajout d'une distance max en 4eme commentaire pour faire disparaitre l'ombre. Distance en pixels (genre 500 ou 1000) (boushy)
- Quelques bug fixés (rataime)
Avatar de l’utilisateur
Amathlog
Modérateur
Modérateur
 
Message(s) : 1510
Inscription : 14 Jan 2007, 19:53
Meilleurs scores: 2

Retour vers Scripts (RGSS)

Qui est en ligne ?

Utilisateur(s) parcourant ce forum : Aucun utilisateur inscrit et 1 invité

cron