Wie gehe ich bei GUI-Elementen vor?


12

Hinweis: Ich plane mein eigenes GUI-System zu erstellen. Es ist gut zum Lernen, leichtgewichtig, hat nur die Teile, die ich brauche, passt zum Spiel usw.

Ich habe darüber nachgedacht, wie es geht. Die Elemente, die ich meine, sind:

  • Radio Knöpfe
  • Geben Sie hier Textfelder ein
  • Tasten
  • Schieberegler
  • Kontrollkästchen

Ich bin noch nicht auf der Suche, wie ich sie herstellen soll. Aber mehr davon, wie sie gehen würden.

Idee

Ich hätte jeden Staat, der Zeug brauchte, also haben fast alle einen Container mit Elementen. Jedes Element ist ein GUI-Teil.

Diese haben jeweils eine Position, eine Grafik usw.

Das, woran ich mehr festhalte, ist die Logik von ihnen.

Meine Idee dafür, Modularität und Einfachheit zu ermöglichen, war, einen MainMenuStartButton zu vermeiden; einen OptionsOneBackButton usw. und stattdessen Slider slider1 ausführen können; oder Taste Start ;.

Stattdessen würde jeder eine boost :: -Funktion für eine Funktion in einem GUI-Namespace haben, z. B. Gui :: StartButtonClick oder GUI :: ColourSliderHover.

Ich habe mich nur gefragt, ob dies außergewöhnlich langsam sein würde oder nicht.

Und gibt es überhaupt eine einfache Möglichkeit, GUI für Spiele zu erstellen? Kein Qt, wxWidgets oder so.

Antworten:


15

GUI ist kein einfaches oder einfaches Problem, besonders wenn Sie sich mit Spielen beschäftigen und den Wunsch nach dynamischen, interessanten Menüs haben.

Eine "einfache" Sache, die Sie tun können, ist zu versuchen, Middleware zu verwenden. Es ist eine Frage , auf die hier .

Wenn Sie es selbst rollen wollen, gibt es ein paar Dinge, die ich vorschlagen würde.

  • GUI-Elemente haben im Allgemeinen ein "Elternelement", entweder ein anderes GUI-Element oder ein "Fenster" oder ähnliches. Wenn Sie entweder nach oben zeigen oder den übergeordneten Punkt nach unten zeigen, können Sie den Status / die Position / usw. für alles festlegen, was ein Kind ist.

  • Sie können GUI-Elemente nach Zusammensetzung erstellen. Viele Widgets haben Labels (fast alle), und es kann sinnvoll sein, das Konzept eines Labels zu einer Komponente oder einem untergeordneten Element Ihrer anderen UI-Elemente zu machen, anstatt den Code zu kopieren / einzufügen oder zu versuchen, von einer Basisklasse zu erben mit Etikettenfunktionalität.

  • Viele sogenannte spezialisierte Widgets sind nur versteckte Knöpfe. Kontrollkästchen sind nur Schaltflächen mit Status und speziellen Bildern. Optionsfelder sind nur Kontrollkästchen, die einen Metastatus (es ist jeweils nur eines aktiv) mit anderen Optionsfeldern aufweisen. Nutzen Sie dies zu Ihrem Vorteil. In einem Spiel, an dem ich gearbeitet habe, wurden "Kontrollkästchen" mit normalen Knöpfen ausschließlich durch Skripten und Kunst erstellt.

  • Ziehen Sie für Ihr erstes Projekt den direkteren Weg in Betracht. Ja, machen Sie Ihre umsetzbaren Ereignisdelegaten und weisen Sie zu, was Sie bei der Elementerstellung benötigen (z. B. onMouseButtonDown, onMouseButtonUp, onHover usw.), aber überlegen Sie sich, was Sie sonst tun möchten (z. B. Farbänderungen beim Hover, Tastentöne), bis Sie etwas erhalten funktionell. Wenn Sie an diesem Punkt angelangt sind, können Sie diese Verhaltensdaten erstellen (z. B. eine Variable auf der Schaltfläche für "Sound drücken") oder Komponenten verwenden, mit denen Ihre Benutzeroberflächenelemente das Verhalten definieren, das Sie ihnen beim Erstellen gerade zuordnen.

  • Teilnehmer sind nicht so langsam, Sie werden wahrscheinlich nicht so viele Widgets haben, dass es ein Problem wäre, und der Menücode ist im Allgemeinen ohnehin nicht so wirkungsvoll. An diesem Punkt im Spiel würde ich mir keine Sorgen um die Leistung machen. Wählen Sie keine naiven Algorithmen und Profile, sobald Sie Ihren Code zum Laufen gebracht haben.


2
Für komplexere GUI-Aufgaben benötigen Sie in Kürze eine Art Layout-Verwaltung. Grundlegende Layouts wie HBox und VBox sind viel einfacher zu verwenden als das Positionieren aller Elemente mit absoluten Koordinaten. Beispiel: web.archive.org/web/20100410150433/http://doc.qt.nokia.com/4.6/… Das macht Ihre GUI einfacher zu bedienen, aber nicht so einfach zu implementieren;)
bummzack

8

In den letzten Jahren gab es einige wirklich interessante Durchbrüche bei den Mainstream-UI-Toolkits. Die Benutzeroberflächen der Spiele haben sich ebenfalls weiterentwickelt, allerdings etwas langsamer. Dies liegt wahrscheinlich daran, dass die Entwicklung eines UI-Subsystems mit vollem Funktionsumfang für sich genommen ein bedeutendes Unterfangen darstellt und es schwierig ist, die Ressourceninvestition zu rechtfertigen.

Mein persönliches Lieblings-UI-System ist die Windows Presentation Foundation (WPF). Das Potenzial für die Benutzeroberflächendifferenzierung wird wirklich auf die nächste Ebene gehoben. Hier sind einige der interessanteren Funktionen:

  1. Steuerelemente sind standardmäßig "ohne Aussehen". Die Logik und das visuelle Erscheinungsbild eines Steuerelements sind im Allgemeinen entkoppelt. Jedes Steuerelement wird mit einem Standardstil und einer Standardvorlage ausgeliefert, die das standardmäßige Erscheinungsbild beschreiben. Beispielsweise kann eine Schaltfläche als abgerundetes Rechteck mit einem äußeren Strich, einer Volltonfarbe oder einem Hintergrund mit Farbverlauf und einem Inhaltspräsentator (um die Beschriftung zu präsentieren) dargestellt werden. Entwickler (oder Designer) können benutzerdefinierte Stilvorlagen erstellen, die das Erscheinungsbild und (in gewissem Umfang) das Verhalten eines Steuerelements ändern. Stile können verwendet werden, um einfache Eigenschaften eines Steuerelements zu überschreiben, z. B. Vordergrund- / Hintergrundfarbe, Vorlage usw .; Templates verändern die eigentliche visuelle Struktur.

  2. Stile und Vorlagen können "Trigger" enthalten. Trigger können auf bestimmte Ereignisse oder Eigenschaftswerte (oder Wertekombinationen) warten und Aspekte eines Stils oder einer Vorlage bedingt ändern. Beispielsweise hat eine Schaltflächenvorlage im Allgemeinen einen Auslöser für die Eigenschaft "IsMouseOver", um die Hintergrundfarbe zu ändern, wenn die Maus über die Schaltfläche bewegt wird.

  3. Es gibt einige verschiedene "Ebenen" von UI-Elementen, angefangen von leichteren Elementen mit minimaler Funktionalität bis hin zu umfassenden schwergewichtigen Steuerelementen. Dies gibt Ihnen Flexibilität bei der Strukturierung Ihrer Benutzeroberfläche. Die einfachste der UI-Elementklassen UIElementhat keinen Stil oder keine Vorlage und unterstützt nur das einfachste Eingabeereignis. Für einfache Elemente wie Statusanzeigen ist diese Funktionalität möglicherweise alles, was Sie benötigen. Wenn Sie eine umfangreichere Eingabehilfe benötigen, können Sie von FrameworkElement(die erweitert wird UIElement) ableiten . Herkömmliche Widgets sind im Allgemeinen von abgeleitet Control, wodurch FrameworkElement(unter anderem) die Unterstützung benutzerdefinierter Stile und Vorlagen erweitert und hinzugefügt wird.

  4. WPF verwendet ein beibehaltenes, skalierbares und auflösungsunabhängiges Vektorgrafikmodell. Unter Windows werden WPF-Anwendungen mit Direct3D gerendert und komponiert.

  5. Die Einführung von WPF beinhaltete eine neue deklarative Programmiersprache namens Xaml. Xaml, basierend auf XML, ist die bevorzugte Sprache für die Deklaration von "Szenen" auf der Benutzeroberfläche. Eigentlich ist es ziemlich clever und obwohl es auf den ersten Blick ähnlich aussieht, unterscheidet es sich grundlegend von existierenden Sprachen wie XUL (und viel mächtiger).

  6. WPF verfügt über ein sehr fortschrittliches Textsubsystem. Es unterstützt die meisten, wenn nicht alle OpenType-Schriftfunktionen, bidirektionales ClearType-Antialiasing, Subpixel-Positionierung usw.

"Ok, großartig, wie ist das für die Spieleentwicklung relevant?"

Als WPF noch in der Entwicklung war (und als "Avalon" bekannt war), belegte ich einen Videospiel-Designkurs bei Georgia Tech. Mein letztes Projekt war ein rundenbasiertes Strategiespiel, und ich wollte eine sehr leistungsfähige Benutzeroberfläche. WPF / Avalon schien mir ein guter Weg zu sein, da es einen vollständigen Satz voll funktionsfähiger Steuerelemente enthielt und ich die Möglichkeit hatte, das Erscheinungsbild dieser Steuerelemente vollständig zu ändern. Das Ergebnis war ein Spiel mit einer schönen und gestochen scharfen Benutzeroberfläche mit der Funktionalität, die Sie normalerweise nur in vollwertigen Anwendungen sehen.

Das Problem bei der Verwendung von WPF für Spiele ist, dass es ziemlich schwer ist und in einer eigenen "Sandbox" gerendert wird. Damit meine ich, dass es keine unterstützte Möglichkeit gibt, WPF in einer Direct3D- oder OpenGL-Spielumgebung zu hosten. Es ist möglich, Direct3D-Inhalte in einer WPF-Anwendung zu hosten. Die Framerate der WPF-Anwendung ist jedoch in der Regel niedriger als gewünscht. Für einige Arten von Spielen, wie z. B. 2D-Strategiespiele (Screenshot meines aktuellen WPF-Spielprojekts), könnte es immer noch großartig funktionieren. Für alles andere nicht so sehr. Sie können jedoch einige der überzeugenderen Architekturkonzepte von WPF bei der Entwicklung Ihres eigenen UI-Frameworks anwenden.

Es gibt auch eine Open-Source-Implementierung von WPF in nicht verwaltetem C ++ / Direct3D mit der Bezeichnung "WPF / G (WPF for Games)" ( http://wpfg.codeplex.com/ ), die speziell für die Verwendung in Spielen unter Win32 entwickelt wurde und Windows Mobile. Die aktive Entwicklung scheint aufgehört zu haben, aber das letzte Mal, als ich es ausprobierte, war es eine ziemlich vollständige Implementierung. Das Textsubsystem war derjenige Bereich, der im Vergleich zur WPF-Implementierung von Microsoft wirklich fehlte, aber für Spiele ist dies weniger ein Problem. Ich würde mir vorstellen, dass die Integration von WPF / G in eine Direct3D-basierte Game-Engine relativ einfach ist. Wenn Sie diesen Weg gehen, erhalten Sie möglicherweise ein äußerst leistungsfähiges, auflösungsunabhängiges UI-Framework mit umfassender Unterstützung für die Anpassung der Benutzeroberfläche.

Um Ihnen eine Vorstellung davon zu geben, wie die Benutzeroberfläche eines WPF-basierten Spiels aussehen könnte, hier ein Screenshot von meinem Lieblingsprojekt:

Screenshot von meinem aktuellen WPF-basierten Spielprojekt


NoesisGUI verwendet WPF. Es ist ziemlich gut, aber ich kenne WPF nicht und finde es schwierig zu lernen. Ich persönlich würde einen Web-Stack-Ansatz vorziehen.
user441521

2

Ich würde mich für eine sofortige Benutzeroberfläche entscheiden: http://code.google.com/p/nvidia-widgets/

Die nVidia-Widgets basieren auf IMGUI (Immediate GUI) von MollyRocket.

Ich denke, das ist so einfach, wie es eine grafische Benutzeroberfläche nur geben kann.

Alles hängt von Ihren Bedürfnissen ab.


1
Einfach, ja, und ideal für schnelle Debug-Arbeiten oder Prototyping, aber das Ausmaß der Kopplung zwischen der Benutzeroberfläche und Ihrer Spielelogik in Sofort-GUIs macht mir Angst.
Tenpn

2

In dem Spiel, an dem ich arbeite, haben wir unser eigenes GUI-Framework. Ich fand es sehr einfach, aber ich tue immer noch alles, was ich will. Ich weiß nicht, ob es ein "Muster" ist, das viele andere verwenden, aber es funktioniert gut für uns.

Grundsätzlich sind alle Schaltflächen, Kontrollkästchen usw. Unterklassen der Klasse Element. und Elemente haben Ereignisse. Dann haben wir CompoundElements (die selbst eine Unterklasse von Element sind), die andere Elemente enthalten. In jedem Zyklus werden drei Methoden aufgerufen: processEvent (Ereignis), tick (Zeit) und draw (Oberfläche). Jedes CompoundElement ruft dann diese Methoden für seine untergeordneten Elemente auf. In diesen Aufrufen (insbesondere der processEvent-Methode) werden alle relevanten Ereignisse ausgelöst.

All dies ist in Python (eine viel langsamere Sprache als C ++), und es läuft einwandfrei.


2

Wenn Sie ziemlich ausgefeilte Benutzeroberflächen benötigen, ist es wahrscheinlich die beste Wahl, nur einen HTML-Renderer einzubetten. Sie erhalten alle üblichen UI-Grundelemente, die Sie gewohnt sind, und Sie können Ihrem Spiel trivial komplexe Benutzeroberflächen hinzufügen, die sich so verhalten Benutzer erwarten, sehen großartig aus und arbeiten schnell (da Browser zu diesem Zeitpunkt über optimierte Rendering-Pipelines verfügen).

Es gibt einige Bibliotheken, die Webkit in Spiele einbetten: Berkelium ist diejenige, die ich empfehle, und ich höre, dass Awesomium ziemlich gut ist (von EVE Online verwendet) und CEF (von Steam verwendet). Sie können auch versuchen, Gecko einzubetten - es ist viel schwieriger, hat aber auch einige coole Vorteile. Ich verwende derzeit Berkelium für alle meine Spiele-Benutzeroberflächen (es hat eine Kombination aus benutzerdefinierten Benutzeroberflächenelementen und nativer Benutzeroberfläche ersetzt und die Menge an Code, die ich schreiben musste, um die Dinge zum Laufen zu bringen, drastisch reduziert).


^ Diese 100%. Ich bin traurig über das Fehlen eines guten Web-Stacks für Spiel-Implementierungen. Der Webstack ist hervorragend für die Benutzeroberfläche und muss in allen Spielen für die Benutzeroberfläche verwendet werden. Bisher waren die Bibliotheken, mit denen ich zu arbeiten versucht habe, ziemlich umständlich zu implementieren, oder sie sind nicht zu 100% html / css / javascript. Momentan schaue ich mir Coherent Labs an und es sieht vielversprechend aus, kostet aber eine ganze Menge, hat aber Indie-Versionen für ein paar Motoren.
user441521

2

Stellen Sie sicher, dass Sie tatsächlich ein ausgeklügeltes GUI-System für Ihr Spiel benötigen. Wenn Sie ein Computer-RPG erstellen, ist dies natürlich eine Voraussetzung. Aber für so etwas wie ein Rennspiel, mach es nicht zu kompliziert. Manchmal reicht es aus, nur Texturen (benutzerdefinierte Schaltflächenbilder) zu rendern und einige "if" -Anweisungen mit fest codierten Koordinaten in Ihrer Eingabefunktion zu haben. Ein Game State Machine (FSM) hilft bei diesem einfachen Ansatz. Oder vergessen Sie irgendwo in der Mitte die komplizierte Herangehensweise an Hierarchien und Szenendiagramme und haben Sie einfach eine "Button" -Klasse, die die oben genannten Textur- und Eingabeprüfungen in einfache Funktionsaufrufe packt, aber nichts Kompliziertes tut.

Das Festnageln Ihrer Anforderungen ist wichtig. Wenn Sie sich nicht sicher sind, erinnern Sie sich einfach an YAGNI .


1

Hier ist ein Beispiel (Quellcode und alles) einer GUI, die für OpenGL erstellt wurde, speziell für Slick2D mit dem Namen Thingle , einem Port von Thinlet .

Eine andere GUI für Slick2D war SUI , die Sie vielleicht ausprobieren möchten.

Ich würde diesen Beispielen folgen und mich für eine XML-gesteuerte Benutzeroberfläche entscheiden. Obwohl diese Projekte alt / tot sind, können Sie möglicherweise einige Ideen von ihnen aufgreifen.


1

Ich denke, eine der besten Möglichkeiten, dies herauszufinden, wäre, einen Blick darauf zu werfen, wie hochentwickelte GUI-Frameworks wie Windows Forms in .NET funktionieren.

Dies sind beispielsweise alle Steuerelemente, die eine Position, Größe, Liste der untergeordneten Steuerelemente, einen Verweis auf das übergeordnete Steuerelement, eine TextEigenschaft für alles , wofür das Steuerelement sie verwenden kann, sowie verschiedene überschreibbare Funktionen und vordefinierte Aktionen aufweisen.

Sie enthalten alle verschiedene Ereignisse wie Click, MouseOverund Resizing.

Wenn beispielsweise ein untergeordnetes Steuerelement geändert wird, sendet es eine Benachrichtigung an die Kette, dass sich das Layout geändert hat, und alle Eltern rufen dann an PerformLayout().

Automatische Größenanpassung und automatische Anordnung sind gemeinsame Merkmale dieser GUIs, sodass Programmierer Steuerelemente einfach hinzufügen und die übergeordneten Steuerelemente automatisch anpassen oder anordnen können.


1

Aus Interessengründen dachte ich, ich würde Scaleform rausschmeißen . Grundsätzlich können die Künstler Illustrator, Photoshop usw. verwenden, dann verwendet der UI-Designer Flash, um die gesamte Interaktivität zu gestalten. Dann wandelt Scaleform es in Code für Ihre Engine um (so verstehe ich es, da ich es nicht verwendet habe). Crysis Warhead nutzte dieses System für ihre Lobby.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.