-
-
Notifications
You must be signed in to change notification settings - Fork 65
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: UIElements Welcome Window (#510)
* Replaced GUI methods with UIElements 2019+ only * fix path issues for NG * add namespace * code smells * rename Mirror to MirrorNG * update URLs * remove template button and text * Update Assets/Mirror/Editor/WelcomeWindow/WelcomeWindow.cs * strings as const * rename method to be more clear on its purpose * move under Window submenu * better button names * Add UI Builder dependency * Move icon to uss * fix title font color in light background * Move button labels to xml * Move presentation content to xml * style cleanups * Don't repeat yourself * Remove unused stuff * Fix vs warnings * fix vs warnings * Get runtime version * path lookup should work with upm * ui builder fails to compile * fix smell Co-authored-by: Erikas <erikastaroza@gmail.com> Co-authored-by: Paul Pacheco <paulpach@gmail.com> Co-authored-by: Paul Pacheco <paul.pacheco@aa.com>
- Loading branch information
1 parent
7a7a1f7
commit 654c5e1
Showing
12 changed files
with
367 additions
and
0 deletions.
There are no files selected for viewing
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
110 changes: 110 additions & 0 deletions
110
Assets/Mirror/Editor/WelcomeWindow/Resources/WelcomeWindow.uss
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,110 @@ | ||
:root { | ||
--window-width: 500; | ||
--window-height: 600; | ||
--banner-color: rgb(12, 12, 12); | ||
--text-color: rgb(255, 255, 255); | ||
} | ||
|
||
#VersionText { | ||
height: 0; | ||
width: var(--window-width); | ||
font-size: 10px; | ||
color: var(--text-color); | ||
-unity-text-align: upper-right; | ||
position: relative; | ||
top: 5px; | ||
right: 5px; | ||
} | ||
|
||
#Banner { | ||
height: 64px; | ||
width: var(--window-width); | ||
background-color: var(--banner-color); | ||
} | ||
|
||
#Icon { | ||
height: 64px; | ||
width: 64px; | ||
align-self: center; | ||
background-color: rgb(255, 255, 255); | ||
} | ||
|
||
#Title { | ||
font-size: 30px; | ||
align-self: center; | ||
padding-top: 10px; | ||
padding-bottom: 10px; | ||
} | ||
|
||
#Header { | ||
font-size: 20px; | ||
-unity-font-style: bold; | ||
-unity-text-align: middle-left; | ||
padding-left: 10px; | ||
padding-right: 10px; | ||
padding-top: 10px; | ||
padding-bottom: 15px; | ||
white-space: normal; | ||
} | ||
|
||
#Description { | ||
font-size: 14px; | ||
-unity-text-align: upper-left; | ||
padding-left: 10px; | ||
padding-right: 10px; | ||
padding-bottom: 10px; | ||
padding-top: 5px; | ||
flex: 3; | ||
white-space: normal; | ||
} | ||
|
||
#Spacer { | ||
display: flex; | ||
flex: 0.02; | ||
} | ||
|
||
Button { | ||
padding: 2px; | ||
height: 50px; | ||
color: rgb(255, 255, 255); | ||
background-color: rgb(85, 85, 85); | ||
} | ||
|
||
Button:hover { | ||
background-color: rgb(95, 95, 95); | ||
} | ||
|
||
Button:active { | ||
background-color: rgb(105, 105, 105); | ||
} | ||
|
||
.redirect { | ||
padding: 2px; | ||
height: 32px; | ||
width: auto; | ||
} | ||
|
||
#ColumnContainer { | ||
border-width: 0; | ||
height: 80%; | ||
width: auto; | ||
padding-left: 3px; | ||
padding-right: 3px; | ||
padding-bottom: 2px; | ||
display: flex; | ||
flex-direction: row; | ||
} | ||
|
||
#LeftColumnBox { | ||
display: flex; | ||
flex: 1; | ||
flex-direction: column; | ||
padding-top: 3px; | ||
} | ||
|
||
#RightColumnBox { | ||
display: flex; | ||
flex: 2; | ||
flex-direction: column; | ||
justify-content: space-between; | ||
} |
11 changes: 11 additions & 0 deletions
11
Assets/Mirror/Editor/WelcomeWindow/Resources/WelcomeWindow.uss.meta
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
58 changes: 58 additions & 0 deletions
58
Assets/Mirror/Editor/WelcomeWindow/Resources/WelcomeWindow.uxml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,58 @@ | ||
<ui:UXML xmlns:ui="UnityEngine.UIElements" xmlns:uie="UnityEditor.UIElements" xsi="http://www.w3.org/2001/XMLSchema-instance" engine="UnityEngine.UIElements" editor="UnityEditor.UIElements" noNamespaceSchemaLocation="../../../../UIElementsSchema/UIElements.xsd" editor-extension-mode="False"> | ||
<Style src="WelcomeWindow.uss" /> | ||
<ui:VisualElement name="Banner"> | ||
<ui:Label name="VersionText" text="Placeholder" /> | ||
<ui:Image name="Icon" style="background-image: url('/Assets/Mirror/Icon/MirrorIcon.png');" /> | ||
</ui:VisualElement> | ||
<ui:Label name="Title" text="Welcome to MirrorNG!" /> | ||
<ui:Box name="ColumnContainer"> | ||
<ui:VisualElement name="LeftColumnBox"> | ||
<ui:Button name="WelcomeButton" text="Welcome" focusable="false" /> | ||
<ui:Button name="ChangeLogButton" text="Change Log" /> | ||
<ui:Button name="QuickStartButton" text="Quick Start Guide" /> | ||
<ui:Button name="BestPracticesButton" text="Best Practices" /> | ||
<ui:Button name="FaqButton" text="FAQ" /> | ||
<ui:Button name="SponsorButton" text="Sponsor Us" /> | ||
<ui:Button name="DiscordButton" text="Discord" /> | ||
</ui:VisualElement> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:VisualElement name="RightColumnBox"> | ||
<ui:VisualElement name="Welcome" style="flex-grow: 0; width: 100%; height: 100%;"> | ||
<ui:Label name="Header" text="Welcome" /> | ||
<ui:Label name="Description" text="Hello! Thank you for installing MirrorNG. Please visit all the pages on this window. Clicking the button at the bottom of the pages will redirect you to a webpage. Additionally, there are example projects in the Mirror folder that you can look at. Have fun using Mirror!" style="-unity-text-align: upper-left;" /> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:Button name="Redirect" text="Visit API Reference" class="redirect" /> | ||
</ui:VisualElement> | ||
<ui:VisualElement name="ChangeLog" style="flex-grow: 0; width: 100%; height: 100%; display: none;"> | ||
<ui:Label name="Header" text="Change Log" /> | ||
<ui:Label name="Description" text="The Change Log is a list of changes made to MirrorNG. Sometimes these changes can cause your game to break." style="-unity-text-align: upper-left;" /> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:Button name="Redirect" text="Visit Change Log" class="redirect" /> | ||
</ui:VisualElement> | ||
<ui:VisualElement name="QuickStart" style="flex-grow: 0; width: 100%; height: 100%; display: none;"> | ||
<ui:Label name="Header" text="Quick Start Guide" /> | ||
<ui:Label name="Description" text="The Quick Start Guide is meant for people who just started using MirrorNG. The Quick Start Guide will help new users learn how to accomplish important tasks. It is highly recommended that you complete the guide." style="-unity-text-align: upper-left;" /> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:Button name="Redirect" text="Visit Quick Start Guide" class="redirect" /> | ||
</ui:VisualElement> | ||
<ui:VisualElement name="BestPractices" style="flex-grow: 0; width: 100%; height: 100%; display: none;"> | ||
<ui:Label name="Header" text="Best Practices" /> | ||
<ui:Label name="Description" text="This page describes the best practices that you should use during development. Currently a work in progress." style="-unity-text-align: upper-left;" /> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:Button name="Redirect" text="Visit Best Practices Page" class="redirect" /> | ||
</ui:VisualElement> | ||
<ui:VisualElement name="Faq" style="flex-grow: 0; width: 100%; height: 100%; display: none;"> | ||
<ui:Label name="Header" text="FAQ" /> | ||
<ui:Label name="Description" text="The FAQ page holds commonly asked questions. Currently, the FAQ page contains answers to: 1. Syncing custom data types 2. How to connect 3. Host migration 4. Server lists and matchmaking" style="-unity-text-align: upper-left;" /> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:Button name="Redirect" text="Visit FAQ" class="redirect" /> | ||
</ui:VisualElement> | ||
<ui:VisualElement name="Sponsor" style="flex-grow: 0; width: 100%; height: 100%; display: none;"> | ||
<ui:Label name="Header" text="Sponsor Us" /> | ||
<ui:Label name="Description" text="Sponsoring will give you access to Mirror PRO which gives you special access to tools and priority support" style="-unity-text-align: upper-left;" /> | ||
<ui:VisualElement name="Spacer" /> | ||
<ui:Button name="Redirect" text="Sponsor Us" class="redirect" /> | ||
</ui:VisualElement> | ||
</ui:VisualElement> | ||
</ui:Box> | ||
</ui:UXML> |
10 changes: 10 additions & 0 deletions
10
Assets/Mirror/Editor/WelcomeWindow/Resources/WelcomeWindow.uxml.meta
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,148 @@ | ||
using UnityEditor; | ||
using UnityEngine; | ||
using UnityEngine.UIElements; | ||
|
||
/** | ||
* Docs used: | ||
* UXML: https://docs.unity3d.com/Manual/UIE-UXML.html | ||
* USS: https://docs.unity3d.com/Manual/UIE-USS-SupportedProperties.html | ||
* Unity Guide: https://learn.unity.com/tutorial/uielements-first-steps/?tab=overview#5cd19ef9edbc2a1156524842 | ||
* External Guide: https://www.raywenderlich.com/6452218-uielements-tutorial-for-unity-getting-started#toc-anchor-010 | ||
*/ | ||
|
||
namespace Mirror | ||
{ | ||
|
||
//this script handles the functionality of the UI | ||
|
||
[InitializeOnLoad] | ||
public class WelcomeWindow : EditorWindow | ||
{ | ||
#region Setup | ||
|
||
#region Urls | ||
|
||
private const string WelcomePageUrl = "https://mirrorng.github.io/MirrorNG/"; | ||
private const string QuickStartUrl = "https://mirrorng.github.io/MirrorNG/Articles/Guides/CommunityGuides/MirrorQuickStartGuide/index.html"; | ||
private const string ChangelogUrl = "https://github.com/MirrorNG/MirrorNG/commits/master"; | ||
private const string BestPracticesUrl = "https://mirrorng.github.io/MirrorNG/Articles/Guides/BestPractices.html"; | ||
private const string FaqUrl = "https://mirrorng.github.io/MirrorNG/Articles/Guides/FAQ.html"; | ||
private const string SponsorUrl = ""; | ||
private const string DiscordInviteUrl = "https://discord.gg/N9QVxbM"; | ||
|
||
#endregion | ||
|
||
//window size of the welcome screen | ||
private static Vector2 windowSize = new Vector2(500, 600); | ||
|
||
//get the start up key | ||
private static string firstStartUpKey = string.Empty; | ||
|
||
#region version | ||
|
||
//called only once | ||
private static string GetVersion() | ||
{ | ||
return typeof(NetworkIdentity).Assembly.GetName().Version.ToString(); | ||
} | ||
|
||
#endregion | ||
|
||
#region Handle visibility | ||
|
||
//constructor (called by InitializeOnLoad) | ||
static WelcomeWindow() | ||
{ | ||
EditorApplication.update += ShowWindowOnFirstStart; | ||
} | ||
|
||
//decide if we should open the window on recompile | ||
private static void ShowWindowOnFirstStart() | ||
{ | ||
//if we haven't seen the welcome page on the current mirror version, show it | ||
//if there is no version, skip this | ||
firstStartUpKey = GetVersion(); | ||
if (!EditorPrefs.GetBool(firstStartUpKey, false) && firstStartUpKey != "MirrorUnknown") | ||
{ | ||
OpenWindow(); | ||
//now that we have seen the welcome window, set this this to true so we don't load the window every time we recompile (for the current version) | ||
EditorPrefs.SetBool(firstStartUpKey, true); | ||
} | ||
|
||
EditorApplication.update -= ShowWindowOnFirstStart; | ||
} | ||
|
||
//open the window (also openable through the path below) | ||
[MenuItem("Window/MirrorNG/Welcome")] | ||
public static void OpenWindow() | ||
{ | ||
//create the window | ||
WelcomeWindow window = GetWindow<WelcomeWindow>("MirrorNG Welcome Page"); | ||
//set the position and size | ||
window.position = new Rect(new Vector2(100, 100), windowSize); | ||
//set min and max sizes so we cant readjust window size | ||
window.maxSize = windowSize; | ||
window.minSize = windowSize; | ||
} | ||
|
||
#endregion | ||
|
||
#endregion | ||
|
||
#region Displaying UI | ||
|
||
//the code to handle display and button clicking | ||
private void OnEnable() | ||
{ | ||
//Load the UI | ||
//Each editor window contains a root VisualElement object | ||
VisualElement root = rootVisualElement; | ||
VisualTreeAsset uxml = Resources.Load<VisualTreeAsset>("WelcomeWindow.uxml"); | ||
StyleSheet uss = Resources.Load<StyleSheet>("WelcomeWindow.uss"); | ||
|
||
//Load the descriptions | ||
|
||
uxml.CloneTree(root); | ||
root.styleSheets.Add(uss); | ||
|
||
//set the version text | ||
Label versionText = root.Q<Label>("VersionText"); | ||
versionText.text = "v" + GetVersion(); | ||
|
||
#region Page buttons | ||
|
||
ConfigureTab("WelcomeButton", "Welcome", WelcomePageUrl); | ||
ConfigureTab("ChangeLogButton", "ChangeLog", ChangelogUrl); | ||
ConfigureTab("QuickStartButton", "QuickStart", QuickStartUrl); | ||
ConfigureTab("BestPracticesButton", "BestPractices", BestPracticesUrl); | ||
ConfigureTab("FaqButton", "Faq", FaqUrl); | ||
ConfigureTab("SponsorButton", "Sponsor", SponsorUrl); | ||
|
||
Button DiscordButton = root.Q<Button>("DiscordButton"); | ||
DiscordButton.clicked += () => Application.OpenURL(DiscordInviteUrl); | ||
|
||
ShowTab("Welcome"); | ||
#endregion | ||
} | ||
|
||
private void ConfigureTab(string tabButtonName, string tab, string url) | ||
{ | ||
Button tabButton = rootVisualElement.Q<Button>(tabButtonName); | ||
tabButton.clicked += () => ShowTab(tab); | ||
Button redirectButton = rootVisualElement.Q<VisualElement>(tab).Q<Button>("Redirect"); | ||
redirectButton.clicked += () => Application.OpenURL(url); | ||
} | ||
|
||
private void ShowTab(string screen) | ||
{ | ||
VisualElement rightColumn = rootVisualElement.Q<VisualElement>("RightColumnBox"); | ||
foreach (VisualElement tab in rightColumn.Children()) | ||
{ | ||
tab.style.display = tab.name == screen ? DisplayStyle.Flex : DisplayStyle.None; | ||
} | ||
} | ||
|
||
#endregion | ||
} | ||
|
||
} |
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
Empty file.
Empty file.
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters