首页 文章

根据单元格值格式化行颜色

提问于
浏览
0

我正在尝试调整this之前相关问题的示例脚本 . 对于列K中的单元格值为零的行,我想将该行设为黄色 .

这是我目前改编的代码:

function colorAll() {
  var sheet = SpreadsheetApp.getActiveSheet();
  var startRow = 3;
  var endRow = sheet.getLastRow();

  for (var r = startRow; r <= endRow; r++) {
    colorRow(r);
  }
}

function colorRow(r){
  var sheet = SpreadsheetApp.getActiveSheet();
  var c = sheet.getLastColumn();
  var dataRange = sheet.getRange(r, 1, 1, c);

  var data = dataRange.getValue();
  var row = data[0];

  if(row[0] === "0"){
    dataRange.setBackground("white");
  }else{
    dataRange.setBackground("yellow");
  }

  SpreadsheetApp.flush(); 
}

function onEdit(event)
{
  var r = event.source.getActiveRange().getRowIndex();
  if (r >= 3) {
    colorRow(r);
  }
}

function onOpen(){
  colorAll();
}

我的问题是,我可以't figure out how to reference column K. In the linked answer above, the script'的创建者声称,“[h]是一个Google Apps脚本示例,它根据A列中的值更改整行的背景颜色." First, and most importantly, I can't figure out where he's referencing column A. I thought changing " var dataRange = sheet.getRange(r,1 ,1,c); " to " var dataRange = sheet.getRange(r, 11 ,1,c);“会这样做,但只是在我的工作表的末尾添加了10个空白列,然后脚本崩溃了 . 我不懂为什么 .

其次,但更多的是,他声称脚本影响整行是不准确的,因为他原来的“var dataRange = sheet.getRange(r,1,1,3);”只有前三列的颜色 - 这就是我添加“var c”并将“3”改为“c”的原因 .

此外,当我播放/调试脚本,或从电子表格脚本管理器运行"onEdit"时,我得到“TypeError:无法从未定义读取属性"source" . " I can see that " source”未定义 - 我错误地认为它最初是一个方法 - 但我我也不确定如何解决这个问题 .

最后,列K并不总是参考列,因为我的意思是在其左侧添加更多列 . 我假设我每次添加列时都必须更新脚本,但是第2行中的列 Headers 永远不会改变,所以如果有人可以帮我设计一些代码来查找行中的特定字符串2,然后获取该列参考用于函数colorRow(),我将不胜感激 .

我不知道这个脚本是否有效地构建,但理想情况下,我希望我的电子表格是被动的 - 我不想在编辑驱动单元格或打开后重新运行此脚本;它看起来像它应该这样做(它不是错误的),但这是我第一次尝试使用Google Apps脚本,我不确定是什么 .

我真的从零开始设计,但我理解基本的原理和概念,即使我能理解"++"在"for"语句中我使用的第三个参数中的含义:“for(var r = startRow; r <= endRow; r++ ) . “我认为我在寓言上相当于一个有文化的西班牙语演讲者试图读意大利语 .

将非常感谢帮助和教育解释/示例 . 谢谢你阅读/略读/跳过这句话 .

2 回答

  • 2

    我会尝试给你解释你提出的具体问题,而不是重写你已经得到一些帮助的代码 . 我看到你已经有了一些答案,但我完全把事情搞得一团糟,因为它有助于理解 .

    My problem is, I can't figure out how to reference column K.

    A列= 1,B = 2,...... K = 10 .

    I can't figure out where he's referencing column A.
    

    当您更改.getRange时,您很接近 . .getRange根据()中的参数数量做不同的事情 . 有4个参数,它是getRange(row,column,numRows,numColumns) .

    sheet.getRange(r, 1, 1, c)  // the first '1' references column A
    

    从行(r)开始,行(r)最初是行(3)和列(1) . 所以这是细胞(A3) . 范围扩展为1行和(c)列 . 由于c = sheet.getLastColumn(),这意味着您已将范围设为1行和所有列 .

    当你改成这个

    var dataRange = sheet.getRange(r, 11, 1, c)  // the '11' references column L
    

    你有一个从第(3)列(L)开始的范围为11 = L.这将运行到第(3)行(getLastColumn()) . 如果你已经超出范围,这将会发生奇怪的事情 . 您可能已将其推入无限for循环,这将导致脚本崩溃

    其次,但更多的是,他声称脚本影响整行是不准确的,因为他原来的“var dataRange = sheet.getRange(r,1,1,3);”只有前三列的颜色 - 这就是我添加“var c”并将“3”改为“c”的原因 .

    你是对的 . (3)表示该范围延伸3列 .

    "TypeError: Cannot read property "source" from undefined."
    

    这里发生的事情并不直观清晰 . 您无法从电子表格脚本管理器运行onEdit(event)函数,因为它期待“事件” .

    • onEdit是一个特殊的谷歌触发器,只要编辑电子表格就会运行 .

    • 它传递了激活它的(事件)和

    • event.source . 指事件发生的表格

    • var r = event.source.getActiveRange() . getRowIndex();获取编辑发生的行号,这是将改变颜色的行 .

    如果你在管理器中运行它,那么就没有事件要读它未定义 . 由于同样的原因,您无法调试它 .

    最后,列K并不总是参考列,因为我的意思是在其左侧添加更多列 . 我假设我每次添加列时都必须更新脚本,但是第2行中的列 Headers 永远不会改变,所以如果有人可以帮我设计一些代码来查找行中的特定字符串2,然后获取该列参考用于函数colorRow(),我将不胜感激 .

    在我给你代码帮助她之前,我有另一个建议,因为你也谈论效率,在电子表格中运行函数通常比使用脚本更快 . 您可以尝试将列A作为索引列,其中ColumnA(行#)= ColumnK(行#) . 如果将以下内容放入单元格(A1)中,ColumnA将与列K完全匹配 .

    =ArrayFormula(K:K)
    

    更好的是,如果在A和K之间添加/删除列,则公式将更改其引用而不执行任何操作 . 现在只需隐藏columnA,您的工作表就会恢复其原始外观 .

    这是您的代码帮助,利用您自己的一些代码 .

    function findSearchColumn () {
      var colNo;  // This is what we are looking for.
      var sheet = SpreadsheetApp.getActiveSheet();
      var c = sheet.getLastColumn();
    
      // gets the values form the 2nd row in array format
      var values = sheet.getRange(2, 1, 1, c).getValues();
      // Returns a two-dimensional array of values, indexed by row, then by column.
    
      // we are going to search through values[0][col] as there is only one row
      for (var col = 0; col < data[0].length; col++) { // data[0].length should = c
        if (data[0][col] == value) {
          colNo = col;
          break; // we don't need to do any more here.
        }
      }
      return(colNo);
    }
    

    如果break给你一个问题,只需删除它并让外观完整或用col = data [0] .length替换它;

    我无法判断这个脚本是否有效构建,但理想情况下,我希望我的电子表格能够被动 - 我不想在编辑驱动单元后或打开时重新运行此脚本;它看起来像它应该这样做(它不是错误的),但这是我第一次尝试使用Google Apps脚本,我不确定是什么 .

    没关系,效率的微调取决于电子表格 . 函数onEdit(event)将在每次编辑工作表时运行,没有什么可以做的 . 然而,它应该做的第一件事是检查相关范围是否已被编辑 . if(r> = 3)的行似乎正在这样做 . 您可以根据需要进行定制 . 我对隐藏索引列的建议旨在提高效率并且更容易实现 .

    I'm not great with scripting,

    你做得很好,但可以做一些背景阅读,只需查看循环等内容 . 不幸的Python在语法上与许多其他语言不同 . 谷歌脚本中的for循环与VBA,C,JAVA等等相同 . 所以阅读这些基本操作实际上是教你很多语言 .

    I don't understand what the "++" means in the third argument in the "for" statement 这就是为什么语言C得名,作为程序员的笑话 .

    r与r = r 1相同

    r--表示r = r-1

    r 2表示r = r 2

    所以

    for (var r = startRow; r <= endRow; r++)
    
    • 表示r以startRow开头,在本例中为3 .

    • 循环将一直运行直到r <= endRow,在这种情况下是sheet.getLastRow()

    • 每次循环运行r后增加1,所以如果endRow == 10,循环将从r = 3运行到r = 10 => 8次

  • 0
    1. onEdit 是一个特殊功能,在您编辑电子表格时会自动调用 . 如果手动运行它,则无法使用所需的参数 .

    2.当K列为0时,要更改整行的颜色,必须对脚本进行简单的修改 . 见下文

    function colorRow(r){
      var sheet = SpreadsheetApp.getActiveSheet();
      var c = sheet.getLastColumn();
      var dataRange = sheet.getRange(r, 1, 1, c); 
    
      var data = dataRange.getValues(); 
    
      if(data[0][10].toString() == "0"){ //Important because based on the formatting in the spreadsheet, this can be a String or an integer 
        dataRange.setBackground("white");
      }else{
        dataRange.setBackground("yellow");
      }
    
      SpreadsheetApp.flush(); 
    }
    

相关问题