Day 29: Table

I modified the Table example from Fullstack D3 today.

What I changed:

  • Adding a month button to filter the table
  • Adding a min & max marker as an SVG element
  • Added the animated weather Icons as images. (I got the animated SVG from Meteocons)

It’s very interesting to add SVG elements to the table.

Below you can find different types of columns we can add to the table, text, SVG, image, and symbol.

console.log((d3.extent(dataset.slice(0, numberOfRows), d => +d.tempmax)))
    function getIconPath(iconType) {
        return `./img/${iconType}.svg`;
    }

    const columns = [
      {label: "Day", type: "date", format: d => dateFormat(d.datetime)},
      {label: "Description", type: "text", format: d => d.description},
      {label: "Min Temp", type: "number", format: d => d3.format(".1f")(d.tempmin), background: d => colorScale(tempScaleMin(+d.tempmin))},
      {label: "Min & Max Temp Marker", type: "marker", format: d => {
        const x1 = markerScale(+d.tempmin) + "%";
        const x2 = markerScale(+d.tempmax) + "%";
        return `
            <svg width="100%" height="20">
                <line x1="${x1}" y1="10" x2="${x2}" y2="10" stroke="#34495e" />
                <line x1="${x1}" y1="0" x2="${x1}" y2="20" stroke="#34495e" />
                <line x1="${x2}" y1="0" x2="${x2}" y2="20" stroke="#34495e" />
            </svg>
        `;
      }},
      {label: "Max Temp", type: "number", format: d => d3.format(".1f")(d.tempmax), background: d => colorScale(tempScaleMax(+d.tempmax))},
      {label: "Wind Speed", type: "number", format: d => d3.format(".2f")(+d.windspeed), background: d => grayColorScale(windScale(+d.windspeed))},
      {
        label: "Weather Icon",
        type: "centered",
        format: d => {
            return `
                <svg width="40" height="40">
                    <image href="${getIconPath(d.icon)}" width="30" height="30" />
                </svg>
            `;
        }
    },
      {label: "UV Index", type: "symbol", format: d => new Array(+d.uvindex).fill("✸").join("")},
    ]

Below are the code to create the table header and update the table body.

// Add table headers and an empty tbody
    table.append("thead").append("tr")
    .selectAll("th")
    .data(columns)
    .join("th")
    .text(d => d.label)
    .attr("class", d => d.type)

    // Append an empty tbody
    table.append("tbody")

    // update the table with value selected in the button

    function updateTable(dataForMonth) {
    const tbody = d3.select("#chart-area tbody");
    tbody.selectAll("tr").remove();

    // Use the actual data rows for the data bind
    tbody.selectAll("tr")
        .data(dataForMonth)
        .join("tr")
        .selectAll("td")
        .data(d => columns.map(column => ({ value: d, column })))
        .join("td")
            .html(d => d.column.format(d.value)) 
            .attr("class", d => d.column.type)
            .style("background", d => d.column.background && d.column.background(d.value))
            .style("transform", d => d.column.transform && d.column.transform(d.value))
    }

    // initiate the table with January data

    updateTable(dataByMonth["January"])

All the codes can be found here.

Leave a comment