PDA

View Full Version : [Essentials script] Speech bubble message system v0.6


carmaniac
January 19th, 2013, 01:45 PM
If you've not ignored this thread post thinking, can't be that's a hoax, then you've over come your senses to check this out. Yes, this is basically a public release, which, hoping Maruno will add it into essentials as a default feature once everything is running smoothly. This is aimed to make your game feel that closer to the originals game freak loves teasing us with. Even though it's not styled like the original games ones, this gives a more direct look into showing events talking. As by default, the messages will only appear on the bottom, not got intention right now to add in arrows for that as it's too generalized for all the scripts. Anyway, enough of my rambling, time for the actual thread.

Conditions of use:
You can modify the script, I don't mind that.
You must give credits to me, otherwise I will hunt and bug you. (Note, link will be removed if I see people breaking conditions)
Cannot claim as your own, or redistribute anywhere else without my permission.

How to use:
To use the script, before each show text command, you will need to do a script call, depending on the type of message you would like to display you need to do pbCallBub(type, eventid) An example of how to use this script, would be pbCallBub(1,13) The first value is set to either 1 or 2. When it is 1, it shows up the floating bubble message, when it is 2, it will show up the arrow message. The second value, is the event ID that you want to show as talking. My eventID is 013, so we put 13. If you don't put this script call before the show text method, it will simply assume you want a normal message window, and will not show the arrow.

Examples:
http://i1004.photobucket.com/albums/af167/carmaniac94/1_zps954213f5.pnghttp://i1004.photobucket.com/albums/af167/carmaniac94/2_zpsd444d2a1.pnghttp://i1004.photobucket.com/albums/af167/carmaniac94/3_zpsd09eb853.png


Downloads:
http://pokemonessentials.wikia.com/wiki/Tutorial:Speech_bubbles V0.6

Arma
January 19th, 2013, 01:56 PM
Wow, never imagined you'd make this public.. I was thinking about asking you if you could let me use this for my game. XD Thanks a lot man! I'll give you some feedback once I fiddled with it for a bit. Maybe you can get Maruno to implement this in the next version of essentials. Oops, should've read the rest of the post before saying things like this. ^^;

Nintendork15
January 19th, 2013, 01:59 PM
Well, it's good thing I'm still using v11 then.
mainly because your other scripts are on there too

ppooookkkkkkk
January 19th, 2013, 02:28 PM
I tought you wrre going to keep it private.

Nintendork15
January 19th, 2013, 02:35 PM
I tought you wrre going to keep it private.

http://lostsoulsdev.deviantart.com/journal/I-ve-been-thinking-349070365

He wrote this yesterday saying how he was considering giving it to public use.

ppooookkkkkkk
January 19th, 2013, 02:48 PM
If you've not ignored this thread post thinking, can't be that's a hoax, then you've over come your senses to check this out. Yes, this is basically a public release, which, hoping Maruno will add it into essentials as a default feature once everything is running smoothly. This is aimed to make your game feel that closer to the originals game freak loves teasing us with. Even though it's not styled like the original games ones, this gives a more direct look into showing events talking. As by default, the messages will only appear on the bottom, not got intention right now to add in arrows for that as it's too generalized for all the scripts. Anyway, enough of my rambling, time for the actual thread.

Conditions of use:
You can modify the script, I don't mind that.
You must give credits to me, otherwise I will hunt and bug you. (Note, link will be removed if I see people breaking conditions)
Cannot claim as your own, or redistribute anywhere else without my permission.

How to use:
Simply do a script call before each message you would like to appear as a bubble like this; pbCallBub(true, eventid)
The eventid is the value listed at the top of the event page, example would be, the event ID is 001, so you would do pbCallBub(true, 1) this will direct the bubble to the screen position of event 1. The bubble will correct itself if it is going off screen. If you do not do the call, the script will assume you want the normal message window, and will display the message at the bottom of the screen.

Examples:
If video doesn't work use this: http://www.youtube.com/watch?v=3zC6n3QkWlM
http://www.youtube.com/watch?v=3zC6n3QkWlM
http://i1004.photobucket.com/albums/af167/carmaniac94/BubbleMessage_zpscc1f5fb5.png


It given an error at the start: ---------------------------
Pokemon Essentials
---------------------------
Exception: NoMethodError
Message: undefined method `events' for nil:NilClass
Interpreter:542:in `get_character'
PokemonMessages*:1211:in `pbRepositionMessageWindow'
PokemonMessages*:1499:in `pbMessageDisplay'
PokemonMessages*:1019:in `pbMessage'
PokemonLoad:156:in `install'
PokemonLoad:289:in `pbStartLoadScreen'
DebugIntro:6:in `main'
Main:37:in `mainFunctionDebug'
Main:15:in `mainFunction'
Main:15:in `pbCriticalCode'

This exception was logged in
C:\Users\M.ahmad\Saved Games/Pokemon Essentials/errorlog.txt.
Press Ctrl+C to copy this message to the clipboard.
---------------------------
OK
---------------------------

Nintendork15
January 19th, 2013, 02:51 PM
It given an error at the start: ---------------------------
Pokemon Essentials
---------------------------
Exception: NoMethodError
Message: undefined method `events' for nil:NilClass
Interpreter:542:in `get_character'
PokemonMessages*:1211:in `pbRepositionMessageWindow'
PokemonMessages*:1499:in `pbMessageDisplay'
PokemonMessages*:1019:in `pbMessage'
PokemonLoad:156:in `install'
PokemonLoad:289:in `pbStartLoadScreen'
DebugIntro:6:in `main'
Main:37:in `mainFunctionDebug'
Main:15:in `mainFunction'
Main:15:in `pbCriticalCode'

This exception was logged in
C:\Users\M.ahmad\Saved Games/Pokemon Essentials/errorlog.txt.
Press Ctrl+C to copy this message to the clipboard.
---------------------------
OK
---------------------------

Huh, I don't get this message.


---------------------
It would be nice if there was a install tutorial

ppooookkkkkkk
January 19th, 2013, 03:00 PM
I'll try redownloading :\

~JV~
January 19th, 2013, 03:03 PM
Really nice job man, glad to see you decided to release this to the public :).

Arma
January 19th, 2013, 03:04 PM
I'll try redownloading :\
I don't think that's the issue, have you tried starting a new game instead?

carmaniac
January 19th, 2013, 03:07 PM
Huh, I don't get this message.


---------------------
It would be nice if there was a install tutorial

I will provide an install tutorial tomorrow, it was mostly released like this as it's not that user friendly to get correct. Also anyone getting an error to the 'events' method, remove your game save.

ppooookkkkkkk
January 19th, 2013, 03:13 PM
i did it still gives error.

Cilerba
January 19th, 2013, 03:17 PM
Fixed your YouTube video for ya.

Script looks good. I might just use this in Auburn hmm..

carmaniac
January 19th, 2013, 03:22 PM
For those getting an error on the 'events' update the PokemonMessages script with this version:
Not available.

Also will be updating the download link for the entire kit:
Not available.

Thank you Cilerba.

ppooookkkkkkk
January 19th, 2013, 03:38 PM
For those getting an error on the 'events' update the PokemonMessages script with this version:


Thank you Cilerba.
Thanks sir i'll surely use your work.

carmaniac
January 19th, 2013, 04:29 PM
Just created an install guide for those who want to use the script outside of the compiled kit.
Not available.

zingzags
January 19th, 2013, 10:19 PM
Well well now Ryan, It seems to look good. I haven't used or seen the script though; So what did you do? Make a method to define which event it should look for? Then depending on the position of the screen it will either be above, or under the event?

Luka S.J.
January 20th, 2013, 12:21 AM
EDIT: My bad, never mind.

carmaniac
January 20th, 2013, 07:47 AM
No. It gets the event and player map positions, and calculates the distance between them. Then it converts them to pixels instead of coordinates and repositions the value from the center of the screen. Having free roaming bubbles anywhere on the screen, no matter where the event is. (courtesy of moi)

It doesn't use that code anymore XD, pretty sure I notified you of this a while back. It just gets the screen position of the event instead of the map position, meaning no more dodgy bubble positions on screen when the map has been scrolled via an event.

Luka S.J.
January 20th, 2013, 08:46 AM
It doesn't use that code anymore XD, pretty sure I notified you of this a while back. It just gets the screen position of the event instead of the map position, meaning no more dodgy bubble positions on screen when the map has been scrolled via an event.

Lol, I looked through our chat history. You did mention something like that. Hahaha, I feel stupid.

carmaniac
January 22nd, 2013, 02:51 PM
Can everyone please update to the latest version as there were some slight issues with the previous one, thank you.

ppooookkkkkkk
January 22nd, 2013, 03:37 PM
I give you a suggestion. In the next update add the Anger speech bubble!

Mortalis
January 22nd, 2013, 07:49 PM
carmaniac, you are a beautiful person. Thanks for this!

Quick question: Is it possible to force the message box to the bottom of the screen? During my game's opening event, the player is facing NPCs who are at the top of the screen while the player is at the bottom, yet the message box is covering them when they talk. When I use value 1 for the first input [ pbCallBub (1, eventid) ], it goes off the screen and can't be read.

carmaniac
January 22nd, 2013, 10:43 PM
My bad, forgot about when events are at the top of the screen with the player being at the bottom facing up XD. I'll have that fixed once I'm home.

oldsnake90
January 23rd, 2013, 10:00 AM
i put it in the game but its not working. It works if i have the old Pokemonmessages script from your last update. but it wont now. :\ idk if i did something wrong

Kaito123
January 24th, 2013, 12:57 AM
i put it in the game but its not working. It works if i have the old Pokemonmessages script from your last update. but it wont now. :\ idk if i did something wrong

you must chance a few scripts too :)
at the first post is one link to the wikia, there are a introduction for it :)

and in the new scriot in the .txt (in the comments) is a introduction too :D


That System is very nice :D

Rayd12smitty
January 24th, 2013, 06:59 PM
Alright Carmaniac. This is awesome. I will definitely use and credit. I think I have a bug or two though. I'm pretty sure one was reported, but I have screens.

http://i.imgur.com/VizoOsq.pnghttp://i.imgur.com/sC79Oaj.png


If it isn't obvious, in the first one, the arrow thing leading to the bubble isn't long enough/too long? Anyway it goes off the screen. In the second one (I think it was reported before) The bubble covers the sprite who is talking. It should go down.

Anyway, awesome script. I hope you have time to fix these few bugs

Mortalis
January 29th, 2013, 01:32 PM
Alright Carmaniac. This is awesome. I will definitely use and credit. I think I have a bug or two though. I'm pretty sure one was reported, but I have screens.

http://i.imgur.com/VizoOsq.pnghttp://i.imgur.com/sC79Oaj.png


If it isn't obvious, in the first one, the arrow thing leading to the bubble isn't long enough/too long? Anyway it goes off the screen. In the second one (I think it was reported before) The bubble covers the sprite who is talking. It should go down.

Anyway, awesome script. I hope you have time to fix these few bugs

The problem with the second image is that the script usually calls itself nearest to the event to make the line shorter so it's not always blocking other things in the environment and such. At least that's how it's worked out for me every time I've used it.

I believe carmaniac said he was going to fix it soon, but for now the only solution is to switch around the events so that your player is facing downward at the event. That, or you can use scroll map to center on the event so this problem doesn't occur. The scroll map looks natural any ways if you put it at the start of the event, but you might be able to place it somewhere else.

For now you'll just have to find a quick fix for it before carmaniac releases the new version.

Charly Um
April 3rd, 2013, 10:54 AM
Thanks works perfectly: D

pokemonmercury
July 20th, 2013, 04:02 PM
Im getting this error...
Im using Essential 12.1
---------------------------
Pokemon Essentials
---------------------------
Exception: NameError
Message: uninitialized constant MessageConfig::BUBBLETEXTBASE
PokemonMessages:1195:in `getSkinColor'
PokemonMessages:1420:in `pbMessageDisplay'
PokemonMessages:1031:in `pbMessage'
PokemonMessages:675:in `command_101'
Interpreter:304:in `execute_command'
Interpreter:193:in `update'
Interpreter:106:in `loop'
Interpreter:198:in `update'
Scene_Map:103:in `update'
Scene_Map:101:in `loop'

carmaniac
July 21st, 2013, 04:43 AM
Im getting this error...
Im using Essential 12.1
---------------------------
Pokemon Essentials
---------------------------
Exception: NameError
Message: uninitialized constant MessageConfig::BUBBLETEXTBASE
PokemonMessages:1195:in `getSkinColor'
PokemonMessages:1420:in `pbMessageDisplay'
PokemonMessages:1031:in `pbMessage'
PokemonMessages:675:in `command_101'
Interpreter:304:in `execute_command'
Interpreter:193:in `update'
Interpreter:106:in `loop'
Interpreter:198:in `update'
Scene_Map:103:in `update'
Scene_Map:101:in `loop'

My guess is you completely ignored the first part of the tutorial to install this.
http://pokemonessentials.wikia.com/wiki/Tutorial:Speech_bubbles

lauerolus
July 22nd, 2013, 06:08 AM
I love this, such a simple thing makes NPC so much more interactive. Thanks for sharing it.

I have a problem though. Setting "2" works as intended, but setting "1" throws the text bubble offscreen.http://img.ctrlv.in/img/51ed3a69d1a7d.jpg

Worldslayer608
November 13th, 2013, 01:20 PM
Any updates on this carmaniac?

carmaniac
November 13th, 2013, 02:09 PM
Any updates on this carmaniac?

In all honesty I forgot I even released this system. I'll likely update the system when V13 of essentials is released to save time on updating it for two versions. Will mainly be bug fixes and a change in the call method to be shorter than what it already is to use just normal commands within messages.

Worldslayer608
November 13th, 2013, 02:38 PM
Sweet, I look forward to it.

theRiolvile2
March 1st, 2014, 03:59 AM
Mine work is there also a shout bubble when someone is shouting

Dylanrockin
March 15th, 2014, 01:40 PM
I was just wondering how you would use this for your player character. Would it still just be \PN? Or is it some kind of number that I am not seeing.

joeyhugg
March 15th, 2014, 07:12 PM
I was just wondering how you would use this for your player character. Would it still just be \PN? Or is it some kind of number that I am not seeing.

I know in RPG Maker VX Ace, when referring to the player as an Event ID, you use either 0/-1, try that.

TheWanap
May 28th, 2014, 04:31 AM
So, I downloaded Carmaniac's Pokemon Essentials Speech Bubbles script (http://pokemonessentials.wikia.com/wiki/Tutorial:Speech_bubbles), and installed it.
It works fine, but I wanted to make that more personal, so I edited it a bit.
I think this is very easy to solve with changing some things in the script, but I don't know how to do that.

This is what I did:

(the original Windowskin looks like this: http://i.imgur.com/ekmELb8.png
I edited that "frlgtextskin" Windowsskin, like this:
http://i.imgur.com/dMRyUCi.png.

So I took some useless space out of it, and it still works fine - almost. I took a picture of it when you play it and it looks like this:
http://i.imgur.com/2rMOjpf.png

So that arrow doesn't reach that text box (or Windowskin). I tried to move that arrow down (with photoshop), but the same problem exist.
There might be an priority with that Windowskin, so how could I fix it?

Here is the script: class Game_Temp
attr_writer :message_window_showing
attr_writer :player_transferring
attr_writer :transition_processing

def message_window_showing
@message_window_showing=false if !@message_window_showing
return @message_window_showing
end

def player_transferring
@player_transferring=false if !@player_transferring
return @player_transferring
end

def transition_processing
@transition_processing=false if !@transition_processing
return @transition_processing
end
end



class Game_Message
attr_writer :background, :visible
def visible; return @visible ? @visible : false; end
def background; return @background ? @background : 0; end
end



class Game_System
attr_writer :message_position

def message_position
@message_position=2 if !@message_position
return @message_position
end
end



#########

class Scene_Map
def updatemini
oldmws=$game_temp.message_window_showing
oldvis=$game_message ? $game_message.visible : false
$game_temp.message_window_showing=true
$game_message.visible=true if $game_message
loop do
$game_map.update
$game_player.update
$game_system.update
if $game_screen
$game_screen.update
else
$game_map.screen.update
end
unless $game_temp.player_transferring
break
end
transfer_player
if $game_temp.transition_processing
break
end
end
$game_temp.message_window_showing=oldmws
$game_message.visible=oldvis if $game_message
@spriteset.update if @spriteset
@message_window.update if @message_window
end
end



class Scene_Battle
def updatemini
if self.respond_to?("update_basic")
update_basic(true)
update_info_viewport # Update information viewport
if $game_message && $game_message.visible
@info_viewport.visible = false
@message_window.visible = true
end
else
oldmws=$game_temp.message_window_showing
$game_temp.message_window_showing=true
# Update system (timer) and screen
$game_system.update
if $game_screen
$game_screen.update
else
$game_map.screen.update
end
# If timer has reached 0
if $game_system.timer_working and $game_system.timer == 0
# Abort battle
$game_temp.battle_abort = true
end
# Update windows
@help_window.update if @help_window
@party_command_window.update if @party_command_window
@actor_command_window.update if @actor_command_window
@status_window.update if @status_window
$game_temp.message_window_showing=oldmws
@message_window.update if @message_window
# Update sprite set
@spriteset.update if @spriteset
end
end
end



def pbMapInterpreterRunning?
interp=pbMapInterpreter
return interp && interp.running?
end

def pbMapInterpreter
if $game_map && $game_map.respond_to?("interpreter")
return $game_map.interpreter
elsif $game_system
return $game_system.map_interpreter
end
return nil
end

def pbRefreshSceneMap
if $scene && $scene.is_a?(Scene_Map)
if $scene.respond_to?("miniupdate")
$scene.miniupdate
else
$scene.updatemini
end
elsif $scene && $scene.is_a?(Scene_Battle)
$scene.updatemini
end
end

def pbUpdateSceneMap
if $scene && $scene.is_a?(Scene_Map) && !pbIsFaded?
if $scene.respond_to?("miniupdate")
$scene.miniupdate
else
$scene.updatemini
end
elsif $scene && $scene.is_a?(Scene_Battle)
$scene.updatemini
end
end
#########

def pbCsvField!(str)
ret=""
str.sub!(/\A\s*/,"")
if str[0,1]=="\""
str[0,1]=""
escaped=false
fieldbytes=0
str.scan(/./) do |s|
fieldbytes+=s.length
break if s=="\"" && !escaped
if s=="\\" && !escaped
escaped=true
else
ret+=s
escaped=false
end
end
str[0,fieldbytes]=""
if !str[/\A\s*,/] && !str[/\A\s*$/]
raise _INTL("Invalid quoted field (in: {1})",ret)
end
str[0,str.length]=$~.post_match
else
if str[/,/]
str[0,str.length]=$~.post_match
ret=$~.pre_match
else
ret=str.clone
str[0,str.length]=""
end
ret.gsub!(/\s+$/,"")
end
return ret
end

def pbCsvPosInt!(str)
ret=pbCsvField!(str)
if !ret[/\A\d+$/]
raise _INTL("Field {1} is not a positive integer",ret)
end
return ret.to_i
end

def pbEventCommentInput(*args)
parameters = []
list = *args[0].list # Event or event page
elements = *args[1] # Number of elements
trigger = *args[2] # Trigger
return nil if list == nil
return nil unless list.is_a?(Array)
for item in list
next unless item.code == 108 || item.code == 408
if item.parameters[0] == trigger
start = list.index(item) + 1
finish = start + elements
for id in start...finish
next if !list[id]
parameters.push(list[id].parameters[0])
end
return parameters
end
end
return nil
end

# Gets the value of a variable.
def pbGet(id)
return 0 if !id || !$game_variables
return $game_variables[id]
end

# Sets the value of a variable.
def pbSet(id,value)
if id && id>=0
$game_variables[id]=value if $game_variables
$game_map.need_refresh = true if $game_map
end
end

def pbCurrentEventCommentInput(elements,trigger)
return nil if !pbMapInterpreterRunning?
event=pbMapInterpreter.get_character(0)
return nil if !event
return pbEventCommentInput(event,elements,trigger)
end



module InterpreterMixin
def pbGlobalLock # Freezes all events on the map (for use at the beginning of common events)
for event in $game_map.events.values
event.minilock
end
end

def pbGlobalUnlock # Unfreezes all events on the map (for use at the end of common events)
for event in $game_map.events.values
event.unlock
end
end

def pbRepeatAbove(index)
index=@list[index].indent
loop do
index-=1
if @list[index].indent==indent
return index+1
end
end
end

def pbBreakLoop(index)
indent = @list[index].indent
temp_index=index
# Copy index to temporary variables
loop do
# Advance index
temp_index += 1
# If a fitting loop was not found
if temp_index >= @list.size-1
return index+1
end
if @list[temp_index].code == 413 and @list[temp_index].indent < indent
return temp_index+1
end
end
end

def pbJumpToLabel(index,label_name)
temp_index = 0
loop do
if temp_index >= @list.size-1
return index+1
end
if @list[temp_index].code == 118 and
@list[temp_index].parameters[0] == label_name
return temp_index+1
end
temp_index += 1
end
end

# Gets the next index in the interpreter, ignoring
# certain events between messages
def pbNextIndex(index)
return -1 if !@list || @list.length==0
i=index+1
loop do
if i>=@list.length-1
return i
end
code=@list[i].code
case code
when 118, 108, 408 # Label, Comment
i+=1
when 413 # Repeat Above
i=pbRepeatAbove(i)
when 113 # Break Loop
i=pbBreakLoop(i)
when 119 # Jump to Label
newI=pbJumpToLabel(i,@list[i].parameters[0])
if newI>i
i=newI
else
i+=1
end
else
return i
end
end
end

# Helper function that shows a picture in a script. To be used in
# a script event command.
def pbShowPicture(number,name,origin,x,y,zoomX=100,zoomY=100,opacity=255,blendType=0)
number = number + ($game_temp.in_battle ? 50 : 0)
$game_screen.pictures[number].show(name,origin,
x, y, zoomX,zoomY,opacity,blendType)
end

# Erases an event and adds it to the list of erased events so that
# it can stay erased when the game is saved then loaded again. To be used in
# a script event command.
def pbEraseThisEvent
if $game_map.events[@event_id]
$game_map.events[@event_id].erase
$PokemonMap.addErasedEvent(@event_id) if $PokemonMap
end
@index+=1
return true
end

# Runs a common event. To be used in a script event command.
def pbCommonEvent(id)
if $game_temp.in_battle
$game_temp.common_event_id = id
else
commonEvent = $data_common_events[id]
$game_system.battle_interpreter.setup(commonEvent.list, 0)
end
end

# Sets another event's self switch (eg. pbSetSelfSwitch(20,"A",true) ).
# To be used in a script event command.
def pbSetSelfSwitch(event,swtch,value)
$game_self_switches[[@map_id,event,swtch]]=value
$game_map.need_refresh = true
end

# Must use this approach to share the methods because the methods already
# defined in a class override those defined in an included module
CustomEventCommands=<<_END_

def command_242
pbBGMFade(pbParams[0])
return true
end

def command_246
pbBGSFade(pbParams[0])
return true
end

def command_251
pbSEStop()
return true
end

def command_241
pbBGMPlay(pbParams[0])
return true
end

def command_245
pbBGSPlay(pbParams[0])
return true
end

def command_249
pbMEPlay(pbParams[0])
return true
end

def command_250
pbSEPlay(pbParams[0])
return true
end
_END_
end



def pbButtonInputProcessing(variableNumber=0,timeoutFrames=0)
ret=0
loop do
Graphics.update
Input.update
pbUpdateSceneMap
for i in 1..18
if Input.trigger?(i)
ret=i
end
end
break if ret!=0
if timeoutFrames && timeoutFrames>0
i+=1
break if i>=timeoutFrames
end
end
Input.update
if variableNumber && variableNumber>0
$game_variables[variableNumber]=ret
$game_map.need_refresh = true if $game_map
end
return ret
end



class Game_Temp
attr_accessor :background
end



class Game_Interpreter
include InterpreterMixin
eval(InterpreterMixin::CustomEventCommands)
@@immediateDisplayAfterWait=false
@buttonInput=false

def pbParams
return @params
end

def command_105
return false if @buttonInput
@buttonInput=true
pbButtonInputProcessing(@list[@index].parameters[0])
@buttonInput=false
@index+=1
return true
end

def command_101
if $game_temp.message_window_showing
return false
end
$game_message=Game_Message.new if !$game_message
message=""
commands=nil
numInputVar=nil
numInputDigitsMax=nil
text=""
facename=@list[@index].parameters[0]
faceindex=@list[@index].parameters[1]
if facename && facename!=""
text+="\\ff[#{facename},#{faceindex}]"
end
if $game_message
$game_message.background=@list[@index].parameters[2]
end
$game_system.message_position=@list[@index].parameters[3]
message+=text
messageend=""
loop do
nextIndex=pbNextIndex(@index)
code=@list[nextIndex].code
if code == 401
text=@list[nextIndex].parameters[0]
text+=" " if text!="" && text[text.length-1,1]!=" "
message+=text
@index=nextIndex
else
if code == 102
commands=@list[nextIndex].parameters
@index=nextIndex
elsif code == 106 && @@immediateDisplayAfterWait
params=@list[nextIndex].parameters
if params[0]<=10
nextcode=@list[nextIndex+1].code
if nextcode==101||nextcode==102||nextcode==103
@index=nextIndex
else
break
end
else
break
end
elsif code == 103
numInputVar=@list[nextIndex].parameters[0]
numInputDigitsMax=@list[nextIndex].parameters[1]
@index=nextIndex
elsif code == 101
messageend="\1"
end
break
end
end
message=_MAPINTL($game_map.map_id,message)
@message_waiting=true
if commands
cmdlist=[]
for cmd in commands[0]
cmdlist.push(_MAPINTL($game_map.map_id,cmd))
end
command=Kernel.pbMessage(message+messageend,cmdlist,commands[1])
@branch[@list[@index].indent] = command
elsif numInputVar
params=ChooseNumberParams.new
params.setMaxDigits(numInputDigitsMax)
params.setDefaultValue($game_variables[numInputVar])
$game_variables[numInputVar]=Kernel.pbMessageChooseNumber(message+messageend,params)
$game_map.need_refresh = true if $game_map
else
Kernel.pbMessage(message+messageend)
end
@message_waiting=false
return true
end

def command_102
@message_waiting=true
command=Kernel.pbShowCommands(nil,@list[@index].parameters[0],@list[@index].parameters[1])
@message_waiting=false
@branch[@list[@index].indent] = command
Input.update # Must call Input.update again to avoid extra triggers
return true
end

def command_103
varnumber=@list[@index].parameters[0]
@message_waiting=true
params=ChooseNumberParams.new
params.setMaxDigits(@list[@index].parameters[1])
params.setDefaultValue($game_variables[varnumber])
$game_variables[varnumber]=Kernel.pbChooseNumber(nil,params)
$game_map.need_refresh = true if $game_map
@message_waiting=false
return true
end
end



class Interpreter
include InterpreterMixin
eval(InterpreterMixin::CustomEventCommands)
@@immediateDisplayAfterWait=false
@buttonInput=false

def pbParams
return @parameters
end

def command_105
return false if @buttonInput
@buttonInput=true
pbButtonInputProcessing(@list[@index].parameters[0])
@buttonInput=false
@index+=1
return true
end

def command_101
if $game_temp.message_window_showing
return false
end
message=""
commands=nil
numInputVar=nil
numInputDigitsMax=nil
text=""
firstText=nil
if @list[@index].parameters.length==1
text+=@list[@index].parameters[0]
firstText=@list[@index].parameters[0]
text+=" " if text[text.length-1,1]!=" "
message+=text
else
facename=@list[@index].parameters[0]
faceindex=@list[@index].parameters[1]
if facename && facename!=""
text+="\\ff[#{facename},#{faceindex}]"
message+=text
end
end
messageend=""
loop do
nextIndex=pbNextIndex(@index)
code=@list[nextIndex].code
if code == 401
text=@list[nextIndex].parameters[0]
text+=" " if text[text.length-1,1]!=" "
message+=text
@index=nextIndex
else
if code == 102
commands=@list[nextIndex].parameters
@index=nextIndex
elsif code == 106 && @@immediateDisplayAfterWait
params=@list[nextIndex].parameters
if params[0]<=10
nextcode=@list[nextIndex+1].code
if nextcode==101||nextcode==102||nextcode==103
@index=nextIndex
else
break
end
else
break
end
elsif code == 103
numInputVar=@list[nextIndex].parameters[0]
numInputDigitsMax=@list[nextIndex].parameters[1]
@index=nextIndex
elsif code == 101
if @list[@index].parameters.length==1
text=@list[@index].parameters[0]
if text[/\A\\ignr/] && text==firstText
text+=" " if text[text.length-1,1]!=" "
message+=text
@index=nextIndex
continue
end
end
messageend="\1"
end
break
end
end
@message_waiting=true # needed to allow parallel process events to work while
# a message is displayed
message=_MAPINTL($game_map.map_id,message)
if commands
cmdlist=[]
for cmd in commands[0]
cmdlist.push(_MAPINTL($game_map.map_id,cmd))
end
command=Kernel.pbMessage(message+messageend,cmdlist,commands[1])
@branch[@list[@index].indent] = command
elsif numInputVar
params=ChooseNumberParams.new
params.setMaxDigits(numInputDigitsMax)
params.setDefaultValue($game_variables[numInputVar])
$game_variables[numInputVar]=Kernel.pbMessageChooseNumber(message+messageend,params)
$game_map.need_refresh = true if $game_map
else
Kernel.pbMessage(message+messageend,nil)
end
@message_waiting=false
return true
end

def command_102
@message_waiting=true
command=Kernel.pbShowCommands(nil,@list[@index].parameters[0],@list[@index].parameters[1])
@message_waiting=false
@branch[@list[@index].indent] = command
Input.update # Must call Input.update again to avoid extra triggers
return true
end

def command_103
varnumber=@list[@index].parameters[0]
@message_waiting=true
params=ChooseNumberParams.new
params.setMaxDigits(@list[@index].parameters[1])
params.setDefaultValue($game_variables[varnumber])
$game_variables[varnumber]=Kernel.pbChooseNumber(nil,params)
$game_map.need_refresh = true if $game_map
@message_waiting=false
return true
end
end



class ChooseNumberParams
def initialize
@maxDigits=0
@minNumber=0
@maxNumber=0
@skin=nil
@messageSkin=nil
@negativesAllowed=false
@initialNumber=0
@cancelNumber=nil
end

def setMessageSkin(value)
@messageSkin=value
end

def messageSkin # Set the full path for the message's window skin
@messageSkin
end

def setSkin(value)
@skin=value
end

def skin
@skin
end

def setNegativesAllowed(value)
@negativeAllowed=value
end

def negativesAllowed
@negativeAllowed ? true : false
end

def setRange(minNumber,maxNumber)
maxNumber=minNumber if minNumber>maxNumber
@maxDigits=0
@minNumber=minNumber
@maxNumber=maxNumber
end

def setDefaultValue(number)
@initialNumber=number
@cancelNumber=nil
end

def setInitialValue(number)
@initialNumber=number
end

def setCancelValue(number)
@cancelNumber=number
end

def initialNumber
return clamp(@initialNumber,self.minNumber,self.maxNumber)
end

def cancelNumber
return @cancelNumber ? @cancelNumber : self.initialNumber
end

def minNumber
ret=0
if @maxDigits>0
ret=-((10**@maxDigits)-1)
elsif
ret=@minNumber
end
ret=0 if !@negativeAllowed && ret<0
return ret
end

def maxNumber
ret=0
if @maxDigits>0
ret=((10**@maxDigits)-1)
elsif
ret=@maxNumber
end
ret=0 if !@negativeAllowed && ret<0
return ret
end

def setMaxDigits(value)
@maxDigits=[1,value].max
end

def maxDigits
if @maxDigits>0
return @maxDigits
else
return [numDigits(self.minNumber),numDigits(self.maxNumber)].max
end
end

private

def clamp(v,mn,mx)
return v<mn ? mn : (v>mx ? mx : v)
end

def numDigits(number)
ans = 1
number=number.abs
while number >= 10
ans+=1
number/=10
end
return ans
end
end



def pbChooseNumber(msgwindow,params)
return 0 if !params
ret=0
maximum=params.maxNumber
minimum=params.minNumber
defaultNumber=params.initialNumber
cancelNumber=params.cancelNumber
cmdwindow=Window_InputNumberPokemon.new(params.maxDigits)
cmdwindow.z=99999
cmdwindow.visible=true
cmdwindow.setSkin(params.skin) if params.skin
cmdwindow.sign=params.negativesAllowed # must be set before number
cmdwindow.number=defaultNumber
curnumber=defaultNumber
pbPositionNearMsgWindow(cmdwindow,msgwindow,:right)
command=0
loop do
Graphics.update
Input.update
pbUpdateSceneMap
cmdwindow.update
msgwindow.update if msgwindow
yield if block_given?
if Input.trigger?(Input::C)
ret=cmdwindow.number
if ret>maximum
pbPlayBuzzerSE()
elsif ret<minimum
pbPlayBuzzerSE()
else
pbPlayDecisionSE()
break
end
elsif Input.trigger?(Input::B)
pbPlayCancelSE()
ret=cancelNumber
break
end
end
cmdwindow.dispose
Input.update
return ret
end

def Kernel.pbShowCommandsWithHelp(msgwindow,commands,help,cmdIfCancel=0,defaultCmd=0)
msgwin=msgwindow
if !msgwindow
msgwin=Kernel.pbCreateMessageWindow(nil)
end
oldlbl=msgwin.letterbyletter
msgwin.letterbyletter=false
if commands
cmdwindow=Window_CommandPokemonEx.new(commands)
cmdwindow.z=99999
cmdwindow.visible=true
cmdwindow.resizeToFit(cmdwindow.commands)
cmdwindow.height=msgwin.y if cmdwindow.height>msgwin.y
cmdwindow.index=defaultCmd
command=0
msgwin.text=help[cmdwindow.index]
msgwin.width=msgwin.width # Necessary evil to make it use the proper margins.
loop do
Graphics.update
Input.update
oldindex=cmdwindow.index
cmdwindow.update
if oldindex!=cmdwindow.index
msgwin.text=help[cmdwindow.index]
end
msgwin.update
yield if block_given?
if Input.trigger?(Input::B)
if cmdIfCancel>0
command=cmdIfCancel-1
break
elsif cmdIfCancel<0
command=cmdIfCancel
break
end
end
if Input.trigger?(Input::C)
command=cmdwindow.index
break
end
pbUpdateSceneMap
end
ret=command
cmdwindow.dispose
Input.update
end
msgwin.letterbyletter=oldlbl
if !msgwindow
msgwin.dispose
end
return ret
end

def Kernel.pbShowCommands(msgwindow,commands=nil,cmdIfCancel=0,defaultCmd=0)
ret=0
if commands
cmdwindow=Window_CommandPokemonEx.new(commands)
cmdwindow.z=99999
cmdwindow.visible=true
cmdwindow.resizeToFit(cmdwindow.commands)
pbPositionNearMsgWindow(cmdwindow,msgwindow,:right)
cmdwindow.index=defaultCmd
command=0
loop do
Graphics.update
Input.update
cmdwindow.update
msgwindow.update if msgwindow
yield if block_given?
if Input.trigger?(Input::B)
if cmdIfCancel>0
command=cmdIfCancel-1
break
elsif cmdIfCancel<0
command=cmdIfCancel
break
end
end
if Input.trigger?(Input::C)
command=cmdwindow.index
break
end
pbUpdateSceneMap
end
ret=command
cmdwindow.dispose
Input.update
end
return ret
end

def pbPositionFaceWindow(facewindow,msgwindow)
return if !facewindow
if msgwindow
if facewindow.height<=msgwindow.height
facewindow.y=msgwindow.y
else
facewindow.y=msgwindow.y+msgwindow.height-facewindow.height
end
facewindow.x=Graphics.width-facewindow.width
msgwindow.x=0
msgwindow.width=Graphics.width-facewindow.width
else
facewindow.height=Graphics.height if facewindow.height>Graphics.height
facewindow.x=0
facewindow.y=0
end
end

def pbPositionNearMsgWindow(cmdwindow,msgwindow,side)
return if !cmdwindow
if msgwindow
height=[cmdwindow.height,Graphics.height-msgwindow.height].min
if cmdwindow.height!=height
cmdwindow.height=height
end
cmdwindow.y=msgwindow.y-cmdwindow.height
if cmdwindow.y<0
cmdwindow.y=msgwindow.y+msgwindow.height
if cmdwindow.y+cmdwindow.height>Graphics.height
cmdwindow.y=msgwindow.y-cmdwindow.height
end
end
case side
when :left
cmdwindow.x=msgwindow.x
when :right
cmdwindow.x=msgwindow.x+msgwindow.width-cmdwindow.width
else
cmdwindow.x=msgwindow.x+msgwindow.width-cmdwindow.width
end
else
cmdwindow.height=Graphics.height if cmdwindow.height>Graphics.height
cmdwindow.x=0
cmdwindow.y=0
end
end

def pbGetBasicMapNameFromId(id)
begin
map = pbLoadRxData("Data/MapInfos")
return "" if !map
return map[id].name
rescue
return ""
end
end

def pbGetMapNameFromId(id)
map=pbGetBasicMapNameFromId(id)
if $Trainer
map.gsub!(/\\PN/,$Trainer.name)
end
return map
end

def Kernel.pbMessage(message,commands=nil,cmdIfCancel=0,skin=nil,defaultCmd=0,&block)
ret=0
msgwindow=Kernel.pbCreateMessageWindow(nil,skin)
if commands
ret=Kernel.pbMessageDisplay(msgwindow,message,true,
proc {|msgwindow|
next Kernel.pbShowCommands(msgwindow,commands,cmdIfCancel,defaultCmd,&block)
},&block)
else
Kernel.pbMessageDisplay(msgwindow,message,&block)
end
Kernel.pbDisposeMessageWindow(msgwindow)
Input.update
return ret
end

def Kernel.pbMessageChooseNumber(message,params,&block)
msgwindow=Kernel.pbCreateMessageWindow(nil,params.messageSkin)
ret=Kernel.pbMessageDisplay(msgwindow,message,true,
proc {|msgwindow|
next Kernel.pbChooseNumber(msgwindow,params,&block)
},&block)
Kernel.pbDisposeMessageWindow(msgwindow)
return ret
end

def Kernel.pbConfirmMessage(message,&block)
return (Kernel.pbMessage(message,[_INTL("Yes"),_INTL("No")],2,&block)==0)
end

def Kernel.pbConfirmMessageSerious(message,&block)
return (Kernel.pbMessage(message,[_INTL("No"),_INTL("Yes")],1,&block)==1)
end

def Kernel.pbCreateStatusWindow(viewport=nil)
msgwindow=Window_AdvancedTextPokemon.new("")
if !viewport
msgwindow.z=99999
else
msgwindow.viewport=viewport
end
msgwindow.visible=false
msgwindow.letterbyletter=false
pbBottomLeftLines(msgwindow,2)
skinfile=MessageConfig.pbGetSpeechFrame()
msgwindow.setSkin(skinfile)
return msgwindow
end

def Kernel.pbCreateMessageWindow(viewport=nil,skin=nil)
if $Bubble==2 # Message window set to floating bubble.
if $game_player.direction==8 # Player facing up, message window top.
@Restriction = Viewport.new(0, 104, Graphics.width, 280)
@Restriction.z = 999999
@Arrow = Sprite.new(@Restriction)
@Arrow.x = $game_map.events[$talkingEvent].screen_x - Graphics.width
@Arrow.y = ($game_map.events[$talkingEvent].screen_y - Graphics.height) - 136
@Arrow.z = 999999
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow4")
@Arrow.zoom_x = 2
@Arrow.zoom_y = 2
if @Arrow.x<-230
@Arrow.x = $game_map.events[$talkingEvent].screen_x
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow3")
end
else # Player facing left, down, right, message window bottom.
@Restriction = Viewport.new(0, 0, Graphics.width, 280)
@Restriction.z = 999999
@Arrow = Sprite.new(@Restriction)
@Arrow.x = $game_map.events[$talkingEvent].screen_x
@Arrow.y = $game_map.events[$talkingEvent].screen_y
@Arrow.z = 999999
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow1")
if @Arrow.y>=Graphics.height-120 # Change arrow direction.
@Outofrange=true
@Restriction.rect.y+=104
@Arrow.x = $game_map.events[$talkingEvent].screen_x - Graphics.width
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow4")
@Arrow.y = ($game_map.events[$talkingEvent].screen_y - Graphics.height) - 136
if @Arrow.x<-250
@Arrow.x = $game_map.events[$talkingEvent].screen_x
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow3")
end
if @Arrow.x>=256
@Arrow.x-=15# = $game_map.events[$talkingEvent].screen_x-Graphics.width
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow3")
end
else
@Outofrange=false
end
@Arrow.zoom_x = 2
@Arrow.zoom_y = 2
end
end
msgwindow=Window_AdvancedTextPokemon.new("")
if !viewport
msgwindow.z=99999
else
msgwindow.viewport=viewport
end
msgwindow.visible=true
msgwindow.letterbyletter=true
msgwindow.back_opacity=MessageConfig::WindowOpacity
pbBottomLeftLines(msgwindow,2)
$game_temp.message_window_showing=true if $game_temp
$game_message.visible=true if $game_message
skin=MessageConfig.pbGetSpeechFrame() if !skin
msgwindow.setSkin(skin)
return msgwindow
end

def Kernel.pbDisposeMessageWindow(msgwindow)
$game_temp.message_window_showing=false if $game_temp
$game_message.visible=false if $game_message
msgwindow.dispose
@Arrow.dispose if @Arrow
@Restriction.dispose if @Restriction
end



class FaceWindowVX < SpriteWindow_Base
def initialize(face)
super(0,0,128,128)
faceinfo=face.split(",")
facefile=pbResolveBitmap("Graphics/Faces/"+faceinfo[0])
facefile=pbResolveBitmap("Graphics/Pictures/"+faceinfo[0]) if !facefile
self.contents.dispose if self.contents
@faceIndex=faceinfo[1].to_i
@facebitmaptmp=AnimatedBitmap.new(facefile)
@facebitmap=BitmapWrapper.new(96,96)
@facebitmap.blt(0,0,@facebitmaptmp.bitmap,Rect.new(
(@faceIndex % 4) * 96,
(@faceIndex / 4) * 96, 96, 96
))
self.contents=@facebitmap
end

def update
super
if @facebitmaptmp.totalFrames>1
@facebitmaptmp.update
@facebitmap.blt(0,0,@facebitmaptmp.bitmap,Rect.new(
(@faceIndex % 4) * 96,
(@faceIndex / 4) * 96, 96, 96
))
end
end

def dispose
@facebitmaptmp.dispose
@facebitmap.dispose if @facebitmap
super
end
end



def itemIconTag(item)
return "" if !item
if item.respond_to?("icon_name")
return sprintf("<icon=%s>",item.icon_name)
else
ix=item.icon_index % 16 * 24
iy=item.icon_index / 16 * 24
return sprintf("<img=Graphics/System/Iconset|%d|%d|24|24>",ix,iy)
end
end

def getSkinColor(windowskin,color,isDarkSkin)
if !windowskin || windowskin.disposed? ||
windowskin.width!=128 || windowskin.height!=128
textcolors=[
shadowc3tag(MessageConfig::BUBBLETEXTBASE, MessageConfig::BUBBLETEXTSHADOW),
"<c2=7E105D08>",
"<c2=421F2117>",
"<c2=43F022E8>",
"<c2=7FF05EE8>",
"<c2=7E1F5D17>",
"<c2=43FF22F7>",
"<c2=63184210>",
"<c2=7FFF5EF7>"
]
color=0 if color>textcolors.length
return textcolors[color]
else # VX windowskin
color=0 if color>=32
x = 64 + (color % 8) * 8
y = 96 + (color / 8) * 8
pixel=windowskin.get_pixel(x, y)
return shadowctagFromColor(pixel)
end
end

# internal function
def pbRepositionMessageWindow(msgwindow, linecount=2)
msgwindow.height=32*linecount+msgwindow.borderY
msgwindow.y=(Graphics.height)-(msgwindow.height)
if $game_temp && $game_temp.in_battle && !$scene.respond_to?("update_basic")
msgwindow.y=0
elsif $game_system && $game_system.respond_to?("message_position")
case $game_system.message_position
when 0 # up
msgwindow.y=0
when 1 # middle
msgwindow.y=(Graphics.height/2)-(msgwindow.height/2)
when 2
@OpposedValue = 0
@NegativeValue = 0
if $Bubble==1
msgwindow.setSkin("Graphics/windowskins/frlgtextskin")
msgwindow.height = 100
msgwindow.width = 400
msgwindow.resizeToFit2(msgwindow.text,400,100)
msgwindow.x = $game_map.events[$talkingEvent].screen_x
msgwindow.y = $game_map.events[$talkingEvent].screen_y - (32 + msgwindow.height)
if msgwindow.y>(Graphics.height-msgwindow.height)
msgwindow.y = (Graphics.height-msgwindow.height)
elsif msgwindow.y<0
msgwindow.y+=msgwindow.height
end
if msgwindow.x>(Graphics.width-msgwindow.width)
msgwindow.x = ($game_map.events[$talkingEvent].screen_x-msgwindow.width)
elsif msgwindow.x<0
msgwindow.x+=(msgwindow.width)
end
$Bubble = 0
elsif $Bubble==2
msgwindow.setSkin("Graphics/windowskins/frlgtextskin")
msgwindow.height = 102
msgwindow.width = Graphics.width
if $game_player.direction==8
@Restriction = Viewport.new(0, 0, Graphics.width, 280)
msgwindow.y = 6
else
@Restriction = Viewport.new(0, 6 + msgwindow.height, Graphics.width, 280)
msgwindow.y = (Graphics.height - msgwindow.height) - 6
if @Outofrange==true
msgwindow.y = 6
end
end
$Bubble = 0
else
msgwindow.height = 102
msgwindow.y = Graphics.height - msgwindow.height - 6
end
end
end
if $game_system && $game_system.respond_to?("message_frame")
if $game_system.message_frame != 0
msgwindow.opacity = 0
end
end
if $game_message
case $game_message.background
when 1 # dim
msgwindow.opacity=0
when 2 # transparent
msgwindow.opacity=0
end
end
end

# internal function
def pbUpdateMsgWindowPos(msgwindow,event,eventChanged=false)
if event
if eventChanged
msgwindow.resizeToFit2(msgwindow.text,Graphics.width*2/3,msgwindow.height)
end
msgwindow.y=event.screen_y-48-msgwindow.height
if msgwindow.y<0
msgwindow.y=event.screen_y+24
end
msgwindow.x=event.screen_x-(msgwindow.width/2)
msgwindow.x=0 if msgwindow.x<0
if msgwindow.x>Graphics.width-msgwindow.width
msgwindow.x=Graphics.width-msgwindow.width
end
else
curwidth=msgwindow.width
if curwidth!=Graphics.width
msgwindow.width=Graphics.width
msgwindow.width=Graphics.width
end
end
end

# internal function

def pbGetGoldString
moneyString=""
if $Trainer
moneyString=_INTL("${1}",$Trainer.money)
else
if $data_system.respond_to?("words")
moneyString=_INTL("{1} {2}",$game_party.gold,$data_system.words.gold)
else
moneyString=_INTL("{1} {2}",$game_party.gold,Vocab.gold)
end
end
return moneyString
end

def pbDisplayGoldWindow(msgwindow)
moneyString=pbGetGoldString()
goldwindow=Window_AdvancedTextPokemon.new(_INTL("Money:\n<ar>{1}</ar>",moneyString))
goldwindow.setSkin("Graphics/Windowskins/goldskin")
goldwindow.resizeToFit(goldwindow.text,Graphics.width)
goldwindow.width=160 if goldwindow.width<=160
if msgwindow.y==0
goldwindow.y=Graphics.height-goldwindow.height
else
goldwindow.y=0
end
goldwindow.viewport=msgwindow.viewport
goldwindow.z=msgwindow.z
return goldwindow
end

def pbDisplayCoinsWindow(msgwindow,goldwindow)
coinString=($PokemonGlobal) ? $PokemonGlobal.coins : "0"
coinwindow=Window_AdvancedTextPokemon.new(_INTL("Coins:\n<ar>{1}</ar>",coinString))
coinwindow.setSkin("Graphics/Windowskins/goldskin")
coinwindow.resizeToFit(coinwindow.text,Graphics.width)
coinwindow.width=160 if coinwindow.width<=160
if msgwindow.y==0
coinwindow.y=(goldwindow) ? goldwindow.y-coinwindow.height : Graphics.height-coinwindow.height
else
coinwindow.y=(goldwindow) ? goldwindow.height : 0
end
coinwindow.viewport=msgwindow.viewport
coinwindow.z=msgwindow.z
return coinwindow
end

def pbRecord(arg); end

def pbMessageWaitForInput(msgwindow,frames,showPause=false)
return if !frames || frames<=0
if msgwindow && showPause
msgwindow.startPause
end
frames.times do
Graphics.update
Input.update
msgwindow.update if msgwindow
pbUpdateSceneMap
if Input.trigger?(Input::C) || Input.trigger?(Input::B)
break
end
end
if msgwindow && showPause
msgwindow.stopPause
end
end

def Kernel.pbMessageDisplay(msgwindow,message,letterbyletter=true,commandProc=nil)
return if !msgwindow
oldletterbyletter=msgwindow.letterbyletter
msgwindow.letterbyletter=(letterbyletter ? true : false)
ret=nil
count=0
commands=nil
facewindow=nil
goldwindow=nil
coinwindow=nil
cmdvariable=0
cmdIfCancel=0
msgwindow.waitcount=0
autoresume=false
text=message.clone
msgback=nil
linecount=(Graphics.height>400) ? 3 : 2
### Text replacement
text.gsub!(/\\\\/,"\5")
if $game_actors
text.gsub!(/\\[Nn]\[([1-8])\]/){
m=$1.to_i
next $game_actors[m].name
}
end
text.gsub!(/\\[Ss][Ii][Gg][Nn]\[([^\]]*)\]/){
next "\\op\\cl\\ts[]\\w["+$1+"]"
}
text.gsub!(/\\[Pp][Nn]/,$Trainer.name) if $Trainer
text.gsub!(/\\[Pp][Mm]/,_INTL("${1}",$Trainer.money)) if $Trainer
text.gsub!(/\\[Nn]/,"\n")
text.gsub!(/\\\[([0-9A-Fa-f]{8,8})\]/){ "<c2="+$1+">" }
text.gsub!(/\\[Bb]/,"<c2=6546675A>")
text.gsub!(/\\[Rr]/,"<c2=043C675A>")
text.gsub!(/\\1/,"\1")
colortag=""
isDarkSkin=isDarkWindowskin(msgwindow.windowskin)
if ($game_message && $game_message.background>0) ||
($game_system && $game_system.respond_to?("message_frame") &&
$game_system.message_frame != 0)
colortag=getSkinColor(msgwindow.windowskin,0,true)
else
colortag=getSkinColor(msgwindow.windowskin,0,isDarkSkin)
end
text.gsub!(/\\[Cc]\[([0-9]+)\]/){
m=$1.to_i
next getSkinColor(msgwindow.windowskin,m,isDarkSkin)
}
begin
last_text = text.clone
text.gsub!(/\\[Vv]\[([0-9]+)\]/) { $game_variables[$1.to_i] }
end until text == last_text
begin
last_text = text.clone
text.gsub!(/\\[Ll]\[([0-9]+)\]/) {
linecount=[1,$1.to_i].max;
next ""
}
end until text == last_text
text=colortag+text
### Controls
textchunks=[]
controls=[]
while text[/(?:\\([WwFf]|[Ff][Ff]|[Tt][Ss]|[Cc][Ll]|[Mm][Ee]|[Ss][Ee]|[Ww][Tt]|[Ww][Tt][Nn][Pp]|[Cc][Hh])\[([^\]]*)\]|\\([Gg]|[Cc][Nn]|[Ww][Dd]|[Ww][Mm]|[Oo][Pp]|[Cc][Ll]|[Ww][Uu]|[\.]|[\|]|[\!]|[\x5E])())/i]
textchunks.push($~.pre_match)
if $~[1]
controls.push([$~[1].downcase,$~[2],-1])
else
controls.push([$~[3].downcase,"",-1])
end
text=$~.post_match
end
textchunks.push(text)
for chunk in textchunks
chunk.gsub!(/\005/,"\\")
end
textlen=0
for i in 0...controls.length
control=controls[i][0]
if control=="wt" || control=="wtnp" || control=="." || control=="|"
textchunks[i]+="\2"
elsif control=="!"
textchunks[i]+="\1"
end
textlen+=toUnformattedText(textchunks[i]).scan(/./m).length
controls[i][2]=textlen
end
text=textchunks.join("")
unformattedText=toUnformattedText(text)
signWaitCount=0
haveSpecialClose=false
specialCloseSE=""
for i in 0...controls.length
control=controls[i][0]
param=controls[i][1]
if control=="f"
facewindow.dispose if facewindow
facewindow=PictureWindow.new("Graphics/Pictures/#{param}")
elsif control=="op"
signWaitCount=21
elsif control=="cl"
text=text.sub(/\001\z/,"") # fix: '$' can match end of line as well
haveSpecialClose=true
specialCloseSE=param
elsif control=="se" && controls[i][2]==0
startSE=param
controls[i]=nil
elsif control=="ff"
facewindow.dispose if facewindow
facewindow=FaceWindowVX.new(param)
elsif control=="ch"
cmds=param.clone
cmdvariable=pbCsvPosInt!(cmds)
cmdIfCancel=pbCsvField!(cmds).to_i
commands=[]
while cmds.length>0
commands.push(pbCsvField!(cmds))
end
elsif control=="wtnp" || control=="^"
text=text.sub(/\001\z/,"") # fix: '$' can match end of line as well
end
end
if startSE!=nil
pbSEPlay(pbStringToAudioFile(startSE))
elsif signWaitCount==0 && letterbyletter
pbPlayDecisionSE()
end
########## Position message window ##############
msgwindow.text=text
pbRepositionMessageWindow(msgwindow,linecount)
if $game_message && $game_message.background==1
msgback=IconSprite.new(0,msgwindow.y,msgwindow.viewport)
msgback.z=msgwindow.z-1
msgback.setBitmap("Graphics/System/MessageBack")
end
if facewindow
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
facewindow.viewport=msgwindow.viewport
facewindow.z=msgwindow.z
end
atTop=(msgwindow.y==0)
########## Show text #############################
#msgwindow.text=text
Graphics.frame_reset if Graphics.frame_rate>40
begin
if signWaitCount>0
signWaitCount-=1
if atTop
msgwindow.y=-(msgwindow.height*(signWaitCount)/20)
else
msgwindow.y=Graphics.height-(msgwindow.height*(20-signWaitCount)/20)
end
end
for i in 0...controls.length
if controls[i] && controls[i][2]<=msgwindow.position && msgwindow.waitcount==0
control=controls[i][0]
param=controls[i][1]
if control=="f"
facewindow.dispose if facewindow
facewindow=PictureWindow.new("Graphics/Pictures/#{param}")
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
facewindow.viewport=msgwindow.viewport
facewindow.z=msgwindow.z
elsif control=="ts"
if param==""
msgwindow.textspeed=-999
else
msgwindow.textspeed=param.to_i
end
elsif control=="ff"
facewindow.dispose if facewindow
facewindow=FaceWindowVX.new(param)
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
facewindow.viewport=msgwindow.viewport
facewindow.z=msgwindow.z
elsif control=="g" # Display gold window
goldwindow.dispose if goldwindow
goldwindow=pbDisplayGoldWindow(msgwindow)
elsif control=="cn" # Display coins window
coinwindow.dispose if coinwindow
coinwindow=pbDisplayCoinsWindow(msgwindow,goldwindow)
elsif control=="wu"
msgwindow.y=0
atTop=true
msgback.y=msgwindow.y if msgback
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
msgwindow.y=-(msgwindow.height*(signWaitCount)/20)
elsif control=="wm"
atTop=false
msgwindow.y=(Graphics.height/2)-(msgwindow.height/2)
msgback.y=msgwindow.y if msgback
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
elsif control=="wd"
atTop=false
msgwindow.y=(Graphics.height)-(msgwindow.height)
msgback.y=msgwindow.y if msgback
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
msgwindow.y=Graphics.height-(msgwindow.height*(20-signWaitCount)/20)
elsif control=="."
msgwindow.waitcount+=Graphics.frame_rate/4
elsif control=="|"
msgwindow.waitcount+=Graphics.frame_rate
elsif control=="wt" # Wait
param=param.sub(/\A\s+/,"").sub(/\s+\z/,"")
msgwindow.waitcount+=param.to_i*2
elsif control=="w" # Windowskin
if param==""
msgwindow.windowskin=nil
else
msgwindow.setSkin("Graphics/Windowskins/#{param}")
end
msgwindow.width=msgwindow.width # Necessary evil
elsif control=="^" # Wait, no pause
autoresume=true
elsif control=="wtnp" # Wait, no pause
param=param.sub(/\A\s+/,"").sub(/\s+\z/,"")
msgwindow.waitcount=param.to_i*2
autoresume=true
elsif control=="se" # Play SE
pbSEPlay(pbStringToAudioFile(param))
elsif control=="me" # Play ME
pbMEPlay(pbStringToAudioFile(param))
end
controls[i]=nil
end
end
break if !letterbyletter
Graphics.update
Input.update
facewindow.update if facewindow
if $DEBUG && Input.trigger?(Input::F6)
pbRecord(unformattedText)
end
if autoresume && msgwindow.waitcount==0
msgwindow.resume if msgwindow.busy?
break if !msgwindow.busy?
end
if (Input.trigger?(Input::C) || Input.trigger?(Input::B))
if msgwindow.busy?
pbPlayDecisionSE() if msgwindow.pausing?
msgwindow.resume
else
break if signWaitCount==0
end
end
pbUpdateSceneMap
msgwindow.update
yield if block_given?
end until (!letterbyletter || commandProc || commands) && !msgwindow.busy?
Input.update # Must call Input.update again to avoid extra triggers
msgwindow.letterbyletter=oldletterbyletter
if commands
$game_variables[cmdvariable]=Kernel.pbShowCommands(
msgwindow,commands,cmdIfCancel)
$game_map.need_refresh = true if $game_map
end
if commandProc
ret=commandProc.call(msgwindow)
end
msgback.dispose if msgback
goldwindow.dispose if goldwindow
coinwindow.dispose if coinwindow
facewindow.dispose if facewindow
if haveSpecialClose
pbSEPlay(pbStringToAudioFile(specialCloseSE))
atTop=(msgwindow.y==0)
for i in 0..20
if atTop
msgwindow.y=-(msgwindow.height*(i)/20)
else
msgwindow.y=Graphics.height-(msgwindow.height*(20-i)/20)
end
Graphics.update
Input.update
pbUpdateSceneMap
msgwindow.update
end
end
return ret
end


Thanks for help beforehand.

linkthehero
May 28th, 2014, 12:57 PM
So, I downloaded Carmaniac's Pokemon Essentials Speech Bubbles script (http://pokemonessentials.wikia.com/wiki/Tutorial:Speech_bubbles), and installed it.
It works fine, but I wanted to make that more personal, so I edited it a bit.
I think this is very easy to solve with changing some things in the script, but I don't know how to do that.

This is what I did:

(the original Windowskin looks like this: http://i.imgur.com/ekmELb8.png
I edited that "frlgtextskin" Windowsskin, like this:
http://i.imgur.com/dMRyUCi.png.

So I took some useless space out of it, and it still works fine - almost. I took a picture of it when you play it and it looks like this:
http://i.imgur.com/2rMOjpf.png

So that arrow doesn't reach that text box (or Windowskin). I tried to move that arrow down (with photoshop), but the same problem exist.
There might be an priority with that Windowskin, so how could I fix it?

Here is the script: class Game_Temp
attr_writer :message_window_showing
attr_writer :player_transferring
attr_writer :transition_processing

def message_window_showing
@message_window_showing=false if !@message_window_showing
return @message_window_showing
end

def player_transferring
@player_transferring=false if !@player_transferring
return @player_transferring
end

def transition_processing
@transition_processing=false if !@transition_processing
return @transition_processing
end
end



class Game_Message
attr_writer :background, :visible
def visible; return @visible ? @visible : false; end
def background; return @background ? @background : 0; end
end



class Game_System
attr_writer :message_position

def message_position
@message_position=2 if !@message_position
return @message_position
end
end



#########

class Scene_Map
def updatemini
oldmws=$game_temp.message_window_showing
oldvis=$game_message ? $game_message.visible : false
$game_temp.message_window_showing=true
$game_message.visible=true if $game_message
loop do
$game_map.update
$game_player.update
$game_system.update
if $game_screen
$game_screen.update
else
$game_map.screen.update
end
unless $game_temp.player_transferring
break
end
transfer_player
if $game_temp.transition_processing
break
end
end
$game_temp.message_window_showing=oldmws
$game_message.visible=oldvis if $game_message
@spriteset.update if @spriteset
@message_window.update if @message_window
end
end



class Scene_Battle
def updatemini
if self.respond_to?("update_basic")
update_basic(true)
update_info_viewport # Update information viewport
if $game_message && $game_message.visible
@info_viewport.visible = false
@message_window.visible = true
end
else
oldmws=$game_temp.message_window_showing
$game_temp.message_window_showing=true
# Update system (timer) and screen
$game_system.update
if $game_screen
$game_screen.update
else
$game_map.screen.update
end
# If timer has reached 0
if $game_system.timer_working and $game_system.timer == 0
# Abort battle
$game_temp.battle_abort = true
end
# Update windows
@help_window.update if @help_window
@party_command_window.update if @party_command_window
@actor_command_window.update if @actor_command_window
@status_window.update if @status_window
$game_temp.message_window_showing=oldmws
@message_window.update if @message_window
# Update sprite set
@spriteset.update if @spriteset
end
end
end



def pbMapInterpreterRunning?
interp=pbMapInterpreter
return interp && interp.running?
end

def pbMapInterpreter
if $game_map && $game_map.respond_to?("interpreter")
return $game_map.interpreter
elsif $game_system
return $game_system.map_interpreter
end
return nil
end

def pbRefreshSceneMap
if $scene && $scene.is_a?(Scene_Map)
if $scene.respond_to?("miniupdate")
$scene.miniupdate
else
$scene.updatemini
end
elsif $scene && $scene.is_a?(Scene_Battle)
$scene.updatemini
end
end

def pbUpdateSceneMap
if $scene && $scene.is_a?(Scene_Map) && !pbIsFaded?
if $scene.respond_to?("miniupdate")
$scene.miniupdate
else
$scene.updatemini
end
elsif $scene && $scene.is_a?(Scene_Battle)
$scene.updatemini
end
end
#########

def pbCsvField!(str)
ret=""
str.sub!(/\A\s*/,"")
if str[0,1]=="\""
str[0,1]=""
escaped=false
fieldbytes=0
str.scan(/./) do |s|
fieldbytes+=s.length
break if s=="\"" && !escaped
if s=="\\" && !escaped
escaped=true
else
ret+=s
escaped=false
end
end
str[0,fieldbytes]=""
if !str[/\A\s*,/] && !str[/\A\s*$/]
raise _INTL("Invalid quoted field (in: {1})",ret)
end
str[0,str.length]=$~.post_match
else
if str[/,/]
str[0,str.length]=$~.post_match
ret=$~.pre_match
else
ret=str.clone
str[0,str.length]=""
end
ret.gsub!(/\s+$/,"")
end
return ret
end

def pbCsvPosInt!(str)
ret=pbCsvField!(str)
if !ret[/\A\d+$/]
raise _INTL("Field {1} is not a positive integer",ret)
end
return ret.to_i
end

def pbEventCommentInput(*args)
parameters = []
list = *args[0].list # Event or event page
elements = *args[1] # Number of elements
trigger = *args[2] # Trigger
return nil if list == nil
return nil unless list.is_a?(Array)
for item in list
next unless item.code == 108 || item.code == 408
if item.parameters[0] == trigger
start = list.index(item) + 1
finish = start + elements
for id in start...finish
next if !list[id]
parameters.push(list[id].parameters[0])
end
return parameters
end
end
return nil
end

# Gets the value of a variable.
def pbGet(id)
return 0 if !id || !$game_variables
return $game_variables[id]
end

# Sets the value of a variable.
def pbSet(id,value)
if id && id>=0
$game_variables[id]=value if $game_variables
$game_map.need_refresh = true if $game_map
end
end

def pbCurrentEventCommentInput(elements,trigger)
return nil if !pbMapInterpreterRunning?
event=pbMapInterpreter.get_character(0)
return nil if !event
return pbEventCommentInput(event,elements,trigger)
end



module InterpreterMixin
def pbGlobalLock # Freezes all events on the map (for use at the beginning of common events)
for event in $game_map.events.values
event.minilock
end
end

def pbGlobalUnlock # Unfreezes all events on the map (for use at the end of common events)
for event in $game_map.events.values
event.unlock
end
end

def pbRepeatAbove(index)
index=@list[index].indent
loop do
index-=1
if @list[index].indent==indent
return index+1
end
end
end

def pbBreakLoop(index)
indent = @list[index].indent
temp_index=index
# Copy index to temporary variables
loop do
# Advance index
temp_index += 1
# If a fitting loop was not found
if temp_index >= @list.size-1
return index+1
end
if @list[temp_index].code == 413 and @list[temp_index].indent < indent
return temp_index+1
end
end
end

def pbJumpToLabel(index,label_name)
temp_index = 0
loop do
if temp_index >= @list.size-1
return index+1
end
if @list[temp_index].code == 118 and
@list[temp_index].parameters[0] == label_name
return temp_index+1
end
temp_index += 1
end
end

# Gets the next index in the interpreter, ignoring
# certain events between messages
def pbNextIndex(index)
return -1 if !@list || @list.length==0
i=index+1
loop do
if i>=@list.length-1
return i
end
code=@list[i].code
case code
when 118, 108, 408 # Label, Comment
i+=1
when 413 # Repeat Above
i=pbRepeatAbove(i)
when 113 # Break Loop
i=pbBreakLoop(i)
when 119 # Jump to Label
newI=pbJumpToLabel(i,@list[i].parameters[0])
if newI>i
i=newI
else
i+=1
end
else
return i
end
end
end

# Helper function that shows a picture in a script. To be used in
# a script event command.
def pbShowPicture(number,name,origin,x,y,zoomX=100,zoomY=100,opacity=255,blendType=0)
number = number + ($game_temp.in_battle ? 50 : 0)
$game_screen.pictures[number].show(name,origin,
x, y, zoomX,zoomY,opacity,blendType)
end

# Erases an event and adds it to the list of erased events so that
# it can stay erased when the game is saved then loaded again. To be used in
# a script event command.
def pbEraseThisEvent
if $game_map.events[@event_id]
$game_map.events[@event_id].erase
$PokemonMap.addErasedEvent(@event_id) if $PokemonMap
end
@index+=1
return true
end

# Runs a common event. To be used in a script event command.
def pbCommonEvent(id)
if $game_temp.in_battle
$game_temp.common_event_id = id
else
commonEvent = $data_common_events[id]
$game_system.battle_interpreter.setup(commonEvent.list, 0)
end
end

# Sets another event's self switch (eg. pbSetSelfSwitch(20,"A",true) ).
# To be used in a script event command.
def pbSetSelfSwitch(event,swtch,value)
$game_self_switches[[@map_id,event,swtch]]=value
$game_map.need_refresh = true
end

# Must use this approach to share the methods because the methods already
# defined in a class override those defined in an included module
CustomEventCommands=<<_END_

def command_242
pbBGMFade(pbParams[0])
return true
end

def command_246
pbBGSFade(pbParams[0])
return true
end

def command_251
pbSEStop()
return true
end

def command_241
pbBGMPlay(pbParams[0])
return true
end

def command_245
pbBGSPlay(pbParams[0])
return true
end

def command_249
pbMEPlay(pbParams[0])
return true
end

def command_250
pbSEPlay(pbParams[0])
return true
end
_END_
end



def pbButtonInputProcessing(variableNumber=0,timeoutFrames=0)
ret=0
loop do
Graphics.update
Input.update
pbUpdateSceneMap
for i in 1..18
if Input.trigger?(i)
ret=i
end
end
break if ret!=0
if timeoutFrames && timeoutFrames>0
i+=1
break if i>=timeoutFrames
end
end
Input.update
if variableNumber && variableNumber>0
$game_variables[variableNumber]=ret
$game_map.need_refresh = true if $game_map
end
return ret
end



class Game_Temp
attr_accessor :background
end



class Game_Interpreter
include InterpreterMixin
eval(InterpreterMixin::CustomEventCommands)
@@immediateDisplayAfterWait=false
@buttonInput=false

def pbParams
return @params
end

def command_105
return false if @buttonInput
@buttonInput=true
pbButtonInputProcessing(@list[@index].parameters[0])
@buttonInput=false
@index+=1
return true
end

def command_101
if $game_temp.message_window_showing
return false
end
$game_message=Game_Message.new if !$game_message
message=""
commands=nil
numInputVar=nil
numInputDigitsMax=nil
text=""
facename=@list[@index].parameters[0]
faceindex=@list[@index].parameters[1]
if facename && facename!=""
text+="\\ff[#{facename},#{faceindex}]"
end
if $game_message
$game_message.background=@list[@index].parameters[2]
end
$game_system.message_position=@list[@index].parameters[3]
message+=text
messageend=""
loop do
nextIndex=pbNextIndex(@index)
code=@list[nextIndex].code
if code == 401
text=@list[nextIndex].parameters[0]
text+=" " if text!="" && text[text.length-1,1]!=" "
message+=text
@index=nextIndex
else
if code == 102
commands=@list[nextIndex].parameters
@index=nextIndex
elsif code == 106 && @@immediateDisplayAfterWait
params=@list[nextIndex].parameters
if params[0]<=10
nextcode=@list[nextIndex+1].code
if nextcode==101||nextcode==102||nextcode==103
@index=nextIndex
else
break
end
else
break
end
elsif code == 103
numInputVar=@list[nextIndex].parameters[0]
numInputDigitsMax=@list[nextIndex].parameters[1]
@index=nextIndex
elsif code == 101
messageend="\1"
end
break
end
end
message=_MAPINTL($game_map.map_id,message)
@message_waiting=true
if commands
cmdlist=[]
for cmd in commands[0]
cmdlist.push(_MAPINTL($game_map.map_id,cmd))
end
command=Kernel.pbMessage(message+messageend,cmdlist,commands[1])
@branch[@list[@index].indent] = command
elsif numInputVar
params=ChooseNumberParams.new
params.setMaxDigits(numInputDigitsMax)
params.setDefaultValue($game_variables[numInputVar])
$game_variables[numInputVar]=Kernel.pbMessageChooseNumber(message+messageend,params)
$game_map.need_refresh = true if $game_map
else
Kernel.pbMessage(message+messageend)
end
@message_waiting=false
return true
end

def command_102
@message_waiting=true
command=Kernel.pbShowCommands(nil,@list[@index].parameters[0],@list[@index].parameters[1])
@message_waiting=false
@branch[@list[@index].indent] = command
Input.update # Must call Input.update again to avoid extra triggers
return true
end

def command_103
varnumber=@list[@index].parameters[0]
@message_waiting=true
params=ChooseNumberParams.new
params.setMaxDigits(@list[@index].parameters[1])
params.setDefaultValue($game_variables[varnumber])
$game_variables[varnumber]=Kernel.pbChooseNumber(nil,params)
$game_map.need_refresh = true if $game_map
@message_waiting=false
return true
end
end



class Interpreter
include InterpreterMixin
eval(InterpreterMixin::CustomEventCommands)
@@immediateDisplayAfterWait=false
@buttonInput=false

def pbParams
return @parameters
end

def command_105
return false if @buttonInput
@buttonInput=true
pbButtonInputProcessing(@list[@index].parameters[0])
@buttonInput=false
@index+=1
return true
end

def command_101
if $game_temp.message_window_showing
return false
end
message=""
commands=nil
numInputVar=nil
numInputDigitsMax=nil
text=""
firstText=nil
if @list[@index].parameters.length==1
text+=@list[@index].parameters[0]
firstText=@list[@index].parameters[0]
text+=" " if text[text.length-1,1]!=" "
message+=text
else
facename=@list[@index].parameters[0]
faceindex=@list[@index].parameters[1]
if facename && facename!=""
text+="\\ff[#{facename},#{faceindex}]"
message+=text
end
end
messageend=""
loop do
nextIndex=pbNextIndex(@index)
code=@list[nextIndex].code
if code == 401
text=@list[nextIndex].parameters[0]
text+=" " if text[text.length-1,1]!=" "
message+=text
@index=nextIndex
else
if code == 102
commands=@list[nextIndex].parameters
@index=nextIndex
elsif code == 106 && @@immediateDisplayAfterWait
params=@list[nextIndex].parameters
if params[0]<=10
nextcode=@list[nextIndex+1].code
if nextcode==101||nextcode==102||nextcode==103
@index=nextIndex
else
break
end
else
break
end
elsif code == 103
numInputVar=@list[nextIndex].parameters[0]
numInputDigitsMax=@list[nextIndex].parameters[1]
@index=nextIndex
elsif code == 101
if @list[@index].parameters.length==1
text=@list[@index].parameters[0]
if text[/\A\\ignr/] && text==firstText
text+=" " if text[text.length-1,1]!=" "
message+=text
@index=nextIndex
continue
end
end
messageend="\1"
end
break
end
end
@message_waiting=true # needed to allow parallel process events to work while
# a message is displayed
message=_MAPINTL($game_map.map_id,message)
if commands
cmdlist=[]
for cmd in commands[0]
cmdlist.push(_MAPINTL($game_map.map_id,cmd))
end
command=Kernel.pbMessage(message+messageend,cmdlist,commands[1])
@branch[@list[@index].indent] = command
elsif numInputVar
params=ChooseNumberParams.new
params.setMaxDigits(numInputDigitsMax)
params.setDefaultValue($game_variables[numInputVar])
$game_variables[numInputVar]=Kernel.pbMessageChooseNumber(message+messageend,params)
$game_map.need_refresh = true if $game_map
else
Kernel.pbMessage(message+messageend,nil)
end
@message_waiting=false
return true
end

def command_102
@message_waiting=true
command=Kernel.pbShowCommands(nil,@list[@index].parameters[0],@list[@index].parameters[1])
@message_waiting=false
@branch[@list[@index].indent] = command
Input.update # Must call Input.update again to avoid extra triggers
return true
end

def command_103
varnumber=@list[@index].parameters[0]
@message_waiting=true
params=ChooseNumberParams.new
params.setMaxDigits(@list[@index].parameters[1])
params.setDefaultValue($game_variables[varnumber])
$game_variables[varnumber]=Kernel.pbChooseNumber(nil,params)
$game_map.need_refresh = true if $game_map
@message_waiting=false
return true
end
end



class ChooseNumberParams
def initialize
@maxDigits=0
@minNumber=0
@maxNumber=0
@skin=nil
@messageSkin=nil
@negativesAllowed=false
@initialNumber=0
@cancelNumber=nil
end

def setMessageSkin(value)
@messageSkin=value
end

def messageSkin # Set the full path for the message's window skin
@messageSkin
end

def setSkin(value)
@skin=value
end

def skin
@skin
end

def setNegativesAllowed(value)
@negativeAllowed=value
end

def negativesAllowed
@negativeAllowed ? true : false
end

def setRange(minNumber,maxNumber)
maxNumber=minNumber if minNumber>maxNumber
@maxDigits=0
@minNumber=minNumber
@maxNumber=maxNumber
end

def setDefaultValue(number)
@initialNumber=number
@cancelNumber=nil
end

def setInitialValue(number)
@initialNumber=number
end

def setCancelValue(number)
@cancelNumber=number
end

def initialNumber
return clamp(@initialNumber,self.minNumber,self.maxNumber)
end

def cancelNumber
return @cancelNumber ? @cancelNumber : self.initialNumber
end

def minNumber
ret=0
if @maxDigits>0
ret=-((10**@maxDigits)-1)
elsif
ret=@minNumber
end
ret=0 if !@negativeAllowed && ret<0
return ret
end

def maxNumber
ret=0
if @maxDigits>0
ret=((10**@maxDigits)-1)
elsif
ret=@maxNumber
end
ret=0 if !@negativeAllowed && ret<0
return ret
end

def setMaxDigits(value)
@maxDigits=[1,value].max
end

def maxDigits
if @maxDigits>0
return @maxDigits
else
return [numDigits(self.minNumber),numDigits(self.maxNumber)].max
end
end

private

def clamp(v,mn,mx)
return v<mn ? mn : (v>mx ? mx : v)
end

def numDigits(number)
ans = 1
number=number.abs
while number >= 10
ans+=1
number/=10
end
return ans
end
end



def pbChooseNumber(msgwindow,params)
return 0 if !params
ret=0
maximum=params.maxNumber
minimum=params.minNumber
defaultNumber=params.initialNumber
cancelNumber=params.cancelNumber
cmdwindow=Window_InputNumberPokemon.new(params.maxDigits)
cmdwindow.z=99999
cmdwindow.visible=true
cmdwindow.setSkin(params.skin) if params.skin
cmdwindow.sign=params.negativesAllowed # must be set before number
cmdwindow.number=defaultNumber
curnumber=defaultNumber
pbPositionNearMsgWindow(cmdwindow,msgwindow,:right)
command=0
loop do
Graphics.update
Input.update
pbUpdateSceneMap
cmdwindow.update
msgwindow.update if msgwindow
yield if block_given?
if Input.trigger?(Input::C)
ret=cmdwindow.number
if ret>maximum
pbPlayBuzzerSE()
elsif ret<minimum
pbPlayBuzzerSE()
else
pbPlayDecisionSE()
break
end
elsif Input.trigger?(Input::B)
pbPlayCancelSE()
ret=cancelNumber
break
end
end
cmdwindow.dispose
Input.update
return ret
end

def Kernel.pbShowCommandsWithHelp(msgwindow,commands,help,cmdIfCancel=0,defaultCmd=0)
msgwin=msgwindow
if !msgwindow
msgwin=Kernel.pbCreateMessageWindow(nil)
end
oldlbl=msgwin.letterbyletter
msgwin.letterbyletter=false
if commands
cmdwindow=Window_CommandPokemonEx.new(commands)
cmdwindow.z=99999
cmdwindow.visible=true
cmdwindow.resizeToFit(cmdwindow.commands)
cmdwindow.height=msgwin.y if cmdwindow.height>msgwin.y
cmdwindow.index=defaultCmd
command=0
msgwin.text=help[cmdwindow.index]
msgwin.width=msgwin.width # Necessary evil to make it use the proper margins.
loop do
Graphics.update
Input.update
oldindex=cmdwindow.index
cmdwindow.update
if oldindex!=cmdwindow.index
msgwin.text=help[cmdwindow.index]
end
msgwin.update
yield if block_given?
if Input.trigger?(Input::B)
if cmdIfCancel>0
command=cmdIfCancel-1
break
elsif cmdIfCancel<0
command=cmdIfCancel
break
end
end
if Input.trigger?(Input::C)
command=cmdwindow.index
break
end
pbUpdateSceneMap
end
ret=command
cmdwindow.dispose
Input.update
end
msgwin.letterbyletter=oldlbl
if !msgwindow
msgwin.dispose
end
return ret
end

def Kernel.pbShowCommands(msgwindow,commands=nil,cmdIfCancel=0,defaultCmd=0)
ret=0
if commands
cmdwindow=Window_CommandPokemonEx.new(commands)
cmdwindow.z=99999
cmdwindow.visible=true
cmdwindow.resizeToFit(cmdwindow.commands)
pbPositionNearMsgWindow(cmdwindow,msgwindow,:right)
cmdwindow.index=defaultCmd
command=0
loop do
Graphics.update
Input.update
cmdwindow.update
msgwindow.update if msgwindow
yield if block_given?
if Input.trigger?(Input::B)
if cmdIfCancel>0
command=cmdIfCancel-1
break
elsif cmdIfCancel<0
command=cmdIfCancel
break
end
end
if Input.trigger?(Input::C)
command=cmdwindow.index
break
end
pbUpdateSceneMap
end
ret=command
cmdwindow.dispose
Input.update
end
return ret
end

def pbPositionFaceWindow(facewindow,msgwindow)
return if !facewindow
if msgwindow
if facewindow.height<=msgwindow.height
facewindow.y=msgwindow.y
else
facewindow.y=msgwindow.y+msgwindow.height-facewindow.height
end
facewindow.x=Graphics.width-facewindow.width
msgwindow.x=0
msgwindow.width=Graphics.width-facewindow.width
else
facewindow.height=Graphics.height if facewindow.height>Graphics.height
facewindow.x=0
facewindow.y=0
end
end

def pbPositionNearMsgWindow(cmdwindow,msgwindow,side)
return if !cmdwindow
if msgwindow
height=[cmdwindow.height,Graphics.height-msgwindow.height].min
if cmdwindow.height!=height
cmdwindow.height=height
end
cmdwindow.y=msgwindow.y-cmdwindow.height
if cmdwindow.y<0
cmdwindow.y=msgwindow.y+msgwindow.height
if cmdwindow.y+cmdwindow.height>Graphics.height
cmdwindow.y=msgwindow.y-cmdwindow.height
end
end
case side
when :left
cmdwindow.x=msgwindow.x
when :right
cmdwindow.x=msgwindow.x+msgwindow.width-cmdwindow.width
else
cmdwindow.x=msgwindow.x+msgwindow.width-cmdwindow.width
end
else
cmdwindow.height=Graphics.height if cmdwindow.height>Graphics.height
cmdwindow.x=0
cmdwindow.y=0
end
end

def pbGetBasicMapNameFromId(id)
begin
map = pbLoadRxData("Data/MapInfos")
return "" if !map
return map[id].name
rescue
return ""
end
end

def pbGetMapNameFromId(id)
map=pbGetBasicMapNameFromId(id)
if $Trainer
map.gsub!(/\\PN/,$Trainer.name)
end
return map
end

def Kernel.pbMessage(message,commands=nil,cmdIfCancel=0,skin=nil,defaultCmd=0,&block)
ret=0
msgwindow=Kernel.pbCreateMessageWindow(nil,skin)
if commands
ret=Kernel.pbMessageDisplay(msgwindow,message,true,
proc {|msgwindow|
next Kernel.pbShowCommands(msgwindow,commands,cmdIfCancel,defaultCmd,&block)
},&block)
else
Kernel.pbMessageDisplay(msgwindow,message,&block)
end
Kernel.pbDisposeMessageWindow(msgwindow)
Input.update
return ret
end

def Kernel.pbMessageChooseNumber(message,params,&block)
msgwindow=Kernel.pbCreateMessageWindow(nil,params.messageSkin)
ret=Kernel.pbMessageDisplay(msgwindow,message,true,
proc {|msgwindow|
next Kernel.pbChooseNumber(msgwindow,params,&block)
},&block)
Kernel.pbDisposeMessageWindow(msgwindow)
return ret
end

def Kernel.pbConfirmMessage(message,&block)
return (Kernel.pbMessage(message,[_INTL("Yes"),_INTL("No")],2,&block)==0)
end

def Kernel.pbConfirmMessageSerious(message,&block)
return (Kernel.pbMessage(message,[_INTL("No"),_INTL("Yes")],1,&block)==1)
end

def Kernel.pbCreateStatusWindow(viewport=nil)
msgwindow=Window_AdvancedTextPokemon.new("")
if !viewport
msgwindow.z=99999
else
msgwindow.viewport=viewport
end
msgwindow.visible=false
msgwindow.letterbyletter=false
pbBottomLeftLines(msgwindow,2)
skinfile=MessageConfig.pbGetSpeechFrame()
msgwindow.setSkin(skinfile)
return msgwindow
end

def Kernel.pbCreateMessageWindow(viewport=nil,skin=nil)
if $Bubble==2 # Message window set to floating bubble.
if $game_player.direction==8 # Player facing up, message window top.
@Restriction = Viewport.new(0, 104, Graphics.width, 280)
@Restriction.z = 999999
@Arrow = Sprite.new(@Restriction)
@Arrow.x = $game_map.events[$talkingEvent].screen_x - Graphics.width
@Arrow.y = ($game_map.events[$talkingEvent].screen_y - Graphics.height) - 136
@Arrow.z = 999999
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow4")
@Arrow.zoom_x = 2
@Arrow.zoom_y = 2
if @Arrow.x<-230
@Arrow.x = $game_map.events[$talkingEvent].screen_x
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow3")
end
else # Player facing left, down, right, message window bottom.
@Restriction = Viewport.new(0, 0, Graphics.width, 280)
@Restriction.z = 999999
@Arrow = Sprite.new(@Restriction)
@Arrow.x = $game_map.events[$talkingEvent].screen_x
@Arrow.y = $game_map.events[$talkingEvent].screen_y
@Arrow.z = 999999
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow1")
if @Arrow.y>=Graphics.height-120 # Change arrow direction.
@Outofrange=true
@Restriction.rect.y+=104
@Arrow.x = $game_map.events[$talkingEvent].screen_x - Graphics.width
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow4")
@Arrow.y = ($game_map.events[$talkingEvent].screen_y - Graphics.height) - 136
if @Arrow.x<-250
@Arrow.x = $game_map.events[$talkingEvent].screen_x
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow3")
end
if @Arrow.x>=256
@Arrow.x-=15# = $game_map.events[$talkingEvent].screen_x-Graphics.width
@Arrow.bitmap = BitmapCache.load_bitmap("Graphics/Pictures/Arrow3")
end
else
@Outofrange=false
end
@Arrow.zoom_x = 2
@Arrow.zoom_y = 2
end
end
msgwindow=Window_AdvancedTextPokemon.new("")
if !viewport
msgwindow.z=99999
else
msgwindow.viewport=viewport
end
msgwindow.visible=true
msgwindow.letterbyletter=true
msgwindow.back_opacity=MessageConfig::WindowOpacity
pbBottomLeftLines(msgwindow,2)
$game_temp.message_window_showing=true if $game_temp
$game_message.visible=true if $game_message
skin=MessageConfig.pbGetSpeechFrame() if !skin
msgwindow.setSkin(skin)
return msgwindow
end

def Kernel.pbDisposeMessageWindow(msgwindow)
$game_temp.message_window_showing=false if $game_temp
$game_message.visible=false if $game_message
msgwindow.dispose
@Arrow.dispose if @Arrow
@Restriction.dispose if @Restriction
end



class FaceWindowVX < SpriteWindow_Base
def initialize(face)
super(0,0,128,128)
faceinfo=face.split(",")
facefile=pbResolveBitmap("Graphics/Faces/"+faceinfo[0])
facefile=pbResolveBitmap("Graphics/Pictures/"+faceinfo[0]) if !facefile
self.contents.dispose if self.contents
@faceIndex=faceinfo[1].to_i
@facebitmaptmp=AnimatedBitmap.new(facefile)
@facebitmap=BitmapWrapper.new(96,96)
@facebitmap.blt(0,0,@facebitmaptmp.bitmap,Rect.new(
(@faceIndex % 4) * 96,
(@faceIndex / 4) * 96, 96, 96
))
self.contents=@facebitmap
end

def update
super
if @facebitmaptmp.totalFrames>1
@facebitmaptmp.update
@facebitmap.blt(0,0,@facebitmaptmp.bitmap,Rect.new(
(@faceIndex % 4) * 96,
(@faceIndex / 4) * 96, 96, 96
))
end
end

def dispose
@facebitmaptmp.dispose
@facebitmap.dispose if @facebitmap
super
end
end



def itemIconTag(item)
return "" if !item
if item.respond_to?("icon_name")
return sprintf("<icon=%s>",item.icon_name)
else
ix=item.icon_index % 16 * 24
iy=item.icon_index / 16 * 24
return sprintf("<img=Graphics/System/Iconset|%d|%d|24|24>",ix,iy)
end
end

def getSkinColor(windowskin,color,isDarkSkin)
if !windowskin || windowskin.disposed? ||
windowskin.width!=128 || windowskin.height!=128
textcolors=[
shadowc3tag(MessageConfig::BUBBLETEXTBASE, MessageConfig::BUBBLETEXTSHADOW),
"<c2=7E105D08>",
"<c2=421F2117>",
"<c2=43F022E8>",
"<c2=7FF05EE8>",
"<c2=7E1F5D17>",
"<c2=43FF22F7>",
"<c2=63184210>",
"<c2=7FFF5EF7>"
]
color=0 if color>textcolors.length
return textcolors[color]
else # VX windowskin
color=0 if color>=32
x = 64 + (color % 8) * 8
y = 96 + (color / 8) * 8
pixel=windowskin.get_pixel(x, y)
return shadowctagFromColor(pixel)
end
end

# internal function
def pbRepositionMessageWindow(msgwindow, linecount=2)
msgwindow.height=32*linecount+msgwindow.borderY
msgwindow.y=(Graphics.height)-(msgwindow.height)
if $game_temp && $game_temp.in_battle && !$scene.respond_to?("update_basic")
msgwindow.y=0
elsif $game_system && $game_system.respond_to?("message_position")
case $game_system.message_position
when 0 # up
msgwindow.y=0
when 1 # middle
msgwindow.y=(Graphics.height/2)-(msgwindow.height/2)
when 2
@OpposedValue = 0
@NegativeValue = 0
if $Bubble==1
msgwindow.setSkin("Graphics/windowskins/frlgtextskin")
msgwindow.height = 100
msgwindow.width = 400
msgwindow.resizeToFit2(msgwindow.text,400,100)
msgwindow.x = $game_map.events[$talkingEvent].screen_x
msgwindow.y = $game_map.events[$talkingEvent].screen_y - (32 + msgwindow.height)
if msgwindow.y>(Graphics.height-msgwindow.height)
msgwindow.y = (Graphics.height-msgwindow.height)
elsif msgwindow.y<0
msgwindow.y+=msgwindow.height
end
if msgwindow.x>(Graphics.width-msgwindow.width)
msgwindow.x = ($game_map.events[$talkingEvent].screen_x-msgwindow.width)
elsif msgwindow.x<0
msgwindow.x+=(msgwindow.width)
end
$Bubble = 0
elsif $Bubble==2
msgwindow.setSkin("Graphics/windowskins/frlgtextskin")
msgwindow.height = 102
msgwindow.width = Graphics.width
if $game_player.direction==8
@Restriction = Viewport.new(0, 0, Graphics.width, 280)
msgwindow.y = 6
else
@Restriction = Viewport.new(0, 6 + msgwindow.height, Graphics.width, 280)
msgwindow.y = (Graphics.height - msgwindow.height) - 6
if @Outofrange==true
msgwindow.y = 6
end
end
$Bubble = 0
else
msgwindow.height = 102
msgwindow.y = Graphics.height - msgwindow.height - 6
end
end
end
if $game_system && $game_system.respond_to?("message_frame")
if $game_system.message_frame != 0
msgwindow.opacity = 0
end
end
if $game_message
case $game_message.background
when 1 # dim
msgwindow.opacity=0
when 2 # transparent
msgwindow.opacity=0
end
end
end

# internal function
def pbUpdateMsgWindowPos(msgwindow,event,eventChanged=false)
if event
if eventChanged
msgwindow.resizeToFit2(msgwindow.text,Graphics.width*2/3,msgwindow.height)
end
msgwindow.y=event.screen_y-48-msgwindow.height
if msgwindow.y<0
msgwindow.y=event.screen_y+24
end
msgwindow.x=event.screen_x-(msgwindow.width/2)
msgwindow.x=0 if msgwindow.x<0
if msgwindow.x>Graphics.width-msgwindow.width
msgwindow.x=Graphics.width-msgwindow.width
end
else
curwidth=msgwindow.width
if curwidth!=Graphics.width
msgwindow.width=Graphics.width
msgwindow.width=Graphics.width
end
end
end

# internal function

def pbGetGoldString
moneyString=""
if $Trainer
moneyString=_INTL("${1}",$Trainer.money)
else
if $data_system.respond_to?("words")
moneyString=_INTL("{1} {2}",$game_party.gold,$data_system.words.gold)
else
moneyString=_INTL("{1} {2}",$game_party.gold,Vocab.gold)
end
end
return moneyString
end

def pbDisplayGoldWindow(msgwindow)
moneyString=pbGetGoldString()
goldwindow=Window_AdvancedTextPokemon.new(_INTL("Money:\n<ar>{1}</ar>",moneyString))
goldwindow.setSkin("Graphics/Windowskins/goldskin")
goldwindow.resizeToFit(goldwindow.text,Graphics.width)
goldwindow.width=160 if goldwindow.width<=160
if msgwindow.y==0
goldwindow.y=Graphics.height-goldwindow.height
else
goldwindow.y=0
end
goldwindow.viewport=msgwindow.viewport
goldwindow.z=msgwindow.z
return goldwindow
end

def pbDisplayCoinsWindow(msgwindow,goldwindow)
coinString=($PokemonGlobal) ? $PokemonGlobal.coins : "0"
coinwindow=Window_AdvancedTextPokemon.new(_INTL("Coins:\n<ar>{1}</ar>",coinString))
coinwindow.setSkin("Graphics/Windowskins/goldskin")
coinwindow.resizeToFit(coinwindow.text,Graphics.width)
coinwindow.width=160 if coinwindow.width<=160
if msgwindow.y==0
coinwindow.y=(goldwindow) ? goldwindow.y-coinwindow.height : Graphics.height-coinwindow.height
else
coinwindow.y=(goldwindow) ? goldwindow.height : 0
end
coinwindow.viewport=msgwindow.viewport
coinwindow.z=msgwindow.z
return coinwindow
end

def pbRecord(arg); end

def pbMessageWaitForInput(msgwindow,frames,showPause=false)
return if !frames || frames<=0
if msgwindow && showPause
msgwindow.startPause
end
frames.times do
Graphics.update
Input.update
msgwindow.update if msgwindow
pbUpdateSceneMap
if Input.trigger?(Input::C) || Input.trigger?(Input::B)
break
end
end
if msgwindow && showPause
msgwindow.stopPause
end
end

def Kernel.pbMessageDisplay(msgwindow,message,letterbyletter=true,commandProc=nil)
return if !msgwindow
oldletterbyletter=msgwindow.letterbyletter
msgwindow.letterbyletter=(letterbyletter ? true : false)
ret=nil
count=0
commands=nil
facewindow=nil
goldwindow=nil
coinwindow=nil
cmdvariable=0
cmdIfCancel=0
msgwindow.waitcount=0
autoresume=false
text=message.clone
msgback=nil
linecount=(Graphics.height>400) ? 3 : 2
### Text replacement
text.gsub!(/\\\\/,"\5")
if $game_actors
text.gsub!(/\\[Nn]\[([1-8])\]/){
m=$1.to_i
next $game_actors[m].name
}
end
text.gsub!(/\\[Ss][Ii][Gg][Nn]\[([^\]]*)\]/){
next "\\op\\cl\\ts[]\\w["+$1+"]"
}
text.gsub!(/\\[Pp][Nn]/,$Trainer.name) if $Trainer
text.gsub!(/\\[Pp][Mm]/,_INTL("${1}",$Trainer.money)) if $Trainer
text.gsub!(/\\[Nn]/,"\n")
text.gsub!(/\\\[([0-9A-Fa-f]{8,8})\]/){ "<c2="+$1+">" }
text.gsub!(/\\[Bb]/,"<c2=6546675A>")
text.gsub!(/\\[Rr]/,"<c2=043C675A>")
text.gsub!(/\\1/,"\1")
colortag=""
isDarkSkin=isDarkWindowskin(msgwindow.windowskin)
if ($game_message && $game_message.background>0) ||
($game_system && $game_system.respond_to?("message_frame") &&
$game_system.message_frame != 0)
colortag=getSkinColor(msgwindow.windowskin,0,true)
else
colortag=getSkinColor(msgwindow.windowskin,0,isDarkSkin)
end
text.gsub!(/\\[Cc]\[([0-9]+)\]/){
m=$1.to_i
next getSkinColor(msgwindow.windowskin,m,isDarkSkin)
}
begin
last_text = text.clone
text.gsub!(/\\[Vv]\[([0-9]+)\]/) { $game_variables[$1.to_i] }
end until text == last_text
begin
last_text = text.clone
text.gsub!(/\\[Ll]\[([0-9]+)\]/) {
linecount=[1,$1.to_i].max;
next ""
}
end until text == last_text
text=colortag+text
### Controls
textchunks=[]
controls=[]
while text[/(?:\\([WwFf]|[Ff][Ff]|[Tt][Ss]|[Cc][Ll]|[Mm][Ee]|[Ss][Ee]|[Ww][Tt]|[Ww][Tt][Nn][Pp]|[Cc][Hh])\[([^\]]*)\]|\\([Gg]|[Cc][Nn]|[Ww][Dd]|[Ww][Mm]|[Oo][Pp]|[Cc][Ll]|[Ww][Uu]|[\.]|[\|]|[\!]|[\x5E])())/i]
textchunks.push($~.pre_match)
if $~[1]
controls.push([$~[1].downcase,$~[2],-1])
else
controls.push([$~[3].downcase,"",-1])
end
text=$~.post_match
end
textchunks.push(text)
for chunk in textchunks
chunk.gsub!(/\005/,"\\")
end
textlen=0
for i in 0...controls.length
control=controls[i][0]
if control=="wt" || control=="wtnp" || control=="." || control=="|"
textchunks[i]+="\2"
elsif control=="!"
textchunks[i]+="\1"
end
textlen+=toUnformattedText(textchunks[i]).scan(/./m).length
controls[i][2]=textlen
end
text=textchunks.join("")
unformattedText=toUnformattedText(text)
signWaitCount=0
haveSpecialClose=false
specialCloseSE=""
for i in 0...controls.length
control=controls[i][0]
param=controls[i][1]
if control=="f"
facewindow.dispose if facewindow
facewindow=PictureWindow.new("Graphics/Pictures/#{param}")
elsif control=="op"
signWaitCount=21
elsif control=="cl"
text=text.sub(/\001\z/,"") # fix: '$' can match end of line as well
haveSpecialClose=true
specialCloseSE=param
elsif control=="se" && controls[i][2]==0
startSE=param
controls[i]=nil
elsif control=="ff"
facewindow.dispose if facewindow
facewindow=FaceWindowVX.new(param)
elsif control=="ch"
cmds=param.clone
cmdvariable=pbCsvPosInt!(cmds)
cmdIfCancel=pbCsvField!(cmds).to_i
commands=[]
while cmds.length>0
commands.push(pbCsvField!(cmds))
end
elsif control=="wtnp" || control=="^"
text=text.sub(/\001\z/,"") # fix: '$' can match end of line as well
end
end
if startSE!=nil
pbSEPlay(pbStringToAudioFile(startSE))
elsif signWaitCount==0 && letterbyletter
pbPlayDecisionSE()
end
########## Position message window ##############
msgwindow.text=text
pbRepositionMessageWindow(msgwindow,linecount)
if $game_message && $game_message.background==1
msgback=IconSprite.new(0,msgwindow.y,msgwindow.viewport)
msgback.z=msgwindow.z-1
msgback.setBitmap("Graphics/System/MessageBack")
end
if facewindow
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
facewindow.viewport=msgwindow.viewport
facewindow.z=msgwindow.z
end
atTop=(msgwindow.y==0)
########## Show text #############################
#msgwindow.text=text
Graphics.frame_reset if Graphics.frame_rate>40
begin
if signWaitCount>0
signWaitCount-=1
if atTop
msgwindow.y=-(msgwindow.height*(signWaitCount)/20)
else
msgwindow.y=Graphics.height-(msgwindow.height*(20-signWaitCount)/20)
end
end
for i in 0...controls.length
if controls[i] && controls[i][2]<=msgwindow.position && msgwindow.waitcount==0
control=controls[i][0]
param=controls[i][1]
if control=="f"
facewindow.dispose if facewindow
facewindow=PictureWindow.new("Graphics/Pictures/#{param}")
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
facewindow.viewport=msgwindow.viewport
facewindow.z=msgwindow.z
elsif control=="ts"
if param==""
msgwindow.textspeed=-999
else
msgwindow.textspeed=param.to_i
end
elsif control=="ff"
facewindow.dispose if facewindow
facewindow=FaceWindowVX.new(param)
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
facewindow.viewport=msgwindow.viewport
facewindow.z=msgwindow.z
elsif control=="g" # Display gold window
goldwindow.dispose if goldwindow
goldwindow=pbDisplayGoldWindow(msgwindow)
elsif control=="cn" # Display coins window
coinwindow.dispose if coinwindow
coinwindow=pbDisplayCoinsWindow(msgwindow,goldwindow)
elsif control=="wu"
msgwindow.y=0
atTop=true
msgback.y=msgwindow.y if msgback
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
msgwindow.y=-(msgwindow.height*(signWaitCount)/20)
elsif control=="wm"
atTop=false
msgwindow.y=(Graphics.height/2)-(msgwindow.height/2)
msgback.y=msgwindow.y if msgback
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
elsif control=="wd"
atTop=false
msgwindow.y=(Graphics.height)-(msgwindow.height)
msgback.y=msgwindow.y if msgback
pbPositionNearMsgWindow(facewindow,msgwindow,:left)
msgwindow.y=Graphics.height-(msgwindow.height*(20-signWaitCount)/20)
elsif control=="."
msgwindow.waitcount+=Graphics.frame_rate/4
elsif control=="|"
msgwindow.waitcount+=Graphics.frame_rate
elsif control=="wt" # Wait
param=param.sub(/\A\s+/,"").sub(/\s+\z/,"")
msgwindow.waitcount+=param.to_i*2
elsif control=="w" # Windowskin
if param==""
msgwindow.windowskin=nil
else
msgwindow.setSkin("Graphics/Windowskins/#{param}")
end
msgwindow.width=msgwindow.width # Necessary evil
elsif control=="^" # Wait, no pause
autoresume=true
elsif control=="wtnp" # Wait, no pause
param=param.sub(/\A\s+/,"").sub(/\s+\z/,"")
msgwindow.waitcount=param.to_i*2
autoresume=true
elsif control=="se" # Play SE
pbSEPlay(pbStringToAudioFile(param))
elsif control=="me" # Play ME
pbMEPlay(pbStringToAudioFile(param))
end
controls[i]=nil
end
end
break if !letterbyletter
Graphics.update
Input.update
facewindow.update if facewindow
if $DEBUG && Input.trigger?(Input::F6)
pbRecord(unformattedText)
end
if autoresume && msgwindow.waitcount==0
msgwindow.resume if msgwindow.busy?
break if !msgwindow.busy?
end
if (Input.trigger?(Input::C) || Input.trigger?(Input::B))
if msgwindow.busy?
pbPlayDecisionSE() if msgwindow.pausing?
msgwindow.resume
else
break if signWaitCount==0
end
end
pbUpdateSceneMap
msgwindow.update
yield if block_given?
end until (!letterbyletter || commandProc || commands) && !msgwindow.busy?
Input.update # Must call Input.update again to avoid extra triggers
msgwindow.letterbyletter=oldletterbyletter
if commands
$game_variables[cmdvariable]=Kernel.pbShowCommands(
msgwindow,commands,cmdIfCancel)
$game_map.need_refresh = true if $game_map
end
if commandProc
ret=commandProc.call(msgwindow)
end
msgback.dispose if msgback
goldwindow.dispose if goldwindow
coinwindow.dispose if coinwindow
facewindow.dispose if facewindow
if haveSpecialClose
pbSEPlay(pbStringToAudioFile(specialCloseSE))
atTop=(msgwindow.y==0)
for i in 0..20
if atTop
msgwindow.y=-(msgwindow.height*(i)/20)
else
msgwindow.y=Graphics.height-(msgwindow.height*(20-i)/20)
end
Graphics.update
Input.update
pbUpdateSceneMap
msgwindow.update
end
end
return ret
end


Thanks for help beforehand.

ahm you could make the windowskin a bit larger
(the simplest way to do this)

Pokegod7020
June 1st, 2014, 07:51 AM
Even after looking through all the posts here, I still cannot figure out how to have the speech bubble get to the bottom of the screen when the event talking is on the top of the screen. Can someone help? Like, the speech bubble is covering the event....

Pokegod

Pokegod7020
June 21st, 2014, 04:41 PM
Hello.

I am using the Speech Bubble System by Carmaniac, and have encountered a problem. The script works fine and all, but I have a scene in my game where the scene is laid out as follows.


Giratina
Dialga Palkia
Arceus

And when giratina speaks, it covers his sprite. How would I fix this? I have already asked on the script section, and have waited 20 days, but nobody has posted anything new post wise, or anything in general on that thread. How would I fix this?


Thanks

Pokegod

Roaming Murkrow
June 21st, 2014, 10:25 PM
There is a scroll map event command. Just mess with it till Giratina isn't covered

Pokegod7020
June 23rd, 2014, 06:47 AM
That seemed so much easier than I thought. THANKS ROAMINGMURKROW

:D :D :D :D :D D :D :D :D :D :D

theRiolvile2
June 26th, 2014, 05:17 AM
how do you use this for Ds essentials.
To make it work normally what do you need to change in the script.

Pokegod7020
June 29th, 2014, 06:42 AM
It should work automatically for DS Essentials.

carmaniac
July 2nd, 2014, 04:57 AM
Sorry everyone for not replying on here lately, got too engrossed with sorting life out in general. This script is pretty outdated now with a fair amount of bugs, I've unfortunately got very little intention in getting back into game development any time soon so seems the script may be inactive for a while when it comes to the updates side of things. If I see fit to do so, I may come back to essentials at a future date to continue making addons.

The script at the moment is not compatible with the DS Essentials project, though isn't too hard to go around line 1200 in pokemon messages and play around with the viewports of the code. Sorry for the lack of updates and replys everyone, hope to soon get back into the community when I get time.