不能 array.map 使用 css 网格来为动态数据创建 table

cant array.map with css grid to make table for dynamic data

尝试用 css 网格制作一个看起来像这样的 table:

不使用动态数据和 array.map 我可以做到,但是当涉及到以 DRY 方式编写时,我就是想不通。

Snippet 不会 运行(不知道如何使用它来反应),只是为了显示代码。

:root {
  --color-primary-purple: #c3a5ff;
  --color-primary-blue: #6fdce0;
  --title-font-h2: 30px;
}

.infoTable {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-template-rows: repeat(4, 1fr);
  grid-template-areas: "c1 c2 c3" "c4 c5 c6" "c7 c8 c9" "c10 c11 c12";
  justify-content: center;
  align-content: center;
  font-family: "Roboto";
  width: 944px;
}

.infoTable__cell_1 {
  grid-area: c1;
}

.infoTable__cell_2 {
  grid-area: c2;
}

.infoTable__cell_3 {
  grid-area: c3;
}

.infoTable__cell_4 {
  grid-area: c4;
}

.infoTable__cell_5 {
  grid-area: c5;
}

.infoTable__cell_6 {
  grid-area: c6;
}

.infoTable__cell_7 {
  grid-area: c7;
}

.infoTable__cell_8 {
  grid-area: c8;
}

.infoTable__cell_9 {
  grid-area: c9;
}

.infoTable__cell_10 {
  grid-area: c10;
}

.infoTable__cell_11 {
  grid-area: c11;
}

.infoTable__cell_12 {
  grid-area: c12;
}

.infoTable__cell_4,
.infoTable__cell_5,
.infoTable__cell_7,
.infoTable__cell_8,
.infoTable__cell_10,
.infoTable__cell_11 {
  border-right: 3px solid rgba(196, 196, 196, 0.06);
}

.infoTable__cell {
  text-align: start;
  padding: 0 25px 5px 25px;
  display: flex;
  align-items: center;
}

.infoTable__columnTitle {
  font-size: var(--title-font-h2);
  font-weight: 700;
  margin: 0;
  color: white;
}

.infoTable__text {
  font-size: 20px;
  font-weight: 700;
  margin: 0;
  width: 280px;
  color: var(--color-primary-purple);
}

.infoTable__text_2 {
  color: var(--color-primary-blue);
}
<div className="infoTable">
      <div className="infoTable__cell infoTable__cell_1">
        <h2 className="infoTable__columnTitle">Name</h2>
      </div>

      <div className="infoTable__cell infoTable__cell_2">
        <h2 className="infoTable__columnTitle">Client</h2>
      </div>

      <div className="infoTable__cell infoTable__cell_3">
        <h2 className="infoTable__columnTitle">Date</h2>
      </div>

      <div className="infoTable__cell infoTable__cell_4">
        <p className="infoTable__text">Build Intranet API</p>
      </div>

      <div className="infoTable__cell infoTable__cell_5">
        <p className="infoTable__text">Demo Customer 1</p>
      </div>

      <div className="infoTable__cell infoTable__cell_6">
        <p className="infoTable__text">06/15/20</p>
      </div>

      <div className="infoTable__cell infoTable__cell_7">
        <p className="infoTable__text">Migrate Sage Data to Sharepoint</p>
      </div>

      <div className="infoTable__cell infoTable__cell_8">
        <p className="infoTable__text">Demo Customer 1</p>
      </div>

      <div className="infoTable__cell infoTable__cell_9">
        <p className="infoTable__text">11/05/21</p>
      </div>

      <div className="infoTable__cell infoTable__cell_10">
        <p
          className={
            customer2 ? `infoTable__text infoTable__text_2 ` : `infoTable__text`
          }
        >
          Build Dynamics 365 to ProCore Integration
        </p>
      </div>

      <div className="infoTable__cell infoTable__cell_11">
        <p
          className={
            customer2 ? `infoTable__text infoTable__text_2 ` : `infoTable__text`
          }
        >
          Demo Customer 2
        </p>
      </div>

      <div className="infoTable__cell infoTable__cell_12">
        <p
          className={
            customer2 ? `infoTable__text infoTable__text_2 ` : `infoTable__text`
          }
        >
          01/05/20
        </p>
      </div>
    </div>

可运行代码:https://codesandbox.io/s/polished-bush-x7vllz?file=/src/InfoTable/InfoTable.js:212-2192

如果您将数据维护为对象数组,则可以迭代它们以生成一系列构成网格的 div。您可以根据添加到数据对象的 clientid 为它们分配不同的颜色 类。

const { Fragment } = React;

// The data which we pass into the component as a prop
const data = [
  { clientId: 1, task: 'Build internet API', clientName: 'Demo customer one', date: '06/15/20' },
  { clientId: 1, task: 'Migrate Sage data to Sharepoint', clientName: 'Demo customer one', date: '11/05/21' },
  { clientId: 2, task: 'Build Dynamics 365 to ProCore Integration', clientName: 'Demo customer two', date: '06/15/20' }
];

// The function that returns all the grid data
function buildGrid(data) {

  // `map` over the data, and for each object
  return data.map(obj => {

    // get the clientId, the name, client (name), and the date
    const { clientId, task, clientName, date } = obj;

    // Create a class name from the clientId property
    const clientClass = `client${clientId}`;

    // And then return a series of divs contained by
    // a fragment. We need the fragment instead of a container
    // otherwise we end up with columns instead of rows
    return (
      <Fragment>
        <div class={clientClass}>{task}</div>
        <div class={clientClass}>{clientName}</div>
        <div class={clientClass}>{date}</div>
      </Fragment>
    );
  });
}

function Example({ data }) {
    
  // And then in your JSX just add in the headings
  // add call the function with your data
  return (
    <div class="grid">
      <div class="heading">Task</div>
      <div class="heading">Client</div>
      <div class="heading">Date</div>
      {buildGrid(data)}
    </div>
  );

}

ReactDOM.render(
  <Example data={data} />,
  document.getElementById('react')
);
.grid { display: grid; grid-template-columns: repeat(3, 1fr); justify-content: center; align-content: center; width: 100%; padding: 0.5em; background-color: #272a2f; gap: 1em; }
.heading { font-size: 1.2em; font-weight: 600; color: #efefef; }
.client1 { color: #ab9af7; }
.client2 { color: #65d3da; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.2/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.2/umd/react-dom.production.min.js"></script>
<div id="react"></div>