Source code - Fluid Topics - Latest

Fluid Topics Designer Guide

Category
Reference Guides
Audience
public
Version
Latest

The following HTML content sets up a container for the table.

The following JavaScript content performs two primary functions:

  • Select all the documents where the document type is map.
  • Retrieve the ft:lastEdition metadata values for each document.

The following JavaScript example relies on:

To add the same Custom component:

  1. In the HTML panel, copy and paste the following:

    <div id="result">
    <table id="result_table">
        <thead>
        <tr>
          <th>Type</th>
          <th>Title</th>
          <th>Last edition</th>
        </tr>
      </thead>
      <tbody>
      </tbody>
      </table>
    </div>
    <div id="result_paging"></div>
    
  2. In the CSS panel, copy and paste the following:

    div#result {
      margin:0px;
      width:100%;
    }
    
    table#result_table {
      border: 1px solid black;
      border-collapse: collapse;
    }
    
    table#result_table td, #result_table th {
      border: 1px solid black;
      padding: 15px 5px;
    }
    
    table#result_table th {
      background-color:#E8ECEF;
    }
    
    div#result_paging {
      margin-top: 10px;
    }
    
    div#result_paging a, div#result_paging span {
      border: 1px solid #000;
      border-radius: 10px;
      padding: 5px;
    }
    
  3. In the JS panel, copy and paste the following:

    (async () => {
      const FTAPI = await new window.fluidtopics.FluidTopicsApi();
      FTAPI["Ft-Calling-App"] = "page-designer";
    
      let allResults = []; // Store all the fetched results
      let currentPage = 1; // Initialize the current page of the table
      const resultsPerPage = 10; // Number of results to display per page of the table
    
      /********* Search Request **********/
    
      async function fetchResults() {
        let body = {
          "filters": [{ 'key': 'ft:editorialType', values: ['book'] }],
          "paging": {
            "perPage": 50
          }
        };
    
        try {
          let apiMaps = await FTAPI.post('/api/khub/clustered-search', body);
    
          allResults = apiMaps.results.map(result => {
            let entry = result.entries[0];
            return {
              'type': entry.type,
              'url': entry.map.readerUrl,
              'title': entry.map.title,
              'metadata': entry.map.metadata
            };
          });
    
          displayResults(currentPage);
        } catch (error) {
          console.error('Error fetching search results:', error);
        }
      }
    
      /********* Metadata **********/
    
      function get_metadata_value_by_key(metas, key) {
        let o = metas.find(e => e.key === key);
        return (o === undefined ? '' : o.values.join(', '));
      }
    
      /********* Results Display **********/
    
      function displayResults(page) {
        // Calculate start and end indices for slicing the results
        const start = (page - 1) * resultsPerPage;
        const end = start + resultsPerPage;
        const paginatedResults = allResults.slice(start, end);
    
        let tbody = document.querySelector("#result_table tbody");
        tbody.innerHTML = ""; // Clear previous results from tbody
    
        paginatedResults.forEach(r => {
          let row = tbody.insertRow();
          let cell = row.insertCell();
          cell.innerHTML = r.type;
          cell = row.insertCell();
          cell.innerHTML = `<a href="${r.url}">${r.title}</a>`;
          cell = row.insertCell();
          cell.innerHTML = get_metadata_value_by_key(r.metadata, 'ft:lastEdition');
        });
    
        // Pagination
        let div_paging = document.getElementById("result_paging");
        div_paging.innerHTML = ""; // Clear previous pagination
    
        if (currentPage > 1) {
          let prevButton = document.createElement('button');
          prevButton.innerText = 'Prev';
          prevButton.onclick = () => {
            if (currentPage > 1) {
              currentPage -= 1;
              displayResults(currentPage);
            }
          };
          div_paging.appendChild(prevButton);
        }
    
        let total_pages = Math.ceil(allResults.length / resultsPerPage);
        let pageInfo = document.createElement('span');
        pageInfo.innerText = `${currentPage}/${total_pages}`;
        div_paging.appendChild(pageInfo);
    
        if (currentPage < total_pages) {
          let nextButton = document.createElement('button');
          nextButton.innerText = 'Next';
          nextButton.onclick = () => {
            if (currentPage < total_pages) {
              currentPage += 1;
              displayResults(currentPage);
            }
          };
          div_paging.appendChild(nextButton);
        }
      }
    
      // Initial fetch
      fetchResults();
    })();
    
  4. Save the component.

  5. Save and publish the page.