GameMaker [HELP] My textbox only works once

N

Nambuc

Guest
Hello there.

Beginner here, be nice :) And sorry for my approximative english.

I've been working for a few weeks with lots of different tutorials on this branching dialogue system for my game, which now works fine except for one thing: the textbox.

I don't know how to make its animation "reset" each time we have a new block of text to show.

So here's what happens when I run the game:
- for the first block of text, the textbox works perfectly: letter by letter, and drawing a rectangle with width and height depending on the string lenght. Everything as expected.
- but after the first branching, it doesn't work fine anymore: the text appears in one time (instead of letter by letter), and the rectangle height is stuck (but curiously, the width keeps changing correctly). No error message, no crash.

Here is the whole code of my object:

Create event:
Code:
//Choices buttons
menu_x = x+520;
menu_y = y+250;
button_h = 24;
button_w = 256;
button_padding = 8;

button[0] = "PROVOKE"
button[1] = "REASSURE"
button[2] = "INTERPRET"
button[3] = "KEEP SILENT"
buttons = array_length_1d(button);

menu_index = 0;
last_selected = 0;

var i = 0
repeat(buttons) {
    unfold[i] = 0;
    i++;
}


///Text
textMap = ds_map_create();
key = "";

spd = 0.35;
letters = 0;
txt = "";
length = string_length (txt);
text_current = "";
w = 0;
h = 0;
border = 10;

//Booleans (true or false)
question = false;

//Path example
ds_map_add(textMap,"","Paul:\n\nSir...I'm...\nnot going very well these days.");
ds_map_add(textMap,"E","Can't sleep.\nCan't wake up.\nCan't go outside.\n*");
ds_map_add(textMap,"E0", "I'm provoking you.");
ds_map_add(textMap,"E1", "Be reassured, it's alright.");
ds_map_add(textMap,"E2", "I'm trying to interpret something.");
ds_map_add(textMap,"E3", "...");
//Etc.
Step event:
Code:
/// Progress Text
length = string_length(txt);
letters += spd;
text_current = string_copy(txt,1,floor(letters));

draw_set_font(fSign);
if (h == 0) h = string_height(txt);
w = string_width(text_current);


//Reseting the textbox? (not sure about that...)
if  (letters >= length) && ((keyboard_check_pressed(vk_space)) || (keyboard_check_pressed(vk_enter)))
{
    draw_text_speed("Reset");
}
                       

//Choose with up and down arrows
if (question == true) {
menu_move = keyboard_check_pressed(vk_down) - keyboard_check_pressed(vk_up);

menu_index += menu_move;
if (menu_index < 0) menu_index = buttons - 1;
if (menu_index > buttons -1) menu_index = 0;

var i = 0
repeat(buttons) {
    if unfold[i] == 1 i++;
   
    if (i < buttons) unfold[i] = min(1, unfold[i] + .02);
    if (i+1 < buttons) unfold[i+1] = min(1, unfold[i+1] + .005);
}

if (menu_index != last_selected) audio_play_sound(snDialogChoice,1,false);

last_selected = menu_index;
}
Draw event:
Code:
//Find branching in dialogues
txt = ds_map_find_value(textMap,key);
if (string_char_at(txt,string_length(txt)) == "*")
{
    question = true;  
}
else
{
    question = false;
}


//Draw the box
var halfw = w * 0.5;
draw_set_colour(c_black);
draw_set_alpha(0.5);
draw_roundrect_ext(x-halfw-border,y-h-(border*2),x+halfw+border,y,15,15,false);
draw_sprite(sMarker,0,x,y);
draw_set_alpha(1);

//Draw Text
DrawSetText(c_white, fSign, fa_center,fa_top);
draw_text(x,y-h-border,text_current);

//If question is false, you can press space
//If question is true, opens the choices menu
draw_set_font(fSpecial_Elite);
draw_set_color(c_red);
if (question == false)
{
    draw_text(x,y + 250/*pixels*/,"(Space) Continue");
}
else //Show interaction menu
    {      
                var i = 0;
        repeat(buttons) {
        draw_set_font(fDialogChoice);
        draw_set_halign(fa_right);
        draw_set_valign(fa_middle)
   
        xx = menu_x+256    * (1-unfold[i]);
        yy = menu_y + (button_h + button_padding) * i;
   
        draw_set_alpha(0.0);
        draw_set_color(c_maroon);
        draw_rectangle(xx - button_w/2, yy, xx - button_w/2 + button_w, yy + button_h, false);
       
        draw_set_color(c_ltgray);
       
        draw_set_alpha(1.0);
       
        if (menu_index == i) draw_set_color(c_red)
   
        draw_text(xx+120, yy + button_h/1.48, button[i]);
        i++;
    }
}


//Transition to another room
if (string_char_at(txt, string_length(txt)) == "1")
{
    room_goto(Room0);
}
Clean up event:
Code:
ds_map_destroy(textMap);
Press Space event:
Code:
//Continuing the dialogue with "space"
if (question == false)
{
    key += "E" ;
    draw_text_speed("Reset");
}
And Press Enter event:
Code:
/// Choices Menu

if (question == true) switch (menu_index)
        {
            case 0://provoke
                key += "0";
                draw_text_speed("Reset");
                audio_play_sound(snDialoguValid,1,false);
                break;
            case 1://reassure
                key += "1";
                draw_text_speed("Reset");
                audio_play_sound(snDialoguValid,1,false);
                break;
            case 2://interpret
                key += "2";
                draw_text_speed("Reset");
                audio_play_sound(snDialoguValid,1,false);
                break;  
            case 3://keep silent
                key += "3";
                draw_text_speed("Reset");
                audio_play_sound(snDialoguValid,1,false);
                break;
        }
Any ideas?
THANKS A LOT.
 

Phil Strahl

Member
Have you tried to destroy the textbox after a choice was made and create a new one for the next bit? That way your creation code would always run and set up things as preferred.

If you want to re-use the same text-box instance you also need to reset all the variables and data structures like you do in the create event, e.g. something like this
Code:
if (do_reset)
{
  do_reset = false; // so that this block only runs once. You need to create this variable and set it to true when you want to reset things, of course.
 
  // clear the map
  if (ds_exists(textMap, ds_type_map)) // just to be safe that the map exists at this point
  { 
    ds_map_clear(textMap);
  }

  key = "";
  letters = 0; 
  text_current = "";
}
I haven't thoroughly dissected your code, so there might be some things missing that also need to reset, but I think you get the idea :)
 
Top