对于 google-apps-script 初学者来说,这是一个大项目,我有一个数组(columnValues)中的 list 列表,需要搜索用户关注的内容(成分)。现在它只是在寻找精确的匹配项,但我要回去让它更智能(在一些帮助下),尽管我现在无法让我的匹配项(匹配项)数组显示在我的侧边栏中。我想最终为用户提供一个更智能的潜在匹配列表(比如搜索水煮鸡会得到鸡胸肉、鸡翅和水煮三文鱼)。单击时,我希望将值写入与用户焦点相关的某些单元格(两个单元格上方)。
那么我应该根据我想做的事情把它做成列表还是表格来显示在侧边栏中呢?我该如何修复构成列表的函数?欢迎任何有关使搜索更智能的建议。也欢迎任何给初学者的提示。
JSFiddle 链接:https://jsfiddle.net/amreinj/fk1a5to7/
Google 文档链接:https://docs.google.com/spreadsheets/d/1Xnbvy4tg2jNhYqL8QKIPJ28AcJ0whygygKzrQ51cGvQ/edit?usp=sharing
我没有使用 jQuery 而这个答案使用了它,可以使用翻译:How to return an array (Google apps script) to a HTML sidebar?
代码.gs
function onOpen() {
SpreadsheetApp.getUi()
.createMenu('Costing Tools')
.addItem('Search menu', 'showSidebar')
.addToUi();
}
function showSidebar() { // Brings up side bar to do inventory search
var html = HtmlService.createHtmlOutputFromFile('page')
.setTitle('Inventory search')
.setWidth(300);
SpreadsheetApp.getUi()
.showSidebar(html);
}
function onSearch() { //When the search button is pressed it loops through the inventory list and finds exact matches eventually I'd like it to be smart
var ui = SpreadsheetApp.getUi();
var ingredient = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet().getActiveCell().getValue(); //user focus, they click on the item they want to search
Logger.log('i ' + ingredient); //debug
var isheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("INVENTORY");
var columnValues = isheet.getRange("G:G").getValues(); //inventory list
var i = columnValues.length,
array, flag = false,
matches = [];
while (i--) { //walk through columnValues
array = columnValues[i]; //get the ingredient in the li
if (-1 !== array.indexOf(ingredient)) { //-1, string not found
flag = true;
matches.push(array);
}
}
if (!flag) {
ui.alert('No match found.');
} else {
Logger.log('m ' + matches); //debug
function makeUL(arr) { //This function not working
var list = document.createElement('ul'); // Create the list element
Logger.log(list); //debug
for (var i = 0; i < arr.length; i++) { //loop through the array to make the list
var item = document.createElement('li'); // Create the list item
item.appendChild(document.createTextNode(arr[i])); // Set its contents
Logger.log(item); //debug
list.appendChild(item); // Add it to the list
}
Logger.log(list); //debug
return list;
}
document.getElementById('foo').appendChild(makeUL(matches)); //this doesn't work
}
}
页面.html
<!DOCTYPE html>
<html>
<head>
<script >
</script>
<base target="_top">
</head>
<body>
<p>Click on the ingredient you want to find in inventory and then click search.</p>
<button onclick="google.script.run.onSearch()">Search</button>
<br>
<br>
<div id="foo">Results</div>
</body>
</html>
最佳答案
"How could I fix the function that makes the list?"
你编写函数 makeUL(arr)
的地方,它负责 DOM 操作和这行代码:
document.getElementById('foo').appendChild(makeUL(matches));
完全是在错误的地方。您正在尝试在 google app script code.gs
文件中操作 HTML DOM 元素,而 google app script 无法直接操作 dom 元素。 HTML 的 document
和它的 API 在谷歌应用程序脚本中不可用。它在浏览器中可用。
那么你应该怎么做?
您应该将 matches
列表从 google app script 返回给客户端,并在 page.html
中编写您的 makeUL
函数您的 javascript 将运行。
page.html:
<!DOCTYPE html>
<html>
<head>
<base target="_top">
</head>
<body>
<p>Click on the ingredient you want to find in inventory and then click search.</p>
<button onclick="onSearchClickHandler()">Search</button>
<br>
<br>
<div id="foo">Results</div>
<script>
// search button click handler
function onSearchClickHandler(e){
google.script.run
.withFailureHandler(function(err){
// failure handler callback
console.log(err)
})
.withSuccessHandler(function(arr){
// arr is your match array returned by onSearch
if(arr.length > 0){
var domList = makeUL(arr);
// document object will be available here
document.getElementById('foo').appendChild(domList);
}
})
.onSearch()
}
function makeUL(arr) {
var list = document.createElement('ul'); // Create the list element
console.log(list); //debug
for (var i = 0; i < arr.length; i++) { //loop through the array to make the list
var item = document.createElement('li'); // Create the list item
item.appendChild(document.createTextNode(arr[i])); // Set its contents
console.log(item); //debug
list.appendChild(item); // Add it to the list
}
console.log(list); //debug
return list;
}
</script>
</body>
</html>
另请注意,在 makeUL
函数中,我已将 Logger.log
替换为 console.log
,这是因为 Logger 在 google app script 中可用,console 在浏览器 window 对象中可用。
代码.gs:
function onSearch() { //When the search button is pressed it loops through the inventory list and finds exact matches eventually I'd like it to be smart
var ui = SpreadsheetApp.getUi();
var ingredient = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet().getActiveCell().getValue(); //user focus, they click on the item they want to search
Logger.log('i ' + ingredient); //debug
var isheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("INVENTORY");
var columnValues = isheet.getRange("G:G").getValues(); //inventory list
var i = columnValues.length,
array, flag = false,
matches = [];
while (i--) { //walk through columnValues
array = columnValues[i]; //get the ingredient in the li
if (-1 !== array.indexOf(ingredient)) { //-1, string not found
flag = true;
matches.push(array);
}
}
if (!flag) {
ui.alert('No match found.');
}
return matches;
}
我自己没有运行代码,但它应该是这样工作的。
"So should I make it a list or a table to display it in the sidebar based on what I want to do?"
完全取决于您想要实现的用户体验;你如何设计你的用户界面。
"Any advice on making the search smarter would be welcome."
根据您的用例,您可以将成分分解为单独的词,然后进行匹配。如果任何关键字匹配,则将其添加到匹配数组。即在您的配料表中:鸡胸肉、鸡翅。用户搜索鸡肉时,可以用空格符拆分配料:
ingredientList = ["chicken breast", "chicken wings"];
ingredientWords = ingredientList[0].split(" ");
ingredientWords
将有 ["chicken", "breast"]
并检查此数组是否包含您的搜索词“chicken”,然后您可以在匹配项中添加该项目.
如果你想要更高级的匹配方案,你可以使用Levenshtein distance algorithm , bitap algorithm .您可以使用 fuzzy matching algorithms .你会发现很多字符串匹配、字符串相似度算法。使用高级算法取决于您的用例和您想要实现的目标。
" Also any tips for a beginner would be welcome."
通过谷歌应用程序脚本教程,查看 documentation了解哪些 API 可用以及它们的作用。此外,google app script 在 google 服务器上运行,因此您在浏览器中获得的所有那些 API 和 javascript 对象,即 window、document、console、alert 等在 google 上不可用应用程序脚本。操作 HTML dom 的代码应该在客户端,即浏览器上。
如何将字符串和对象从 google app script 发送到您在 中的客户端代码 document bound script 看到这个answer .
关于javascript - 如何在 Google 应用程序脚本中将数组显示到 HTML 侧边栏,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39022630/