Как искать и заменять горизонтальное правило и переносы строк - PullRequest
0 голосов
/ 18 февраля 2019

Мне нужно автоматически удалить все горизонтальные правила, которые окружены 6 разрывами строки (3 до и 3 после) в документе Google.

Этот фрагмент кода, кажется, помещает в журналы правильные разрывы строк, которые я хочуудалить (это первый шаг):

function myFunction() {
var doc = DocumentApp.getActiveDocument();
var body = doc.getBody().getText();
var pattern = /\s\s\s\s/g; 
  while (m=pattern.exec(body)) { Logger.log(m[0]); }
}

У меня два вопроса:

  • Какой инструмент я могу использовать для удаления этих разрывов строк (я пока не понимаю подтиповиспользования replace или replaceText, все мои попытки с ними потерпели неудачу)?

  • Как я могу добавить в свой шаблон var (шаблон, который нужно удалить) горизонтальное правило?Я попытался / \ s \ s \ s \ sHor HorizontalRule \ s \ s \ s \ s / g, но, конечно, это не сработало.

1 Ответ

0 голосов
/ 18 февраля 2019

Горизонтальное правило - это элемент внутри абзаца (или иногда внутри элемента списка).Поскольку это не текст, его нельзя найти или заменить с помощью регулярного выражения.Мы должны найти объекты, которые специально расположены в теле документа, и удалить их, если найдены.

Рассмотрим следующий пример кода:

function deleteHR() {
  var body = DocumentApp.getActiveDocument().getBody();
  var hr = null, hrArray = [], countDeleted = 0;

  // Collect all horizontal rules in the Document
  while (true) {
    hr = body.findElement(DocumentApp.ElementType.HORIZONTAL_RULE, hr);
    if (hr == null) break;
    hrArray.push(hr);
  }

  hrArray.forEach(function(hr) {
    var p = hr.getElement().getParent();
    // Get empty paragraphs as siblings (if any)
    var prevSiblings = getSiblings(p, 3, true),
        nextSiblings = getSiblings(p, 3, false);
    // Define a short function for batch deleting items
    function remove(e) {
      e.removeFromParent();
    }
    // If empty paragraphs exist (3 before and 3 after)
    if (prevSiblings.length == 3 && nextSiblings.length == 3) {
      // then delete them as well as the rule itself
      hr.getElement().removeFromParent();
      prevSiblings.forEach(remove);
      nextSiblings.forEach(remove);
      countDeleted++;
    }
  });
  // Optional report
  Logger.log(countDeleted + ' rules deleted');
}


// Recursive search for empty paragraphs as siblings
function getSiblings(p, n, isPrevious) {
  if (n == 0) return [];
  if (isPrevious) {
    p = p.getPreviousSibling();
  } else {
    p = p.getNextSibling();
  }
  if (p == null) return [];
  if (p.getType() != DocumentApp.ElementType.PARAGRAPH) return [];
  if (p.asParagraph().getText().length > 0) return [];
  var siblings = getSiblings(p, n - 1, isPrevious);
  siblings.push(p);
  return siblings;
}

Основная функция deleteHR() выполняет всю работу,Однако представляется полезным использовать другую отдельную функцию getSiblings() для рекурсивного поиска пустых абзацев.Может быть, этот способ не единственный, но он работает.

...