【问题标题】:How do I improve my script for dragging multiple cells in Google Apps Scripts?如何改进我的脚本以在 Google Apps 脚本中拖动多个单元格?
【发布时间】:2021-02-06 09:31:27
【问题描述】:

我在这里有一个谷歌脚本,它将行从一张表发送到另一张表,然后根据单元格值删除源行。目的是将旧任务发送到单独的电子表格(即从“任务列表”选项卡到“存档任务列表”选项卡),以防止在一张表中过度拥挤。

当我将状态(第 5 列)更改为“存档”时,我的代码成功运行,但是当我尝试一次更改多行(即向下拖动或复制)时,脚本仅适用于一行。我想我必须创建某种循环来阻止这个问题,但我是脚本新手,所以任何关于这方面的帮助都会很棒!

这是我目前的代码:

function onEdit(event) {
  // assumes source data in sheet named Task List
  // target sheet of move to named Archive Task List
  // test column with "Archive" is col5
  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var s = event.source.getActiveSheet();
  var r = event.source.getActiveRange();

  if(s.getName() == "Task List" && r.getColumn() == 5 && r.getValue() == "Archive") {
    var row = r.getRow();
    var numColumns = s.getLastColumn();
    var targetSheet = ss.getSheetByName("Archive Task List");
    var target = targetSheet.getRange(targetSheet.getLastRow() + 1, 1);
    s.getRange(row, 1, 1, numColumns).moveTo(target);
    s.deleteRow(row);
  }
}

更新: 我已经实现了建议的代码更改,并且脚本对于单行编辑仍然可以正常工作,但是如果我一次进行 2 次或更多编辑,则循环会将某些行归档到所选范围之外。一个例子是,如果我将单元格 F16:F19 全部复制为条目“存档”并粘贴到 col5 中。 我更新的代码是:

function onEdit(event) {
  // assumes source data in sheet named Task List
  // target sheet of move to named Archive Task List
  // test column with "Archive" is col5 
  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var s = event.source.getActiveSheet();
  var r = event.source.getActiveRange();

  if(s.getName() == "Task List" && r.getColumn() == 5 && r.getValue() == "Archive") {
    var row = r.getRow();
    var lastRow = r.getLastRow(); //Save the last edited row index
    var numColumns = s.getLastColumn();
    var numRows = lastRow - row == 0? 1: lastRow - row; // numRows has to be at least 1 =, this is in case of a single-line row.
    var targetSheet = ss.getSheetByName("Archive Task List");
    var target = targetSheet.getRange(targetSheet.getLastRow() + 1, 1);
    //s.getRange(row, 1, 1, numColumns).moveTo(target);
    s.getRange(row, 1, numRows, numColumns).moveTo(target); // Take in account the lastRow when archiving the edited range.     
    //s.deleteRow(row);
    for (let i = row; i<=lastRow; i++) {
      s.deleteRow(i);
      console.log(`Deleted row ${i}`);
    }
  }
}

【问题讨论】:

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


    【解决方案1】:

    考虑

    在您当前的脚本中,您只使用编辑范围的第一行: var row = r.getRow();。这就是为什么它只需要多行编辑范围的第一行。要克服这个问题,您应该考虑编辑范围的最后一行,您可以使用 var lastRow = r.getLastRow(); 轻松获得它。

    记住这一点,我建议对您的脚本进行以下修改:

    解决方案

    第一个:

       var row = r.getRow();
       var lastRow = r.getLastRow(); //Save the last edited row index
    

    第二次(已编辑):

    获取整个编辑行的正确语法:getRange(row, column, numRows, numColumns)

        var numRows = lastRow-row + 1; // Corrected this calculation
        s.getRange(row, 1, numRows, numColumns).moveTo(target); // Take in account the lastRow when archiving the edited range. 
    

    第 3 次(已编辑):

    删除所有存档的行:

    for (let i = row; i<=lastRow; i++) {
          s.deleteRow(row); // The row deletion will slide up all the other rows so the next row to delete will have always the same index
          console.log(`Deleted row ${row} at pass number ${i}`);
        }
    

    这是一个循环操作,循环编辑范围内的行。

    参考文献

    getRange(row,col,numRow,numCol)

    for loop

    Event Objects

    【讨论】:

    • 我已经实现了您建议的代码更改,并且脚本对于单行编辑仍然可以正常工作,但是如果我一次进行 2 次或更多编辑,则循环将归档所选范围之外的某些行- 任何想法为什么或如何解决这个问题?
    • 请更新您的问题,举例说明您如何编辑单元格和更新后的代码。
    • 我明白了,抱歉我弄错了。请查看我的更新答案。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多