Menu main — MRTK3
Les menus à main permettent aux utilisateurs d’afficher l’interface utilisateur attachée à la main pour les fonctions fréquemment utilisées. Il s’agit généralement de petits groupes de boutons qui offrent des actions rapides. Toutefois, parfois, des dispositions plus complexes pour l’affichage d’informations ou de paramètres sont fournies à l’utilisateur en tant que menu de main, souvent avec l’option « déchirer » le menu de la main et l’ancrer dans le monde.
Le menu Main fournit les options « Exiger une main plate » et « Utiliser l’activation du regard » pour empêcher la fausse activation lors de l’interaction avec d’autres objets. Il est recommandé d’utiliser ces options pour empêcher l’activation indésirable.
Exemple de scène et de prefabs
Notes
Les préfabriqués de menu de main sont actuellement créés à l’aide des contrôles non-Canevas. Ils seront bientôt reconstruits à l’aide des composants canevas et du système de mise en page automatique, comme indiqué dans la documentation du groupe de boutons .
Si vous utilisez le projet de modèle, HandMenuExamples.unity
illustre plusieurs configurations courantes pour les menus à main, tout en utilisant le HandConstraintPalmUp
script.
HandMenu1x4 et HandMenu2x4
Le menu devient visible et invisible dans ces préfabriqués en activant et en désactivant l’objet MenuContent sur OnFirstHandDetected() et Les événements OnLastHandLost(). Ce comportement est recommandé pour le menu avec une petite interface utilisateur, ce qui nécessite une courte durée d’interaction.
HandMenuLarge
Ce préfabriqué illustre l’exemple d’une interface utilisateur volumineuse ou complexe qui nécessite un temps d’interaction étendu. Pour ce type d’interface utilisateur, il est recommandé de verrouiller le menu à la main pour améliorer la facilité d’utilisation et éviter la fatigue des bras. Cet exemple prend également en charge « saisir et extraire » pour verrouiller le menu.
Dans cet exemple, le menu devient visible et invisible en activant l’objet MenuContent sur l’événement OnFirstHandDetected(). Avec l’événement OnLastHandLost(), le bouton de fermeture est activé et l’animation de placement est déclenchée. L’animation est une fluctuation de mise à l’échelle simple. Comme nous n’avons pas masqué l’événement MenuContent sur OnLastHandLost(), le menu sera automatiquement verrouillé lorsque la main n’est pas visible. Les valeurs de la section Palm Up ont été optimisées pour rendre le menu verrouillé au monde sans être traîné trop sur la liste déroulante de main.

Cet exemple fournit la barre pouvant être saisie dans la zone inférieure du menu et le comportement de verrouillage automatique du monde. L’utilisateur peut détacher explicitement le menu de la main et le placer dans le monde en prenant cela. Pour ce faire, sur l’événement ManipulationStarted() dans ObjectManipulator, nous désactive SolverHandler.UpdateSolvers. Sinon, le menu ne pourra pas être détaché, car le solveur HandConstraint tentera de positionner le menu près de la position de la main. Nous utilisons également HandConstraintPalmUp.StartWorldLockReattachCheckCoroutine pour permettre à l’utilisateur de lever la main pour détacher le menu à la main.
Enfin, le bouton de fermeture doit réactiver le SolverHandler.UpdateSolvers pour restaurer la fonctionnalité du solveur HandConstraint.
scripts ;
Le comportement HandConstraint
fournit un résolveur qui limite l’objet suivi à une région sécurisée pour le contenu contraint à la main (par exemple, interface utilisateur et menus Main, etc.). Les régions sûres sont considérées comme des zones qui ne présentent pas d’intersection avec la main. Une classe dérivée de HandConstraint
appelée HandConstraintPalmUp
est également incluse pour illustrer un comportement courant de l’activation de l’objet suivi du résolveur lorsque la paume est orientée vers l’utilisateur.
Consultez les info-bulles disponibles pour chaque HandConstraint
propriété pour obtenir une documentation supplémentaire. Quelques propriétés sont définies plus en détail ci-dessous.
Coffre Zone : la zone sécurisée spécifie où de la main pour limiter le contenu. Il est recommandé que le contenu soit placé sur le côté Ulnar pour éviter les chevauchements avec la main et améliorer la qualité de l’interaction. Coffre zones sont calculées par l’orientation des mains projetées dans un plan orthogonal à la vue de la caméra et en raycasting sur une zone englobante autour des mains. Coffre zones sont définies pour fonctionner avec
XRNode
. L’exploration de chaque zone sécurisée représente sur différents types de contrôleurs est recommandée.Suivez La main jusqu’à ce que le Caméra avec cette action active, le résolveur suit la rotation des mains jusqu’à ce que le menu soit suffisamment aligné avec le regard lorsqu’il fait face à la caméra. Pour effectuer ce travail, modifiez le
SolverRotationBehavior
contenu dans leHandConstraintSolver
, deLookAtTrackedObject
àLookAtMainCamera
mesure que l’angleGazeAlignment
avec le solveur varie.
Événements d’activation : Actuellement, le
HandConstraint
déclencheur quatre événements d’activation. Ces événements peuvent être utilisés dans de nombreuses combinaisons différentes pour créer des comportements uniquesHandConstraint
.- OnHandActivate : déclenche lorsqu’une main satisfait à la méthode IsHandActive.
- OnHandDeactivate : déclenche lorsque la méthode IsHandActive n’est plus satisfaite.
- OnFirstHandDetected : se produit lorsque l’état de suivi des mains passe d’aucune main en vue à la première main en mode.
- OnLastHandLost : se produit lorsque l’état de suivi des mains passe d’au moins une main en vue à aucune main en mode.
Logique d’activation/de désactivation du solveur : Actuellement, la recommandation d’activation et de
HandConstraintPalmUp
désactivation de la logique consiste à le faire à l’aide de la valeur de l’objetSolverHandler
UpdateSolver
plutôt qu’en désactivant/en activant l’objet. Cela peut être vu dans l’exemple de scène via les crochets basés sur l’éditeur déclenchés après les événements ManipulationHandler « OnManipulationStarted/Ended » du menu attaché.- Arrêt de la logique de contrainte de main : lorsque vous essayez de définir l’objet contrainte à la main pour arrêter (et non exécuter la logique d’activation/de désactivation), définissez UpdateSolver sur False plutôt que de désactiver HandConstraintPalmUp.
- Si vous souhaitez activer la logique de retachage basée sur le regard (ou même non basé sur le regard), cela est suivi de l’appel de la
HandConstraintPalmUp.StartWorldLockReattachCheckCoroutine()
fonction. Cela déclenche une coroutine qui continue à vérifier si les critères «IsValidController
» sont remplis et définissent UpdateSolver sur True une fois qu’il est (ou l’objet est désactivé).
- Si vous souhaitez activer la logique de retachage basée sur le regard (ou même non basé sur le regard), cela est suivi de l’appel de la
- Démarrage de la logique de contrainte de main : lorsque vous essayez de définir l’objet contrainte de main pour commencer à suivre votre main à nouveau (selon s’il répond aux critères d’activation), définissez la valeur UpdateSolver de SolverHandler sur true.
- Arrêt de la logique de contrainte de main : lorsque vous essayez de définir l’objet contrainte à la main pour arrêter (et non exécuter la logique d’activation/de désactivation), définissez UpdateSolver sur False plutôt que de désactiver HandConstraintPalmUp.
- Retacher la logique : Actuellement, il
HandConstraintPalmUp
peut détacher automatiquement l’objet cible au point suivi, quelle que soit laSolverHandler
UpdateSolver
valeur true. Cela est effectué en appelant la fonction 'sStartWorldLockReattachCheckCoroutine()
une fois qu’elle a été verrouillée dans leHandConstraintPalmUp
monde (ce qui, dans ce cas, définit efficacement la valeur UpdateSolver de SolverHandler sur False).