How to divide the text into separate pages (like Google docs) in contenteditable?

I have been working on the creation of a specialized text editor running in the browser. I’ve got a question that has put me in a stupor. How to detect and divide long text into separate pages, as is done in Google docs?
I know that google docs does not work through contenteditable, but there must be some solution…

Edit1: We need to consider a few scenarios:

  • How to parse editable DIV's text with browser compatibility
  • contentEditable javascript caret placement in div
  • How to get the caret's position in contentEditable div when entering a new line?
  • Setting the caret position to an empty node inside a contentEditable element
  • Removing any html/formatting/ect from text string as it is pasted, via Javascript/JQuery?
  • How to set the cursor inside a newly added empty span with Javascript (in a contenteditable div)?
    1. We load a document by means of json object and then rendering our pages.
    2. We are typing the text and reached the end of the page.
    3. We delete the text.
    4. We insert or remove a piece of text.

    Google docs pagination


    <div class="box-base">
        <div id="page-1" class="page">
             <div id="editable-1" class="document" contenteditable="true"></div>
        <div id="page-2" class="page">
             <div id="editable-2" class="document" contenteditable="true"></div>


    .box-base {
        margin-left: 50px;
        flex: 1 0 430px;
        border-style: solid;
        display: -webkit-flex;
        display: flex;
        flex-wrap: wrap;
        justify-content: center;
        height: 900px;
        overflow: auto;
    .page {
        width: @page-width;
        height: @page-width * 1.414;
        /*overflow-y: auto;*/
        background: white;
        margin: 25px 0 25px 0;
    .document {
      /*max-height: 1000px;*/
      overflow: hidden;

  • contentEditable - Firefox <br /> tag
  • History of contentEditable alternatives
  • How to disable % in the condent editable box
  • How to change div contenteditable from true to false
  • Set anchor name with execCommand
  • Closing keyboard on iPad in div contenteditable
  • One Solution collect form web for “How to divide the text into separate pages (like Google docs) in contenteditable?”

    I think you have to try splitting the text at different places and watch until scrollHeight is just less than or equal to clientHeight. Something like:

    var divs = document.querySelectorAll('div');
    var div = divs[0]
    // Get text from content of first div - this wouldn't be what real code used
    var text = div.textContent;
    // Guess the split point as a percentage of the hidden characters
    var splitPoint = text.length * div.clientHeight / div.scrollHeight;
    // Find first space after splitpoint
    splitPoint = text.indexOf(' ', splitPoint);
    // Used to make sure we don't get into an infinite loop. Not needed if this code is proven to work on all browsers.
    var count = 0;
    div.textContent = text.substr(0, splitPoint);
    // Add words until we are bigger 
    while ((div.clientHeight == div.scrollHeight) && (count++ < 1000)) {
      splitPoint = text.indexOf(' ', splitPoint + 1);
      div.textContent = text.substr(0,splitPoint);
    // Subtract words until we are smaller 
    while ((div.clientHeight < div.scrollHeight) && (count++ < 1000)) {
      splitPoint = text.lastIndexOf(' ', splitPoint - 1);
      div.textContent = text.substr(0, splitPoint);
    divs[1].textContent = text.substr(splitPoint);
    // Create new divs starting at splitpoint (left as an exercise) {
      width: 150px;
      height: 150px;
      border: 1px solid black;
    div.moretext {
      background: #ccc;
    <div class="box">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Praesent viverra malesuada nibh, sed luctus eros egestas in. Donec imperdiet, purus a consequat ultricies, mauris magna laoreet neque, quis tincidunt risus augue in lorem. Donec mauris odio, vehicula eget sollicitudin sed, aliquet et metus. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Donec condimentum sed lacus at porttitor. Suspendisse tincidunt vehicula mauris, a ultricies mi fringilla et. Aliquam eget imperdiet magna. Quisque justo libero, commodo vitae dolor quis, volutpat consectetur tellus. Nullam consectetur commodo sem vel posuere. Praesent nec suscipit sem, quis porta diam. Duis gravida lectus fringilla, efficitur quam ut, luctus sem. Ut elit tortor, bibendum a molestie vel, tincidunt vitae lacus. In dapibus commodo mi, id blandit velit mollis placerat. Praesent quis posuere ligula. Praesent ac rhoncus est. In blandit non justo ut egestas. Praesent nec mi sagittis, eleifend nisl ac, egestas enim. Aliquam in tortor ac tellus rutrum feugiat. Etiam bibendum eget metus eget facilisis. Sed mollis eget tellus at viverra. Fusce at leo vel magna convallis dictum. Sed convallis ipsum non feugiat sagittis. Donec a lacus nisl. Donec elementum metus nec arcu interdum interdum. Praesent malesuada eu purus nec tempus. Aliquam in velit nulla. Ut vel turpis et sapien consectetur facilisis. Fusce a pulvinar lorem. Vestibulum vel neque vitae arcu placerat sodales quis ut risus. Cras aliquet, nibh quis sodales venenatis, felis est tempus enim, at condimentum felis nulla sollicitudin tortor. Morbi viverra dolor tempus, lacinia ante ac, dapibus diam. Suspendisse nec ligula viverra, pellentesque lacus nec, maximus turpis.</div>
    <div class="moretext"></div>