Anmelden

Archiv verlassen und diese Seite im Standarddesign anzeigen : Problem mit Dialogsystem in GameMaker: Studio



Kurojin
24.09.2016, 15:22
Hallo Leute,
da sich hier einige auch mit GameMaker:Studio befassen, möchte ich hier mal mein Problem schildern...vielleicht kann mir ja jemand helfen, da ich schon regelrecht verzweifle XD

Es geht um ein Programmierproblem bei einem Dialogsystem. Da es explizit um den GameMaker geht poste ich es mal hier. Um es möglichst kurz zu machen:
Ich habe einen NPC und ein Schild erstellt. Der NPC soll anfangen seinen Text zu sprechen, wenn der Spieler eine bestimmte Taste drückt, beim Schild das gleiche. Beide Objekte besitzen den gleichen Code.
Das Problem besteht darin, dass der Text zwar angezeigt wird, aber dieser vom Text des anderen Objektes überlappt wird. Im Klartext: Beide Objekte führen ihren Code zur selben Zeit aus und ich kriege einfach nicht raus warum...ich befasse mich seit ner Woche mit nichts anderem, aber ich kriegs nicht raus. Ich denke, dass es etwas mit dem Step-Event zu tun hat, aber ich wüsste nicht was. Vielleicht hab ich da nen Logikfehler, da ich mich auch noch nicht soo lange mit dem GameMaker befasse.

Da ich HIlfe brauche, komme ich nicht drum herum den Code zu posten. Ich würde dennoch darum bitte, diesen nicht einfach so zu verwenden. Der Code befindet sich im Spoiler:

// Create Event




textbox_en = false;

message[0] = "Hello there!";
message[1] = "I'm a NPC!";
message[2] = "I'm here go going on your nerves every time you talk to me.";
message[3] = "Have fun!";
message[4] = "And don't forget to change your underwear!";

message_current = 0; //0 is the first number in our array, and the message we are currently at
message_end = 5; //6 is the last number in our array
message_draw = ""; //this is what we 'write' out. It's blank right now
increase = 1; //the speed at which new characters are added
characters = 0; //how many characters have already been drawn
hold = 0; //if we hold 'Z', the text will render faster

message_length = string_length(message[message_current]); //get the number of characters in the first message



// Step Event



if(global.input == 0 && global.status_en == false)
{
if(keyboard_check(vk_space) && distance_to_object(obj_player) < 4 && textbox_en == false)
{
if (!instance_exists(obj_textbox))
{
instance_create(view_xview[0]+238, view_yview[0], obj_textbox);

}
if (instance_exists(obj_textbox))
{
global.move = false;
textbox_en = true;
obj_textbox.visible = true;
}

}

if (textbox_en == true)
{


if (characters < message_length) //if current character count is less than the amount in current message*
{
hold = keyboard_check(ord('X')); //hold is true or false if 'X' is hold or not
characters += increase * (1 + hold); //increase speed based on hold
message_draw = string_copy(message[message_current], 0, characters); //copy string to current character

if (characters >= message_length)
{
obj_textbox.image_speed = .1;
}

else if (characters != message_length)
{
obj_textbox.image_index = 0;
}

}

else { //if current character is more than the amount in the current message
if (keyboard_check_pressed(ord('X'))) //if we press X...
{
if (message_current < message_end) //if there are more messages left to show
{
message_current += 1; //increase the message by 1
message_length = string_length(message[message_current]); //get the new character length for message
characters = 0; //set the characters back to 0
message_draw = ""; //clear the drawn text
}

else {
if (keyboard_check_pressed(ord('X')))
{

if (message_current >= message_end) //if the messages are done
{


characters = 0;
message_draw = "";
message_length = string_length(message[message_current]);

obj_textbox.image_index = 0;
obj_textbox.visible = false;
textbox_en = false;
with (obj_textbox) instance_destroy(); //destroy the object
global.move = true;
}
}
}
}
}
}
}



// Draw Event


draw_self();
if(textbox_en == true && instance_exists(obj_textbox))
{

draw_sprite(obj_textbox.sprite_index, 0, view_wview[0]/2 - 10, view_yview[0]);
draw_set_colour(c_white);
draw_set_halign(fa_left);
draw_set_valign(fa_top);
draw_text_ext(view_xview[0]+80, view_yview[0]+15, message_draw, 5, 320); //draw the text at the coordinates
}



Vielen Dank im Voraus :)

Schotti
24.09.2016, 18:05
Wenn der Spieler am NPC oder Schild dran ist und space drückt, wird obj_textbox erschaffen. Das Problem: im Drawevent des NPCs UND des Schildes wird dieses Objekt über instance_exists(obj_textbox) abgefragt und mit true beantwortet. Ergo werden beide Draw-Events ausgeführt. Du musst dem Objekt beibringen, dass er nach DEM obj_textbox checken soll, welches von dem Objekt und keinem anderen erschaffen wurde. Das geht z.B. über IDs. Einfache Lösung:

Ergänze das Create Event mit diesem Codesnippet
Create:


textbox_id = -1;

Der Wert von -1 bedeutet, dass kein obj_textbox von diesem Objekt erschaffen wurde.

Verbessere den Step-Event mit folgendem Snippet:
Step:


if (textbox_id = -1)
{
textbox_id = instance_create(view_xview[0]+238, view_yview[0], obj_textbox);

}

Wenn kein obj_textbox vom Objekt erschaffen wurde (textbox_id = -1), dann erschafft er das obj_textbox und speichert die ID davon in textbox_id ab. Jetzt kannst du alle weiteren Abfragen in deinem Step- und Draw-Events daran anpassen und ein anderes Objekt wird nicht durch ein fremdes obj_textbox getriggert. Ich hoffe, meine Ausführungen waren soweit verständlich! :D

Viel Erfolg!

Kurojin
24.09.2016, 18:37
Schotti, ich danke dir schon mal. Ja deine Ausführen waren für mich schon verständlich ^^
Jetzt spricht jeder seinen Satz aus dem Array, aber scheinbar ist da immer noch der Wurm drin ^^" Wenn ich den NPC oder das Schilöd nun anspreche, bekomme ich diesen Error:




___________________________________________
############################################################################################
FATAL ERROR in
action number 1
of Draw Event
for object obj_test_npc:

Unable to find any instance for object index '7' name 'obj_textbox'
at gml_Object_obj_test_npc_DrawEvent_1 (line 5) - draw_sprite(obj_textbox.sprite_index, 0, view_wview[0]/2 - 10, view_yview[0]);
############################################################################################



Ich blick da grade echt nix mehr XD Wenn ich den instance_destroy Befehl auskommentiere taucht der Fehler nicht mehr auf, aber das Array wird nicht zurückgesetzt...Die Instanz soll ja aus performancegründen zerstört werden oder hat das nicht so viel Einfluss?
Btw: Kann man statt textbox_id = -1 auch textbox_id = 0 schreiben oder wird die -1 da besonders gewertet?

EDIT: Nochmal ein herzliches Dankeschön an Schotti für seine Unterstützung. Ich habe es nun hinbekommen :)