发布的问题解决方案似乎包含不必要的代码

时间:2018-10-01 20:47:30

标签: javascript

随附的代码段是针对CS50移动应用开发者的作业问题的已发布解决方案。我对一个功能感到困惑。

Todo.prototype.toggleCheck = function() {
  this.checked = !this.checked
  if (this.element && this.checkbox) {
    this.checkbox.checked = this.checked
  } else {
    this.element = renderTodo(this)
  }
}

似乎不需要if else语句。注意:在renderTodo函数中checkbox.checked = todo.checked

如果我们删除该条件程序,该程序似乎可以正常运行。我想念什么吗?

const classNames = {
  DELETE_BUTTON: 'delete-button',
  TODO_ITEM: 'todo-container',
  TODO_CHECKBOX: 'todo-checkbox',
  TODO_TEXT: 'todo-text',
}

const list = document.getElementById('todo-list')
const itemCountDiv = document.getElementById('item-count')
const uncheckedCountDiv = document.getElementById('unchecked-count')

let todos = []

function count(arr, fn) {
  return arr.reduce((acc, next) => fn(next) ? acc + 1 : acc, 0)
}

function Todo(name) {
  this.name = name || 'New TODO'
  this.checked = false
  this.element = null
  this.checkbox = null
}

Todo.prototype.toggleCheck = function() {
  this.checked = !this.checked
  if (this.element && this.checkbox) {
    this.checkbox.checked = this.checked
  } else {
    this.element = renderTodo(this)
  }
}

function renderTodo(todo) {
  if (todo.element) return todo.element

  const deleteButton = document.createElement('button')
  deleteButton.innerHTML = '&times'
  deleteButton.className = classNames.DELETE_BUTTON
  // keep reference of todo on button so that it can be dereferenced in the callback
  deleteButton.onclick = removeTodo
  deleteButton.todoRef = todo

  const checkbox = document.createElement('input')
  checkbox.className = classNames.TODO_CHECKBOX
  checkbox.type = 'checkbox'
  checkbox.checked = todo.checked
  checkbox.todoRef = todo
  checkbox.onchange = toggleChecked
  const span = document.createElement('span')
  span.className = classNames.TODO_TEXT
  span.setAttribute('contenteditable', 'true')
  span.innerHTML = todo.name

  const li = document.createElement('li')
  li.className = classNames.TODO_ITEM
  li.appendChild(deleteButton)
  li.appendChild(checkbox)
  li.appendChild(span)


  // keep reference of element on todo for performance
  todo.element = li
  todo.checkbox = checkbox

  return li
}

function render() {
  list.innerHTML = ''
  todos.map(renderTodo).forEach(todo => list.appendChild(todo))
  uncheckedCountDiv.innerHTML = count(todos, todo => !todo.checked)
  itemCountDiv.innerHTML = todos.length
  return false
}

function addTodo(name) {
  const todo = new Todo(name)
  todos.push(todo)
  return render()
}

function toggleChecked() {
  this.todoRef.toggleCheck()
  return render()
}

function removeTodo() {
  const todo = this.todoRef
  todos = todos.filter(t => t !== todo)
  return render()
}
* {
  box-sizing: border-box;
}

html, body {
  background-color: #eee;
  margin: 0;
  padding: 0;
}

ul {
  margin: 0;
  padding: 0;
  list-style-type: none;
}

.center {
  align-self: center;
}

.flow-right {
  display: flex;
  justify-content: space-around;
}

.container {
  max-width: 800px;
  margin: 0 auto;
  padding: 10px;
  display: flex;
  flex-direction: column;
  background-color: white;
  height: 100vh;
}

.title, .controls, .button {
  flex: none;
}

.button {
  padding: 10px 20px;
}

.todo-list {
  flex: 1 1 0;
  margin-top: 20px;
  padding: 20px;
  overflow-y: auto;
}

.delete-button {
  margin: 10px;
}

.todo-checkbox {
  margin: 10px;
}

.todo-container {
  padding: 20px;
  border-bottom: 1px solid #333;
}

.todo-container:first-of-type {
  border-top: 1px solid #333;
}
<!DOCTYPE html>
<html>
  <head>
    <title>TODO App</title>
    
  <body>
    <div class="container center">
      <h1 class="center title">My TODO App</h1>
      <div class="flow-right controls">
        <span>Item count: <span id="item-count">0</span></span>
        <span>Unchecked count: <span id="unchecked-count">0</span></span>
      </div>
      <button class="button center" onClick="addTodo()">New TODO</button>
      <ul id="todo-list" class="todo-list"></ul>
    </div>
   
  </body>
</html>

0 个答案:

没有答案