One task list, two ways to render it
Both lists show the same state. They differ in one function: the one that brings the state to the screen.
This is a copy of the page, made ahead of time. No script runs here, so nothing reacts. Open the live page.
The left side starts with the rebuild. Each "Left" line below is about the rebuild. Set the left side to "Track every change by hand" and try again: it then keeps its rows, as the right side does.
  1. Turn on "Another user is editing". Then type a note in a row on the left, and in a row on the right. Left: the note and your cursor are gone every two seconds. Right: the note stays, and you can type on.
  2. Press until a Remove button has focus. Then press "Move the first task to the end". Left: the focus is lost. Right: the focus stays on the same button.
  3. Put the focus on a checkbox and press . Left: the task moves to "Done", and the focus is lost. Right: the same row moves to "Done", with the focus on it.
  4. Type in the "New task" field. Left: every row is made again for each key. Right: nothing happens to the rows.
  5. Press "1,000 rows". Then move the first task to the end. Left: 1,000 rows are made again. Read the time. Right: one row moves. Read the time.
  6. Open this page with no script. Every component shows. Nothing reacts.
Add Move the first task to the end
10 rows 1,000 rows
Counting records every write to the page. That slows the left side. Turn it off to see true times.
Plain DOM code 32 lines of code
Rows on screen3 Rows made for the last change3 Rows made, running total3 Time for the last change5.4 ms Renders of components for the last change9 Renders of components, running total9
To do
  • Read the thread Remove
  • Write the task list Remove
  • Ship it Remove
Done
    The BareMirror functions 30 lines of code
    A row that stays keeps its node, in either list.
    Rows on screen3 Rows made for the last change3 Rows made, running total3 Time for the last change48.4 ms Renders of components for the last change9 Renders of components, running total9
    To do
    • Read the threadRemove
    • Write the task listRemove
    • Ship itRemove
    Done
      The state One value. Both sides show it.
      The plan The plan that the right side made and performed for the last change. After it, the functions write the values of each row that stayed.
      The BareMirror functions, in numbers 17 functions, 4.3 kB compressed. They hold no state of their own. What they remember is on the node it concerns. They load beside the file that every BareDOM component needs, which is 69.0 kB compressed.
      Where plain DOM code is ahead
      • A list of new rows. Press "10 rows", then "1,000 rows", and read the two times. The functions take longer. They help when a list changes. When every row is new, there is nothing to keep.
      • A long list, tracked by hand. Set the left side to "Track every change by hand", press "1,000 rows" and move a task. Compare the two times: the left side is faster. The functions read the place of every row from the page on each change. Careful code by hand remembers its rows and reads nothing. Its price is its length: read the two line counts.
      • The shortest code. The rebuild is the shortest of the three files. It is also the one that loses your note and your focus.
      • No code to load. The left side needs no file besides its own. The right side loads the functions.
      • Nothing to learn. The left side uses only what the browser gives. The right side asks you to learn a template and a few functions.
      The limits of this page
      • Each change is a message. The page has one function that takes a message, makes the next state and renders it. Both sides depend on that.
      • A row has no state of its own. What a row shows comes from the state. The note is the exception: it is text in the node, and the page uses it to show what a rebuild destroys.
      • The focus across a move needs moveBefore. Your browser has it.
      • The count of renders uses the trace recorder of BareDOM. It records every write, which costs time. For a long list the page turns it off and shows the time.
      • One render less for a tick is not about tracking. The badge of a row has two attributes that change with a tick. Plain code writes them one after the other, and the badge renders twice. The functions write both in one hold, which every BareDOM element offers. Plain code could use that hold too.
      • The view has the shape that the functions take. It gives the lists as ids and the rows by id. The two left renderers use the same shape.
      • The running totals start again when you switch the left side. The total of renders also starts again when counting does.
      • The time is the time of the script. The work of the browser after it, to lay out new rows, is not in the number.
      The source Every file of this page, in full. The application is app.js, one of the first three files, which are the three ways to render, and the few lines of main.js that hold the state and take a message. The rest is the instruments of this page: they count, measure and show.