Jump to content
Unity Insider Forum

Text per Script manipulieren


TerepN

Recommended Posts

Hallo

In meinem 2D-Spiel(Unity 2020.3.6f1 (64-bit)) habe ich einen UI-Button generiert. Mittels Script habe ich public int Variablen hinterlegt, die die zufällig erzeugten Zahlen in der Buttonkomponente Script auch anzeigen.

Im nächsten Schritt habe ich ein GameObject.UI.Text mit der Bezeichnung Text Wuerfelwert erstellt und im Spiel platziert. Auch ok.

Nun stellt sich die Frage, wie spreche ich per Script das GameObject.UI.Text an, um hier den Text zu ändern, oder auch um später die Avatare zu bewegen?

Wenn ein GameObjekt als Klasse zu sehen ist und ich davon eine Instanz erzeuge und ich im Inspector anschließend den Namen Wuerfelwert hinterlege, dann muss ich doch über diesen Namen das Objekt aufrufen können und es möglich sein dieses Objekt  mittels Punkt-Operator zu  manipulieren?  Aber ich bekomme per Script keinen Zugriff.  Ohne Unity hätte ich damit kein Problem.

Also konkret, wie spreche ich per Script meine erzeugten Objekte an?

TerepN

Link zu diesem Kommentar
Auf anderen Seiten teilen

Also.
Du musst natürlich das GameObjekt oder aber einfach die Komponente kennen, mit dem Du kommunizieren willst.

Ist das Objekt schon in der Szene drin, kannst du es einfach im Inspector auf eine vorgefertigte Variable selben Typs fallen lassen. Wenn nicht, musst du einen Weg schaffen, dass sich ein neues Objekt irgendwo anmeldet oder aber dass es zur rechten Zeit einmalig gesucht wird. Aber das ist ja eine Sache für sich.

Ich erkläre dir erst einmal die Kommunikation.

Du hast diese Textkomponente in der Szene und irgend ein Anderes Objekt, welches dieser Komponente einen String übergeben will.

Leg z.B. eine public Variable vom Typ Text in deinem Script an. Damit du den Typ Text nutzen kannst, musst du über Using die UnityEngine.UI hinzufügen.

using UnityEngine;
using UnityEngine.UI; // diesen Using Befehl nutzen, damit die Bibliothek bekannt ist.

public class TextVerwalter : MonoBehaviour
{
  public Text InfoText; // diese Variable ist im Inspector sichtbar und dort kann das TextObejkt einfach fallen gelassen werden
  
  void Update()
  {
    if(irgendwas)
    {
      InfoText.text="ich habe einen neuen Text!";
    }
  }
}

Wenn dieses Script jetzt so auf deinem Objekt liegt, welches den Text bearbeiten soll, dann siehst du im Inspector diese Variable mit einem leeren Slot.
Dort kannst du einfach das GameObject aus der Szene rein legen, welches die Textkomponente hat. Unity weiß, dass es nicht das GameOject selbst sein soll sondern nur dessen Text-Komponente und verknüpft sie, wie du sehen wirst.

Jetzt kennt dein Script diese Textkomponente / Klasse und kann die diversen Eigenschaften manipulieren. Wie z.B. den anzuzeigenden Text, dem du irgendeinen String übergeben kannst. (Siehe Codebeispiel)

So funktioniert das mit allen Komponenten, die du manipulieren willst. Du musst nur den Typ kennen und wissen welche Dinge veränderbar sind.

In der Unity Dokumentation findest du alle Properties und Methoden, die es bei den diversen Klassen gibt.

Hier: https://docs.unity3d.com/2017.3/Documentation/ScriptReference/UI.Text.html

 

Wenn du jetzt aber dieses Script auf dem selben GameObject hinzufügst, welches auch die Textkomponente hat, dann kannst du auch über GetComponent die Komponente direkt verknüpfen und musst nichts im Inspector hinzufügen.

Das will ich dir auch mal kurz zeigen.

 

using UnityEngine;
using UnityEngine.UI; 

public class TextVerwalter : MonoBehaviour
{
  Text InfoText; 
  
  void Start
  ( 
  // nach der Textkomponente suchen, die auch auf meinem Gameobject liegen sollte
  	InfoText=GetComponent<Text>(); // Schnapp dir die Textkomponente.
  }
  void Update()
  {
    if(irgendwas)
    {
      InfoText.text="ich habe einen neuen Text!";
    }
  }
}

GetComponent ist eine Methode von GameObject.
https://docs.unity3d.com/2017.3/Documentation/ScriptReference/GameObject.html

Wie du in der Dokumentation sehen kannst, gibt es da viele Methoden um GameObjekte und Komponenten zu finden und zu referenzieren.
 

Schau dir das mal ganz genau an. Denn in Unity geht es ganz oft über das Finden von Objekten oder einzelnen Komponenten. Ständig entstehen in Spielen neue Objekte oder werden zerstört. Was ja nicht schlimm ist. Aber wenn man mit diesen Dingen kommunizieren will, muss man wissen wo sie sind und wie man sie ansprechen kann.

Link zu diesem Kommentar
Auf anderen Seiten teilen

Hallo malzbie

Ich habe Deine Antwort 2 bis 3mal gelesen. Mein Grundgedanke war, dass in den Scripten alles nach den bekannten C-sharp-Regeln ein Dialog zwischen den Objekten läuft. Das heißt, jedes (Game)objekt schafft den Zugriff mittels den Operator new.

Unity kommuniziert mittels c-sharp. Daher kein new, sondern entweder direkt im Inspektor verknüpfen oder irgendwie den Zugriff auf das gewünschte Objekt schaffen um Informationen zu ziehen oder um es zu manipulieren.

Das ist für mich noch sehr theoretisch. Aber durch Dein Posting habe ich jetzt einen Einstieg. Da es wohl ein paar Tage dauert, bis ich es wirklich kapiert habe, wollte ich mich auf jeden Fall vorab bedanken.

Du gibst wirklich gute Ansätze, wie man sich das erarbeiten kann. Das motiviert, um weiter zu machen.

TerepN

Link zu diesem Kommentar
Auf anderen Seiten teilen

vor 2 Minuten schrieb TerepN:

jedes (Game)objekt schafft den Zugriff mittels den Operator new.

DAS ist aber keine gute Idee - Unity oder nicht. new erzeugt ein neues Objekt - Da wird kein Zugriff geschaffen, sondern etwas neues gebaut. Du willst aber nicht ständig neue Objekte bauen, sondern die existierenden benutzen. In Unity hast du halt den Fall, dass Unity die Objekte baut. Das muss so sein, weil Unitys Editor dir die Möglichkeit geben will, visuell deine Levels, Objekte, Menüs usw. zusammenzubauen anstatt da "blind" zu coden. Du erstellst also ein GameObject, speicherst die Szene, startest oder buildest das Spiel und das "new" übernimmt Unity für dich, indem es die Szenendatei anschaut und dann alle GameObjects erstellt, die du im Editor angelegt hast.

An die Dinger ranzukommen ist also eine Frage danach, die Mittel zu kennen, die Unity dir bereitstellt. GameObject.Find wäre da ein Beispiel, aber halt ein ganz schlechtes. Dinge, die zusammengehören, kommen auf dasselbe GameObject und das eine sucht das andere mit GetComponent heraus, wie @malzbie als zweites schreibt. Sachen, die Teil des Leveldesigns sind, wie "Knopf A öffnet Tür X" machst du am besten über serialisierte Felder, wie bei seinem ersten Code. Da ziehst du die Tür in den Knopf und definierst damit, dass das die zu öffnende Tür ist und keine andere. Wenn der Spieler in einen Bereich läuft, nutzt du vermutlich OnTriggerEnter, um den Spieler und den Bereich einander vorzustellen. Da gibt's noch ein paar mehr Sachen... und mach dir keine Sorgen, wenn das auf Anhieb nach viel aussieht. Ist es nämlich auch. Da kann man auch nach 20 Jahren (kein Witz) noch dazulernen. Taste dich da also langsam ran und lasse dich nicht entmutigen :)

Link zu diesem Kommentar
Auf anderen Seiten teilen

Ich tue mich schwerer als erwartet. Mein Script habe ich dem UI.Button zugefügt. Es funktioniert im Inspector und in der Consolenausgabe:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

public class Wuerfeln : MonoBehaviour
{
    public int wurf1, wurf2;
    public int wurfWert;
    public bool istPasch;
   
    public void OnClick()
    {
        istPasch = false;
        wurf1 = Random.Range(1, 7);
        wurf2 = Random.Range(1, 7);
        wurfWert = wurf1 + wurf2;

        if ( wurf1 == wurf2) istPasch = true;
        Debug.Log("" + wurf1 + " + " + wurf2 + " = " + wurfWert);
     }
}

 Meine Herausforderung. Ich möchte die jeweiligen Würfelwerte anfangs als Werte in einem UI-Text ausgeben. Hört sich einfach an, ich bekomme es leider nicht geregelt.

Sorry, anfangs hatte ich versucht, Unity mittels Udemy zu lernen und habe Projekte abgetippt in dem Glauben, etwas zu lernen. Es war wohl ein Irrtum. Ein eigenes Projekt zeigt leider erhebliche Defizite. Ich hoffe, Ihr helft mir weiter und erklärt mir, wie ich die Würfelwerte in ein Textfeld bringe. In C-sharp würde ich mein Brettspiel umsetzen können und hoffe noch auf einen Einstieg in Unity. 

Terep

Link zu diesem Kommentar
Auf anderen Seiten teilen

Ich füge dir das nötige einfach mal in deinen Code ein.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

public class Wuerfeln : MonoBehaviour
{
    public int wurf1, wurf2;
    public int wurfWert;
    public bool istPasch;
    public Text AusgabeTextfeld; // im Inspector dein UI Textelement hier rein ziehen
   
    public void OnClick()
    {
        istPasch = false;
        wurf1 = Random.Range(1, 7);
        wurf2 = Random.Range(1, 7);
        wurfWert = wurf1 + wurf2;

        if ( wurf1 == wurf2) istPasch = true;
        Debug.Log("" + wurf1 + " + " + wurf2 + " = " + wurfWert);
        AusgabeTextfeld.text="" + wurf1 + " + " + wurf2 + " = " + wurfWert; // Hier wird ganz einfach der Text mit dem String gefüllt.
     } 
}

Du musst also einfach ein UI Textelement. z.B. ein Label in deiner Szene dem Canvas hinzufügen und so groß machen, dass es den Text ganz aufnehmen kann.
Dann nimmst du dir dieses Objekt und lässt es im Inspector auf den Slot im Script fallen, der da AusgabeTextfeld heißt.

Das war's. :)

Link zu diesem Kommentar
Auf anderen Seiten teilen

Dank Eurer Hilfe habe ich einen Einstieg in Unity gefunden. Meine erste Spielfigur bewegt sich mittels Würfelzahl auf die entsprechenden Brettfelder( mittels Gimp-Grafik). Die Feldnamen und Anzahl der Runden werden angezeigt. Meinen Quellcode würde ich aber niemanden zeigen wollen. Er ist sehr c-sharp lastig. Unity ist noch sehr borstig zu mir. Aber egal; als nächstes kommen mehrere Figuren mit Namen und dann die üblichen Aktivitäten die auf den einzelnen Feldern auszuführen sind. Das wird wohl bis Weihnachten dauern.

Im Prinzip ignoriere ich Unity weitestgehend und versuche alles über Scripte zu regeln. Es ist nicht elegant und wohl auch aufwendig, wie ich zum Beispiel die xy-Koordinaten in 2 Arrays hinterlegt habe, aber irgendwann werde ich es updaten. Also noch einmal danke.

Es ist wohl nur eine Zeitfrage bis ich mich wieder melde. Bis dann

 

TerepN

Link zu diesem Kommentar
Auf anderen Seiten teilen

Archiviert

Dieses Thema ist jetzt archiviert und für weitere Antworten gesperrt.

×
×
  • Neu erstellen...