シート上では数行しか見えていなくても、getValuesは指定した範囲の値を取得します。非表示になっている行が自動で除かれるわけではありません。画面の見た目と同じ対象を読みたいときは、何によって行が隠れているかを確認します。
GASには通常のフィルタによる非表示と、利用者が手動で隠した行を調べるメソッドがあります。ただし、フィルタ表示は通常のフィルタと別の仕組みです。まず「通常フィルタと手動非表示を除く」という範囲を決めた、小さな読み取り処理から始めます。
フィルタと手動非表示の違い
isRowHiddenByFilterは、通常のフィルタで隠れている行を調べます。公式のSheetリファレンスは、フィルタ表示を対象にしないと明記しています。ブラウザで見えている状態を、すべてこのメソッドで再現できるとは考えないでください。
isRowHiddenByUserは手動で非表示にした行の確認に使います。行を隠す理由が「今だけ見たくない」なのか「集計から外したい」なのかは、シートの状態だけでは決まりません。集計の業務条件を、表示の操作へ依存させてよいかも先に確認します。
日々の集計なら、対象列に「対象」「保留」などの明示的な値を持つ方法もあります。非表示行を除く方式は、表示状態を今回の選択条件として使う場合に向いています。恒久的な対象判定と混ぜないことが大切です。
行番号と値を組にして返す
練習用シート「表示練習」のA2:B5に4件のデータを用意します。3行目を通常フィルタで隠し、4行目は手動で隠した状態を想定します。
function readVisibleRows(sheet, startRow, count, width) {
if (![startRow, count, width].every(Number.isSafeInteger) ||
startRow < 1 || count < 1 || width < 1) {
throw new Error('開始行・行数・列数を確認してください');
}
const rows = sheet.getRange(startRow, 1, count, width).getValues();
const result = [];
rows.forEach(function (values, index) {
const row = startRow + index;
if (sheet.isRowHiddenByFilter(row) || sheet.isRowHiddenByUser(row)) return;
result.push({row: row, values: values});
});
return result;
}
function previewVisibleRows() {
const sheet = SpreadsheetApp.getActiveSpreadsheet()
.getSheetByName('表示練習');
if (!sheet) throw new Error('表示練習シートがありません');
console.log(JSON.stringify(readVisibleRows(sheet, 2, 4, 2)));
}
期待する対象は2行目と5行目です。元の行番号を結果に残しているので、行を除いた後の配列の順番を、シートの行番号と取り違えずに済みます。範囲の行数と配列の添字についてはセルと範囲の基本も参考になります。
全行を表示した場合と比べる
まず通常フィルタを解除し、手動非表示も戻して、4件が返ることを確認します。次にそれぞれの非表示を設定し直し、どの行が除かれたかを比べます。片方だけで試すと、もう片方を除外できていないことに気づきにくくなります。
このコードは指定した範囲をすべて読み取ってから、非表示行を結果から外します。権限のないデータの取得を防ぐための処理ではありません。そもそも読み取ってはいけない情報は、共有範囲や取得元から分ける必要があります。
フィルタ表示を使っている表では、この例の結果と画面が一致しない場合があります。利用者ごとの表示状態を集計条件にしたいなら、検索条件を入力欄などへ明示的に渡す設計を検討します。表示状態の取得だけを継ぎ足して解決しようとしないほうが、対象を説明しやすくなります。
大きな表で使う前の確認
行ごとの非表示判定にはサービス呼び出しが必要です。全列・全行を指定せず、対象行と必要な列に絞って試してください。処理中に別の人がフィルタを変える場合もあるため、結果は取得時点の条件によるものとして記録します。
ローカルでは、代用シートの通常フィルタ行と手動非表示行をそれぞれ除くこと、全件表示、全件非表示、引数不備を確認しています。実際のフィルタ表示やGoogle上の実行時間は未確認です。共有先の判断はGASの共有範囲と権限も合わせて確認してください。
