TEST_F(FrameSelectionTest, PaintCaretShouldNotLayout)
{
    RefPtrWillBeRawPtr<Text> text = appendTextNode("Hello, World!");
    document().view()->updateAllLifecyclePhases();

    document().body()->setContentEditable("true", ASSERT_NO_EXCEPTION);
    document().body()->focus();
    EXPECT_TRUE(document().body()->focused());

    VisibleSelection validSelection(Position(text, 0), Position(text, 0));
    selection().setCaretVisible(true);
    setSelection(validSelection);
    EXPECT_TRUE(selection().isCaret());
    EXPECT_TRUE(selection().ShouldPaintCaretForTesting());

    int startCount = layoutCount();
    {
        // To force layout in next updateLayout calling, widen view.
        FrameView& frameView = dummyPageHolder().frameView();
        IntRect frameRect = frameView.frameRect();
        frameRect.setWidth(frameRect.width() + 1);
        frameRect.setHeight(frameRect.height() + 1);
        dummyPageHolder().frameView().setFrameRect(frameRect);
    }
    selection().paintCaret(nullptr, LayoutPoint(), LayoutRect());
    EXPECT_EQ(startCount, layoutCount());
}
TEST_F(HTMLTextFormControlElementTest, SpellCheckDoesNotCauseUpdateLayout)
{
    HTMLInputElement* input = toHTMLInputElement(document().getElementById("input"));
    input->focus();
    input->setValue("Hello, input field");
    VisibleSelection oldSelection = document().frame()->selection().selection();

    Position newPosition(input->innerEditorElement()->firstChild(), 3);
    VisibleSelection newSelection(newPosition, TextAffinity::Downstream);
    document().frame()->selection().setSelection(newSelection, FrameSelection::CloseTyping | FrameSelection::ClearTypingStyle | FrameSelection::DoNotUpdateAppearance);
    ASSERT_EQ(3, input->selectionStart());

    Persistent<SpellChecker> spellChecker(SpellChecker::create(page().frame()));
    forceLayoutFlag();
    int startCount = layoutCount();
    spellChecker->respondToChangedSelection(oldSelection, FrameSelection::CloseTyping | FrameSelection::ClearTypingStyle);
    EXPECT_EQ(startCount, layoutCount());
}
TEST_F(HTMLTextFormControlElementTest, SetSelectionRangeDoesNotCauseLayout) {
  input().focus();
  input().setValue("Hello, input form.");
  input().setSelectionRange(1, 1);
  FrameSelection& frameSelection = document().frame()->selection();
  forceLayoutFlag();
  LayoutRect oldCaretRect(frameSelection.absoluteCaretBounds());
  EXPECT_FALSE(oldCaretRect.isEmpty());
  int startLayoutCount = layoutCount();
  input().setSelectionRange(1, 1);
  EXPECT_EQ(startLayoutCount, layoutCount());
  LayoutRect newCaretRect(frameSelection.absoluteCaretBounds());
  EXPECT_EQ(oldCaretRect, newCaretRect);

  forceLayoutFlag();
  oldCaretRect = LayoutRect(frameSelection.absoluteCaretBounds());
  EXPECT_FALSE(oldCaretRect.isEmpty());
  startLayoutCount = layoutCount();
  input().setSelectionRange(2, 2);
  EXPECT_EQ(startLayoutCount, layoutCount());
  newCaretRect = LayoutRect(frameSelection.absoluteCaretBounds());
  EXPECT_NE(oldCaretRect, newCaretRect);
}