Skip to content

[BUG] TapToPlace doesn't start placement when StartPlacement() is called just after prefab creation #784

Description

@anonymous2585

Describe the bug

When you call StartPlacement() on a TapToPlace just after a prefab creation (or AddComponent<TapToPlace>()), the TapToPlace isn't being placed.

To reproduce

Steps to reproduce the behavior:

  1. Add this test to SolverTapToPlaceTests.cs
/// <summary>
/// Verify TapToPlace can start placement when method is called before its own Start.
/// </summary>
[UnityTest]
public IEnumerator TapToPlaceIsBeingPlacedBeforeStart()
{
    // Disable gaze interactions for this unit test;
    InputTestUtilities.DisableGazeInteractor();

    // Set up GameObject with a SolverHandler
    var testObject = GameObject.CreatePrimitive(PrimitiveType.Cube);
    var solverHandler = testObject.AddComponent<SolverHandler>();
    var solver = testObject.AddComponent<TapToPlace>();

    // Disable smoothing so moving happens instantly. This makes testing positions easier.
    solver.Smoothing = false;

    // Set it to track interactors
    solverHandler.TrackedHandedness = Handedness.Both;
    solverHandler.TrackedTargetType = TrackedObjectType.Interactor;
    var lookup = FindObjectUtility.FindAnyObjectByType<ControllerLookup>();
    var leftInteractor = lookup.LeftHandController.GetComponentInChildren<MRTKRayInteractor>();
    var rightInteractor = lookup.RightHandController.GetComponentInChildren<MRTKRayInteractor>();
    solverHandler.LeftInteractor = leftInteractor;
    solverHandler.RightInteractor = rightInteractor;

    int onPlacingStartedCount = 0;
    int onPlacingStoppedCount = 0;
    solver.OnPlacingStarted.AddListener(() => onPlacingStartedCount++);
    solver.OnPlacingStopped.AddListener(() => onPlacingStoppedCount++);

    // Call immediately whithout the TapToPlace Start being called
    solver.StartPlacement();

    yield return RuntimeTestUtilities.WaitForUpdates(1);

    Assert.IsTrue(solver.IsBeingPlaced, "TapToPlace should have started.");
    Assert.AreEqual(1, onPlacingStartedCount, "TapToPlace should have invoked event OnPlacingStarted exactly 1 time.");
    Assert.AreEqual(0, onPlacingStoppedCount, "TapToPlace shouldn't have invoked event OnPlacingStarted.");
}
  1. Run the test

Expected behavior

The test succeed, the tap to place is being placed as soon as its Start() method have been called.

Your setup (please complete the following information)

  • Unity Version 2022.3.7f1
  • MRTK Version or Commit ded4a78

Target platform (please complete the following information)

  • HoloLens 2

Additional context

There is a proprety called placementRequested already made to fix this usecase, but the DoubleClickTimeout check conflict and cancel the request.
This usecase isn't tested.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Needs: TriageNeeds to be triaged.Type: BugA problem with an existing feature that can be fixed with the next patched release.

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions