【问题标题】:How to search and filter a Google Sheet based on two parameters in two different columns如何根据两个不同列中的两个参数搜索和过滤 Google 表格
【发布时间】:2019-10-17 21:47:51
【问题描述】:

我有一张 46 列的工作表,行数不定。我正在寻找一种方法来生成一个具有简单 UI 的 Web 应用程序,它可以让我按两个标准进行搜索并过滤掉所有与这些标准不匹配的结果。第一个是 name/emp# 搜索,分别位于第 3 列和第 4 列。另一种是日期搜索。我的想法是我可以搜索该人姓名或号码在该日期的所有实例,并将其作为 html 表格或类似的均匀且间隔合理的演示文稿返回。

下面是我目前试验过的代码。我的知识非常有限,我想了解它是如何工作的,所以让它尽可能简单是理想的。我已经能够使用 TextFinder 创建一个单框搜索,但我听说这可能会很慢,而且这张表可能会很大。我也不知道如何用另一个类别再次过滤它。我尝试获取第一个文本查找器的结果并通过另一个文本查找器运行它们,但没有奏效。

代码.gs

function doGet() {
  return HtmlService.createTemplateFromFile('index').evaluate();
}

function getValuesFromSS(search) {
  var ss = SpreadsheetApp.getActiveSpreadsheet().getSheetByName('Sheet1');
  var lastRow = ss.getLastRow();
  var range = ss.getRange(1,3,lastRow,2); //define range for column D
  var ranges = range.createTextFinder(search).findAll();
  var names = '';
  var nums = '';
  var dates = '';
  var urls = '';

  //loop through each range
  for (i = 0; i < ranges.length; i++) {

    var row = ranges[i].getRow();
    var lastCol = ss.getLastColumn();
    var values = ss.getRange(row, 1, 1, lastCol).getDisplayValues(); //get all values for the row
    var empname = values[0][2]; //column C
    var empnum = values[0][3];  //column D
    var date = values[0][4];  //column E
    var url = values[0][46];

    names+=Utilities.formatString("<td>" + empname + "</td>");
    nums+=Utilities.formatString("<td>" + empnum + "</td>");
    dates+=Utilities.formatString("<td>" + date + "</td>");
    urls+=Utilities.formatString("<td>" + "<a href='https://drive.google.com/uc?export=view&id='" + url + "'>DVIR</a>" + "</td>");
}

return {
  first: names,
  second: nums,
  third: dates,
  fourth: urls
}
}

index.html

<!DOCTYPE html>
<html>
<head>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
  <script type="text/javascript">

    function setPageValues () {
    var search = document.getElementsByName('searchtext')[0].value;
      google.script.run.withSuccessHandler(disp).getValuesFromSS(search);
    }

    function disp(values){
      document.getElementById("results1").innerHTML = values.first;
      document.getElementById("results2").innerHTML = values.second;
      document.getElementById("results3").innerHTML = values.third;
      document.getElementById("results4").innerHTML = values.fourth;
    }
  </script>
</head>
<style>
table {
    border-collapse: collapse;
    }
tr { 
  display: block; 
  float: left; 
  }
td {
    border: 1px solid Black;
    display: block; 
    }
</style>
<body>
<input type="text" name="searchtext">
<input type="button" value="Search" onclick="setPageValues();">
<br>
<div name="resultbox">
<table>
<tr id="results1">
</tr>
<tr id="results2">
</tr>
<tr id="results3">
</tr>
<tr id="results4">
</tr>
</table>
</div>
</body>
<script>
</script>
</html>

这是示例电子表格链接: https://docs.google.com/spreadsheets/d/1scFOr4nUXwm7brvlMPHFJhyLei3TI-uvoOVugsx-TeA/edit?usp=sharing

正如我所提到的,我想在一个框中搜索名称 -or- emp#,在另一个框中搜索日期,并仅过滤与两者匹配的结果以在 html 中显示。谢谢!

【问题讨论】:

    标签: javascript html google-apps-script google-sheets


    【解决方案1】:
    • 您不仅要搜索“驱动程序名称”和“驱动程序编号”,还要搜索电子表格中的“日期”。
      • 在这种情况下,存在仅输入“驱动程序名称”或“驱动程序编号”的情况。也有只输入“日期”的情况。
    • 您希望使用带有 Google Apps 脚本的 Web Apps 来实现此目的。

    如果我的理解是正确的,那么这个答案呢?请认为这只是几个答案之一。

    修改点:

    • 在此修改中,将日期输入标签添加到 HTML 端。
    • 输入“驱动程序名称”/“驱动程序编号”和“日期”后,这些值将作为对象发送到 Google Apps 脚本端。
    • 在 Google Apps 脚本中,使用 TextFinder 搜索这些值。
      • TextFinder 的处理成本低于搜索每一行的处理成本。所以我用“Driver Name”/“Driver Number”和“Date”来搜索。

    修改后的脚本:

    当你的脚本被修改时,请进行如下修改。

    HTML 端:index.html

    从:
    function setPageValues () {
      var search = document.getElementsByName('searchtext')[0].value;
      google.script.run.withSuccessHandler(disp).getValuesFromSS(search);
    }
    
    到:
    function setPageValues () {
      var search = document.getElementsByName('searchtext')[0].value;
      var date = document.getElementsByName('date')[0].value;
      var obj = {};
      if (!search && !date) alert("No search values.");
      if (search) {
        obj.name = search;
      }
      if (date) {
        obj.date = date;
      }
      google.script.run.withSuccessHandler(disp).getValuesFromSS(obj);
    }
    

    从:
    <input type="text" name="searchtext">
    <input type="button" value="Search" onclick="setPageValues();">
    
    到:
    <input type="text" name="searchtext">
    <input type="date" name="date">
    <input type="button" value="Search" onclick="setPageValues();">
    

    Google Apps 脚本端:code.gs

    从:
    var range = ss.getRange(1,3,lastRow,2); //define range for column D
    var ranges = range.createTextFinder(search).findAll();
    
    到:
    var ranges = [];
    if ("name" in search && search.name != "") {
      ranges = ss.getRange(1, 3, lastRow, 2).createTextFinder(search.name).findAll();
    }
    if ("date" in search && search.date != "") {
      var dateRanges = ss.getRange(1, 5, lastRow, 1).createTextFinder(search.date).findAll();
      if (ranges.length > 0) {
        ranges = ranges.filter(function(r1) {return dateRanges.some(function(r2) {return r1.getRow() == r2.getRow()})});
      } else {
        ranges = dateRanges;
      }
    }
    
    • 在这种情况下,当运行 Web 应用程序时,您可以看到 2 个输入标签。
      • 当您只输入“Driver Name”/“Driver Number”时,会显示通过搜索“Driver Name”/“Driver Number”检索到的值。
      • 仅输入“日期”时,会显示通过搜索“日期”检索到的值。
      • 当您输入“Driver Name”/“Driver Number”和“Date”时,会显示通过搜索“Driver Name”/“Driver Number”和“Date”检索到的值。

    注意:

    • 在这个修改后的脚本中,使用了您的共享电子表格。请注意这一点。
    • 对于输出,使用了您当前的脚本和格式。

    参考:

    如果我误解了您的问题并且这不是您想要的方向,我深表歉意。

    【讨论】:

    • 太完美了!非常感谢!!!我一直在尝试解决这个问题,并且做到了!感谢您将其与原著保持一致,以便更容易理解。
    • @NMALM 感谢您的回复。很高兴您的问题得到解决。
    • 我发现了一个小问题。看起来搜索包括标题,有没有办法排除第一行?我知道我以前读过它,我也会尝试自己弄清楚。
    • @NMALM 感谢您的回复。从您的问题中我无法注意到这一点。这是因为我的英语水平不好。我对此深表歉意。当您不想在搜索范围内包含标题行时,请将getRange(1, 3, lastRow, 2)getRange(1, 5, lastRow, 1)分别修改为getRange(2, 3, lastRow - 1, 2)getRange(2, 5, lastRow - 1, 1)
    • 这是非常好的信息。我从来没有提到我的数据有一个标题,所以这是我的错。非常感谢您,田池老师。
    【解决方案2】:

    使用查询函数动态显示更改结果。

    使用名称 range1 和命名 range2 作为过滤器指南以运行查询选择。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-08-26
      • 2015-12-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-09-29
      相关资源
      最近更新 更多