mirror of
https://github.com/VOREStation/VOREStation.git
synced 2026-08-23 03:57:48 +01:00
Adds TGUI functionality to Trait Tutorial
* Creates trait_tutorial_tgui.dm to act as backend, adds to vorestation.dme * Creates TraitTutorial.tsx to act as frontend * Modifies traits_tutorial.dm for TGUI compatibility * Adds comment to var/tutorial definition on how to make it pretty in TGUI * Modifies logic in trait_tutorial to catch empty trait lists. * Edits bloodsucker obligate/freeform to add another <br>
This commit is contained in:
@@ -88,7 +88,7 @@
|
||||
tutorial = "This trait forces you to only consume blood - you cannot have normal food anymore. Vore is, of course, an exception! <br> \
|
||||
You can satisfy this by clicking bloodbags in your hand on harm intent, drinking from glasses, blood tomatoes \
|
||||
or finding a (un)willing donor for your appropriate appendage! <br><br> \
|
||||
Controls for taking blood from your victim can be changed at will by trying to drink from yourself.\
|
||||
Controls for taking blood from your victim can be changed at will by trying to drink from yourself. <br>\
|
||||
Intent-based control scheme: <br> \
|
||||
HELP - Loud, No Bleeding <br> \
|
||||
DISARM - Subtle, Causes bleeding <br> \
|
||||
@@ -110,7 +110,7 @@
|
||||
tutorial = "This trait allows you to consume blood on top of normal food! <br> \
|
||||
You can do this by clicking bloodbags in your hand on harm intent, drinking from glasses, blood tomatoes \
|
||||
or finding a (un)willing donor for your appropriate appendage! <br><br> \
|
||||
Controls for taking blood from your victim can be changed at will by trying to drink from yourself.\
|
||||
Controls for taking blood from your victim can be changed at will by trying to drink from yourself. <br>\
|
||||
Intent-based control scheme: <br> \
|
||||
HELP - Loud, No Bleeding <br> \
|
||||
DISARM - Subtle, Causes bleeding <br> \
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/datum/trait
|
||||
var/name
|
||||
var/desc = "Contact a developer if you see this trait."
|
||||
var/tutorial = "This trait has no detailed tutorial yet. Suggest one at #Dev-Suggestions on the discord!"
|
||||
var/tutorial = "This trait has no detailed tutorial yet. Suggest one at #Dev-Suggestions on the discord!" //Use <br> for newlines, NOT \n
|
||||
|
||||
var/cost = 0
|
||||
var/sort = TRAIT_SORT_NORMAL // Sort order, 1 before 2 before 3 etc. Alphabetical is used for same-group traits.
|
||||
|
||||
@@ -7,6 +7,11 @@ then retrieve their relevant vars by assuming the character's species has the fu
|
||||
The ability is intended to be developed both as a to_chat() and a tgui window.
|
||||
The user is given the ability to choose which they would like whenever they press the ability to better suit whatever scenario they find themselves
|
||||
thirsty for knowledge.
|
||||
|
||||
When adding new tutorials for trait subtypes, use <br> rather than \n newlines
|
||||
|
||||
TGUI backend path: code\modules\tgui\modules\trait_tutorial_tgui.dm
|
||||
TGUI frontend path: tgui\packages\tgui\interfaces\TraitTutorial.tsx
|
||||
*/
|
||||
|
||||
|
||||
@@ -17,13 +22,19 @@ thirsty for knowledge.
|
||||
set name = "Explain Custom Traits"
|
||||
set desc = "Click this verb to obtain a detailed tutorial on your selected traits. "
|
||||
set category = "Abilities"
|
||||
var/datum/tgui_module/trait_tutorial_tgui/fancy_UI
|
||||
if(!fancy_UI)
|
||||
fancy_UI = new /datum/tgui_module/trait_tutorial_tgui/ //Preventing a bunch of instances being spawned all over the place. Hopefully
|
||||
|
||||
|
||||
|
||||
var/list/list_of_traits = species.traits
|
||||
if(!list_of_traits)
|
||||
if(!LAZYLEN(list_of_traits))
|
||||
to_chat(usr, SPAN_NOTICE("You do not have any custom traits!"))
|
||||
return
|
||||
|
||||
|
||||
var/UI_choice = tgui_alert(src, "Would you like the tutorial text to be printed to chat?", "Choose preferred tutorial interface", list("To Chat", "Cancel"))
|
||||
var/UI_choice = tgui_alert(src, "Would you like the tutorial text to be printed to chat?", "Choose preferred tutorial interface", list("TGUI","To Chat", "Cancel"))
|
||||
if(UI_choice == "Cancel")
|
||||
return
|
||||
|
||||
@@ -34,7 +45,6 @@ thirsty for knowledge.
|
||||
var/trait_tutorial = list() //name:tutorial
|
||||
for(var/trait in list_of_traits)
|
||||
var/datum/trait/T = all_traits[trait]
|
||||
to_world_log("##DEBUG [T.name] is of category [T.category]")
|
||||
trait_names += T.name
|
||||
trait_desc[T.name] = T.desc
|
||||
trait_tutorial[T.name] = T.tutorial
|
||||
@@ -54,5 +64,7 @@ thirsty for knowledge.
|
||||
<b>Guide:</b> \n [trait_tutorial[to_chat_choice]]"))
|
||||
|
||||
|
||||
// else if(UI_choice == "TGUI")
|
||||
to_chat(usr, SPAN_NOTICE("TGUI functionality is not yet implemented, sorry!"))
|
||||
else if(UI_choice == "TGUI")
|
||||
|
||||
fancy_UI.set_vars(trait_names, trait_category, trait_desc, trait_tutorial)
|
||||
fancy_UI.tgui_interact(usr)
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
/*
|
||||
Verb/Main definition path: code\modules\mob\living\carbon\human\species\station\traits_vr\traits_tutorial.dm
|
||||
Frontend path: tgui\packages\tgui\interfaces\TraitTutorial.tsx
|
||||
*/
|
||||
|
||||
/datum/tgui_module/trait_tutorial_tgui
|
||||
name = "Explain Custom Traits"
|
||||
tgui_id = "TraitTutorial"
|
||||
var/trait_names = list()
|
||||
var/trait_category = list() // name:category
|
||||
var/trait_desc = list() // name:desc
|
||||
var/trait_tutorial = list() //name:tutorial
|
||||
var/trait_selected = ""
|
||||
|
||||
/datum/tgui_module/trait_tutorial_tgui/proc/set_vars(list/names, list/categories, list/descriptions, list/tutorials)
|
||||
trait_names = names
|
||||
trait_category = categories
|
||||
trait_desc = descriptions
|
||||
trait_tutorial = tutorials
|
||||
|
||||
/datum/tgui_module/trait_tutorial_tgui/tgui_interact(mob/living/carbon/human/user, datum/tgui/ui)
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, tgui_id, name)
|
||||
ui.open()
|
||||
|
||||
/datum/tgui_module/trait_tutorial_tgui/tgui_data(mob/user)
|
||||
var/list/data = list()
|
||||
data["names"] = trait_names //passes a list of strings
|
||||
data["descriptions"] = trait_desc //passes an assoc list as obj
|
||||
data["categories"] = trait_category //passes an assoc list as obj
|
||||
data["tutorials"] = trait_tutorial //passes an assoc list as obj
|
||||
data["selection"] = trait_selected //passes a string
|
||||
return data
|
||||
|
||||
/datum/tgui_module/trait_tutorial_tgui/tgui_act(action, params)
|
||||
. = ..()
|
||||
if(.)
|
||||
return
|
||||
if(action == "select_trait")
|
||||
var/selection = params["name"]
|
||||
trait_selected = selection
|
||||
|
||||
|
||||
. = TRUE
|
||||
|
||||
/datum/tgui_module/trait_tutorial_tgui/tgui_state(mob/user)
|
||||
return GLOB.tgui_always_state
|
||||
@@ -0,0 +1,80 @@
|
||||
/* eslint-disable react/no-danger */
|
||||
import { useBackend } from '../backend';
|
||||
import { Flex, Tabs, Section, Box, Divider } from '../components';
|
||||
import { Window } from '../layouts';
|
||||
|
||||
type data = {
|
||||
namae: string;
|
||||
names: string[];
|
||||
descriptions: { key: string; val: string }[];
|
||||
categories: { key: string; val: string }[];
|
||||
tutorials: { key: string; val: string }[];
|
||||
selection: string;
|
||||
};
|
||||
|
||||
export const TraitTutorial = (props, context) => {
|
||||
const { act, data } = useBackend<data>(context);
|
||||
return (
|
||||
<Window width={804} height={426} scrollable>
|
||||
<Window.Content scrollable>
|
||||
<Section title="Guide to Custom Traits" scrollable>
|
||||
<TraitSelection />
|
||||
</Section>
|
||||
</Window.Content>
|
||||
</Window>
|
||||
);
|
||||
};
|
||||
|
||||
export const TraitSelection = (props, context) => {
|
||||
const { act, data } = useBackend<data>(context);
|
||||
|
||||
const { names, selection } = data;
|
||||
|
||||
return (
|
||||
<Flex scrollable>
|
||||
<Flex.Item shrink scrollable>
|
||||
<Section title="Trait Selection" scrollable>
|
||||
<Tabs vertical scrollable>
|
||||
{names.map((name) => (
|
||||
<Tabs.Tab key={name} selected={name === selection} onClick={() => act('select_trait', { name })}>
|
||||
<Box inline>{name}</Box>
|
||||
</Tabs.Tab>
|
||||
))}
|
||||
</Tabs>
|
||||
</Section>
|
||||
</Flex.Item>
|
||||
<Flex.Item grow={2}>
|
||||
<Divider vertical />
|
||||
</Flex.Item>
|
||||
<Flex.Item grow={8} scrollable>
|
||||
{selection && (
|
||||
<Section title={selection} scrollable>
|
||||
<TraitDescription name={selection} />
|
||||
</Section>
|
||||
)}
|
||||
</Flex.Item>
|
||||
</Flex>
|
||||
);
|
||||
};
|
||||
|
||||
export const TraitDescription = (props, context) => {
|
||||
const { act, data } = useBackend<data>(context);
|
||||
|
||||
const { name } = props;
|
||||
const { descriptions, categories, tutorials } = data;
|
||||
|
||||
return (
|
||||
<Section scrollable flexWrap>
|
||||
<b>Name:</b> {name}
|
||||
<br />
|
||||
<b>Category:</b> {categories[name]}
|
||||
<br />
|
||||
<b>Description:</b> {descriptions[name]}
|
||||
<br />
|
||||
<b>Details & How to Use:</b>
|
||||
<br />
|
||||
<br />
|
||||
<div dangerouslySetInnerHTML={{ __html: tutorials[name] as unknown as string }} />
|
||||
</Section>
|
||||
);
|
||||
};
|
||||
File diff suppressed because one or more lines are too long
@@ -3979,6 +3979,7 @@
|
||||
#include "code\modules\tgui\modules\shutoff_monitor.dm"
|
||||
#include "code\modules\tgui\modules\supermatter_monitor.dm"
|
||||
#include "code\modules\tgui\modules\teleporter.dm"
|
||||
#include "code\modules\tgui\modules\trait_tutorial_tgui.dm"
|
||||
#include "code\modules\tgui\modules\admin\player_notes.dm"
|
||||
#include "code\modules\tgui\modules\ntos-only\cardmod.dm"
|
||||
#include "code\modules\tgui\modules\ntos-only\configurator.dm"
|
||||
|
||||
Reference in New Issue
Block a user