Цикл и рендеринг объектов на HTML - PullRequest
1 голос
/ 03 февраля 2020

Я пытаюсь динамически визуализировать данные на моем HTML, и при нажатии на selectPlayer данные должны показывать раскрывающийся список игроков и иметь возможность выбрать

Одновременно при выборе статистика должна появиться в <div id="stats"></div>

Я могу провести oop через объект, но как мне представить его динамически на HTML?

<!DOCTYPE html>
<html lang="en">

<head>
  <link rel="stylesheet" href="./static/style.css" />
  <title>card</title>
</head>

<body>
  <header>
    <h1 id="selectPlayer">Select a player...</h1>
  </header>
  <div id="stats">
    <div id="name"></div>
    <div id="position"></div>
  </div>
  <script>
    const statsData = {
      players: [{
          player: {
            info: {
              positionInfo: "Defender"
            },
            name: {
              first: "Toby",
              last: "Alderweireld"
            },
            currentTeam: {
              name: "Tottenham Hotspur"
            }
          },
          stats: [{
              name: "goals",
              value: 5
            },
            {
              name: "losses",
              value: 20
            },
            {
              name: "wins",
              value: 48
            },
            {
              name: "draws",
              value: 23
            }
          ]
        },
        {
          player: {
            info: {
              positionInfo: "Midfielder"
            },
            name: {
              first: "Yaya",
              last: "Toure"
            },
            currentTeam: {
              name: "Manchester City"
            }
          },
          stats: [{
              name: "goals",
              value: 65
            },
            {
              name: "losses",
              value: 49
            },
            {
              name: "wins",
              value: 149
            },
            {
              name: "draws",
              value: 35
            }
          ]
        },
        {
          player: {
            info: {
              positionInfo: "Attacker"
            },
            name: {
              first: "Riyad",
              last: "Mahrez"
            },
            currentTeam: {
              name: "Leicester City"
            }
          },
          stats: [{
              name: "goals",
              value: 22
            },
            {
              name: "losses",
              value: 23
            },
            {
              name: "wins",
              value: 35
            },
            {
              name: "draws",
              value: 21
            }
          ]
        }
      ]
    };

    document.getElementById(
      "selectPlayer"
    ).innerHTML = `<h1>${statsData.players}<h1>`;
    document.getElementById(
      "stats"
    ).innerHTML = `<h2> ${statsData.player.stats}<h2>`;
  </script>
</body>

</html>

Здесь довольно много кода, но он застрял

Ответы [ 2 ]

1 голос
/ 03 февраля 2020

Есть много способов, к которым можно приблизиться - простым решением было бы сериализовать JSON в строку и отобразить это в вашем документе напрямую, используя JSON .stringify. () метод:

document.getElementById("stats").innerText = JSON.stringify(statsData.players);

const statsData = {
  players: [{
      player: {
        info: {
          positionInfo: "Defender"
        },
        name: {
          first: "Toby",
          last: "Alderweireld"
        },
        currentTeam: {
          name: "Tottenham Hotspur"
        }
      },
      stats: [{
          name: "goals",
          value: 5
        },
        {
          name: "losses",
          value: 20
        },
        {
          name: "wins",
          value: 48
        },
        {
          name: "draws",
          value: 23
        }
      ]
    },
    {
      player: {
        info: {
          positionInfo: "Midfielder"
        },
        name: {
          first: "Yaya",
          last: "Toure"
        },
        currentTeam: {
          name: "Manchester City"
        }
      },
      stats: [{
          name: "goals",
          value: 65
        },
        {
          name: "losses",
          value: 49
        },
        {
          name: "wins",
          value: 149
        },
        {
          name: "draws",
          value: 35
        }
      ]
    },
    {
      player: {
        info: {
          positionInfo: "Attacker"
        },
        name: {
          first: "Riyad",
          last: "Mahrez"
        },
        currentTeam: {
          name: "Leicester City"
        }
      },
      stats: [{
          name: "goals",
          value: 22
        },
        {
          name: "losses",
          value: 23
        },
        {
          name: "wins",
          value: 35
        },
        {
          name: "draws",
          value: 21
        }
      ]
    }
  ]
};

document.getElementById("stats").innerText = JSON.stringify(statsData.players);
<header>
  <h1 id="selectPlayer">Select a player...</h1>
</header>
<div id="stats"></div>

Однако лучшим подходом было бы представление данных JSON в более удобочитаемом виде. Чтобы сделать это, вам обычно нужно «l oop» над коллекцией (массивом) данных, где для каждого элемента массива вы делаете дополнительную обработку, чтобы сделать данные более читабельными.

Например, вы можете сделать что-то вроде следующего, чтобы отобразить данные JSON в таблице HTML:

/* Assuming you've replaced the stats element with a table */
const table = document.getElementById("stats");

/* Loop through each item of statsData object */
statsData.players.forEach(item => {

  /* Extract info and name objects from player (optional) */
  const { info, name } = item.player;

  /* Add row to table for current player */
  const row = table.insertRow();

  /* Add cell for name/position to row */
  const cellName = row.insertCell(0);
  const cellPosition = row.insertCell(1);

  /* Fill each cell with data from current player data */
  cellName.innerText = name.first;
  cellPosition.innerText = info.positionInfo;
});

Полный рабочий пример приведен ниже:

const statsData = {
  players: [{
      player: {
        info: {
          positionInfo: "Defender"
        },
        name: {
          first: "Toby",
          last: "Alderweireld"
        },
        currentTeam: {
          name: "Tottenham Hotspur"
        }
      },
      stats: [{
          name: "goals",
          value: 5
        },
        {
          name: "losses",
          value: 20
        },
        {
          name: "wins",
          value: 48
        },
        {
          name: "draws",
          value: 23
        }
      ]
    },
    {
      player: {
        info: {
          positionInfo: "Midfielder"
        },
        name: {
          first: "Yaya",
          last: "Toure"
        },
        currentTeam: {
          name: "Manchester City"
        }
      },
      stats: [{
          name: "goals",
          value: 65
        },
        {
          name: "losses",
          value: 49
        },
        {
          name: "wins",
          value: 149
        },
        {
          name: "draws",
          value: 35
        }
      ]
    },
    {
      player: {
        info: {
          positionInfo: "Attacker"
        },
        name: {
          first: "Riyad",
          last: "Mahrez"
        },
        currentTeam: {
          name: "Leicester City"
        }
      },
      stats: [{
          name: "goals",
          value: 22
        },
        {
          name: "losses",
          value: 23
        },
        {
          name: "wins",
          value: 35
        },
        {
          name: "draws",
          value: 21
        }
      ]
    }
  ]
};

const table = document.getElementById("stats");

/* Loop through each player of statsData object */
statsData.players.forEach(item => {

  /* Extract info and name objects from player (optional) */
  const { info, name } = item.player;
  
  /* Add row to table for current player */
  const row = table.insertRow();
  
  /* Add cell for name/position to row */
  const cellName = row.insertCell(0);
  const cellPosition = row.insertCell(1);
  
  /* Fill each cell with data from current player data */
  cellName.innerText = name.first;
  cellPosition.innerText = info.positionInfo;
});
<header>
  <h1 id="selectPlayer">Select a player...</h1>
</header>
<table id="stats">
  <thead><td>Name</td><td>Position</td></thead>
</table>

Надеюсь, это поможет!

0 голосов
/ 03 февраля 2020

Поскольку вы хотите иметь возможность выбрать игрока, используйте элемент <select>. Выведите доступных игроков внутри этого элемента выбора. Вы можете сделать это, создав элемент <option> для каждого игрока и добавив его к элементу выбора.

// Loop over each player in the array and use the player and info keys of each player.
for (const [ index, { player, stats } ] of statsData.players.entries()) {

  // Get the name and info of each player.
  const { name, info } = player;

  // Get the first and last name out of the name property.
  const { first, last } = name;

  // Get the position info out of the info property.
  const { positionInfo } = info;

  // Create an option element with the player info available and add it to the select element.
  // The index is the number of position in the players array.
  const html = `<option value="${index}">${first} ${last}</option>`;
  select.insertAdjacentHTML('beforeend', html);
}

Теперь игроки выбираются в списке. И если вы добавите другого игрока к объекту с вашими данными об игроке, он также появится в списке при загрузке страницы.

Просмотрите приведенный ниже фрагмент, чтобы увидеть это в действии.

const statsData = {
  players: [{
      player: {
        info: {
          positionInfo: "Defender"
        },
        name: {
          first: "Toby",
          last: "Alderweireld"
        },
        currentTeam: {
          name: "Tottenham Hotspur"
        }
      },
      stats: [{
          name: "goals",
          value: 5
        },
        {
          name: "losses",
          value: 20
        },
        {
          name: "wins",
          value: 48
        },
        {
          name: "draws",
          value: 23
        }
      ]
    },
    {
      player: {
        info: {
          positionInfo: "Midfielder"
        },
        name: {
          first: "Yaya",
          last: "Toure"
        },
        currentTeam: {
          name: "Manchester City"
        }
      },
      stats: [{
          name: "goals",
          value: 65
        },
        {
          name: "losses",
          value: 49
        },
        {
          name: "wins",
          value: 149
        },
        {
          name: "draws",
          value: 35
        }
      ]
    },
    {
      player: {
        info: {
          positionInfo: "Attacker"
        },
        name: {
          first: "Riyad",
          last: "Mahrez"
        },
        currentTeam: {
          name: "Leicester City"
        }
      },
      stats: [{
          name: "goals",
          value: 22
        },
        {
          name: "losses",
          value: 23
        },
        {
          name: "wins",
          value: 35
        },
        {
          name: "draws",
          value: 21
        }
      ]
    }
  ]
};

const select = document.getElementById('select-player');
const nameField = document.getElementById('name');
const positionField = document.getElementById('position');
const statsList = document.getElementById('stats');

for (const [ index, { player, stats } ] of statsData.players.entries()) {
  const { name } = player;
  const { first, last } = name;
  const html = `<option value="${index}">${first} ${last}</option>`;
  select.insertAdjacentHTML('beforeend', html);
}

function emptyStatsList() {
  while(statsList.firstElementChild) {
    statsList.removeChild(statsList.firstElementChild);
  }
}

select.addEventListener('change', function(event) {
  const { target } = event;
  const { value } = target;
  const { player, stats } = statsData.players[value];
  const { name } = player;
  const { first, last } = name;
  nameField.innerText = `${first} ${last}`;
  positionField.innerText = value;
  // Empty stats list.
  emptyStatsList();
  // Loop through the stats array.
  for (const { name, value } of stats) {
    const stat = `<li>${name}: ${value}</li>`;
    statsList.insertAdjacentHTML('beforeend', stat);
  }
});
<select id="select-player">
  <option selected hidden value="">Select a player...</option>
</select>

<div>
  <div id="name"></div>
  <div id="position"></div>
  <ul id="stats"></ul>
</div>
...