我有一个Google Spreadsheet,可以与员工共享,以记录每个订单的详细信息。 这仅是示例:
https://docs.google.com/spreadsheets/d/1r8_6S_jI-ZzL1GgZEur4ZVM51xqu3fWfnbFOHw3ZTZw/edit?usp=sharing
每次关闭订单时,我希望保护整个订单行,以免错误编辑。 在示例文件中,我有一个脚本代码,是从其他一些帖子中复制的(我再也找不到了),但是我和原始海报之间的需求有点不同,因此我编辑了范围,但仍然无法做到完美。
这就是我需要的:
如果G2 = 1,则只有所有者才能进行A2:F2保护。 当G2为其他值时,清除保护范围A2:F2。 我需要它在2000年之前的每一行中都执行相同的操作。 (G3 = 1然后保护A3:F3) (G4 = 1然后保护A4:F4) 直到2000行为止都是这样的。
我希望将相同的代码应用于所有4个标签(Sheet1至Sheet4)
我发现使用当前脚本,如果G2 = 1,则每次编辑内容都会在相同范围(A2:F2)中添加一个新范围。我记得原来的帖子是onOpen,但我必须将其设置为onEdit,以确保所有内容均受到良好的保护。
答案 0 :(得分:1)
也许这可以帮助您。首先要考虑以下几点:
首先,创建范围不是一个快速的过程,它需要0.5到1秒,因此对于4张纸中的2000行(即8000行)执行此操作将需要1或2个小时,而即使您是Enterprise G Suite用户,也远远超出执行时间limit。
范围的主要问题是它们存储在SpreadsheetApp.ProtectionType.RANGE
中,这会创建一个范围数组,因此要在G不为1时删除特定范围,必须将编辑的行与Range数组的所有值。
此脚本在您每次编辑一行时都会执行,如果它受到保护(G = 1),则不执行任何操作;如果不行,并且您更改G = 1,则它将保护该行的范围A:F。如果更改G中的1,则会删除保护。因此,这不会保护或取消保护4张工作表的每一行,而只会保护或取消保护您在任何工作表中编辑的行。
function onEdit() {
var sprsheet = SpreadsheetApp.getActiveSpreadsheet();
var sheet = sprsheet.getActiveSheet();
var protections = sheet.getProtections(SpreadsheetApp.ProtectionType.RANGE);
var col_G = sheet.getRange("G2:G2000").getValues();
var edited_row = sheet.getActiveRange().getRow();
var protected = false;
var range_pos;
modifyProtection(edited_row, protections, col_G, sheet, protected);
}
function modifyProtection(edited_row, protections, col_G, sheet, protected, range_pos){
if (protections.length == 0 && col_G[edited_row - 2] == 1){ //In case there aren't ranges yet
createRange(edited_row, sheet);
} else {
for (var i = 0; i < protections.length; i++){
if (edited_row == protections[i].getRange().getRow()){
range_pos = i;
protected = true;
}
}
if (protected && col_G[edited_row - 2] != 1){
protected = false;
deleteRange(range_pos, protections);
} else {
if (!protected && col_G[edited_row - 2] == 1){
protected = true;
createRange(edited_row, sheet);
}
}
}
}
function createRange(edited_row, sheet, protected){
var range = sheet.getRange('A'+(edited_row)+':F'+(edited_row));
var protection = range.protect().setDescription('Sample protected range');
var me = 'your_email';//This will be the only editor of the protected ranges
protection.addEditor(me);
protection.removeEditors(protection.getEditors());
if (protection.canDomainEdit()) {
protection.setDomainEdit(false);
}
}
function deleteRange(i, protections){
protections[i].remove();
}