Questa pagina ti guida attraverso la creazione di un nuovo componente Scene Graph denominato puzzle_component che gestisce un puzzle costruito con entità Scene Graph. Una volta creato, posiziona un puzzle_component su un'entità Scene Graph per determinare se un puzzle composto da entità Scene Graph discendenti con componenti attivabili indicati come pezzi del puzzle sia risolto.
Ad esempio, l'immagine seguente è un semplice puzzle che costruirai nell'ultima sezione di questo tutorial.
L'Outliner corrispondente a questo puzzle è mostrato nell'immagine successiva.
Ogni entità discendente di Prefab_PuzzleManager fa parte del puzzle gestito dal puzzle_component corrispondente di Prefab_PuzzleManager. Il puzzle_component:
Riceve eventi quando un pezzo del puzzle è passato alla configurazione risolta.
Determina quando il puzzle è risolto.
Invia eventi lungo la gerarchia del Scene Graph quando il puzzle è risolto per attivare le azioni corrispondenti alla soluzione.
Quando il giocatore sale sulle piattaforme e accende entrambe le luci, la mesh si anima e si trasforma.
Per maggiori informazioni sulle funzioni del linguaggio Verse utilizzate in questa pagina, vedi:
Definisci l'evento Puzzle risolto
Per iniziare, vai a Verse Explorer, fai clic con il pulsante destro del mouse sul nome del progetto e scegli Aggiungi nuovo file Verse al progetto.
Scegli il modello Componente Scene Graph e modifica il Nome del componente in puzzle_component.
Definisci
puzzle_solved_event. Questo è l'evento trasmesso attraverso la gerarchia del Scene Graph quando il puzzle viene risolto per attivare un'azione, ad esempio l'apertura di un cancello o l'estensione di un ponte in modo che il giocatore possa spostarsi oltre l'area delimitata dal puzzle. Definiscipuzzle_solved_eventcome classe figlia discene_event. Questo evento non richiede alcun parametro trasmesso lungo la gerarchia.Versepuzzle_solved_event<public> := class(scene_event){}
Definisci il componente del puzzle
A questo punto, definisci il puzzle_component con campi e funzioni per gestire il puzzle e la possibilità che sia risolto o meno.
Aggiungi campi per monitorare se il puzzle è risolto o meno, un array dei pezzi del puzzle che si trovano nella configurazione risolta e se i pezzi del puzzle continuano ad attivarsi o meno dopo la risoluzione del puzzle:
Versepuzzle_component := class<final_super>(component): # Is this puzzle component solved var<private> Solved<public>:logic = false # Map of puzzle pieces and whether they have been "solved" var<private> TriggerableEntities<private>:[]entity = array{} # Disable puzzle pieces triggering once puzzle is solved @editableAggiungi una funzione denominata
InitializeTriggerableDescendantEntitiesper inizializzare l'elenco di tutti i pezzi che fanno parte di questo puzzle. Questa funzione attraversa la gerarchia del Scene Graph per trovare tutte le entità attivabili contrassegnate come pezzi di un puzzle e le aggiunge all'arrayTriggerableEntities.Verse# Initialize array of triggerable entities InitializeTriggereableDescendantEntities<private>()<transacts>:void= for: DescendantEntity : Entity.FindDescendantEntities(entity) DescendantEntityComponent : DescendantEntity.GetComponents() CastToTriggerable := triggerable[DescendantEntityComponent] CastToTriggerable.PuzzlePiece? do: set TriggerableEntities += array{DescendantEntity}Aggiungi una funzione denominata
DisableTriggerableComponentsper disabilitare qualunque componente attivabile sulle entità discendenti.Verse# Disable puzzle pieces DisableTriggerableComponents<private>():void= for: DescendantEntity : Entity.FindDescendantEntities(entity) DescendantEntityComponent : DescendantEntity.GetComponents() CastToTriggerable := triggerable[DescendantEntityComponent] CastToTriggerable.PuzzlePiece? CastToEnableable := enableable[DescendantEntityComponent] do: CastToEnableable.Disable()Aggiungi una funzione denominata
IsPuzzleSolvedche decide se il puzzle è in uno stato risolto. Ciò avviene iterando attraverso tutte le entità discendenti trovate in precedenza con un componente che implementa l'interfacciaattivabile, controllando se l'entità associata è contrassegnata come pezzo del puzzle e se il componente dell'entità che implementaattivabileè in uno stato risolto.Verse# Decides whether puzzle is solved IsPuzzleSolved<private>()<decides><transacts>:void= for: TriggerableEntity : TriggerableEntities TriggerableEntityComponent : TriggerableEntity.GetComponents() CastToTriggerable := triggerable[TriggerableEntityComponent] CastToTriggerable.PuzzlePiece? do: CastToTriggerable.InSolvedState[]Aggiungi una funzione denominata
HandlePuzzleSolvedper eseguire tutte le azioni necessarie una volta stabilito che il puzzle è risolto. Ciò include l'impostazione del campoRisoltosu questa classe, la disabilitazione degli attivabili del puzzle in base al campo della classeDisablePuzzleTriggerablesWhenSolvede l'invio dipuzzle_solved_eventlungo la gerarchia del Scene Graph.Verse# Handle all necessary actions once puzzle is known to be solved HandlePuzzleSolved<private>():void= set Solved = true if (DisablePuzzleTriggerablesWhenSolved?): DisableTriggerableComponents() Entity.SendDown(puzzle_solved_event{})Quindi, aggiungi una funzione denominata
CheckPuzzleSolution. Si tratta di una funzione wrapper asincrona per determinare se il puzzle è risolto conIsPuzzleSolvede, in caso affermativo, chiama ancheHandlePuzzleSolvedper eseguire le azioni necessarie quando il puzzle viene risolto.Verse# Async wrapper for determining whether puzzle is solved CheckPuzzleSolved()<suspends>:void= Sleep(0.25) if (not Solved?, IsPuzzleSolved[]): HandlePuzzleSolved()Aggiungi un override per la funzione
OnReceivedella classe del componente Scene Graph.Verse# Handle triggered events sent through the Scene Graph hierarchy OnReceive<override>(SceneEvent:scene_event):logic= if (TriggeredEvent := triggered_event[SceneEvent], TriggeredEntity := TriggeredEvent.TriggeredEntity?): spawn{CheckPuzzleSolved()} true falseAggiungi una chiamata a
InitializeTriggerableDescendantEntitiesalla funzioneOnBeginSimulationdel componente.Verse# Runs when the component should start simulating in a running game. OnBeginSimulation<override>():void = # Run OnBeginSimulation from the parent class before # running this component's OnBeginSimulation logic (super:)OnBeginSimulation() InitializeTriggereableDescendantEntities()
Step successivi
Poi crea il componente attivatore e i componenti attivabili che implementano l'interfaccia attivabile.
Codice finale per Puzzle.verse
using { /Verse.org/Simulation }
using { /UnrealEngine.com/Temporary/Diagnostics }
using { /Verse.org/SceneGraph }
using { Logging }
puzzle_solved_event<public> := class(scene_event){}
# Scene Graph component handling puzzle component triggered events and when the puzzle is solved.
puzzle_component := class<final_super>(component):