简体   繁体   English

使用 Google Doc Apps 脚本缓存选定的文本元素

[英]Caching Selected Text Element with Google Doc Apps Script

Update: This is a better way of asking the following question.更新:这是提出以下问题的更好方法。

Is there an Id like attribute for an Element in a Document which I can use to reach that element at a later time. DocumentElement是否有类似Id属性,我可以稍后使用它来访问该元素。 Let's say I inserted a paragraph to a document as follows:假设我在文档中插入了一个段落,如下所示:

var myParagraph = 'This should be highlighted when user clicks a button';
body.insertParagraph(0, myParagraph);

Then the user inserts another one at the beginning manually (ie by typing or pasting).然后用户手动(即通过键入或粘贴)在开头插入另一个。 Now the childIndex of my paragraph changes to 1 from 0 .现在我段落的childIndex0变为1 I want to reach that paragraph at a later time and highlight it.我想稍后到达该段落并突出显示它。 But because of the insertion, the childIndex is not valid anymore.但是由于插入, childIndex不再有效。 There is no Id like attribute for Element interface or any type implementing that. Element接口或实现该接口的任何类型都没有类似Id属性。 CahceService and PropertiesService only accepts String data, so I can't store myParagraph as an Object . CahceServicePropertiesService只接受String数据,所以我不能将myParagraph存储为Object

Do you guys have any idea to achieve what I want?你们有什么想法来实现我想要的吗?

Thanks,谢谢,

Old version of the same question (Optional Read):同一问题的旧版本(可选阅读):

Imagine that user selects a word and presses the highlight button of my add-on.想象一下,用户选择一个单词并按下我的附加组件的突出显示按钮 Then she does the same thing for several more words.然后她又做了几个同样的事情。 Then she edits the document in a way that the start end end indexes of those highlighted words change.然后,她以更改这些突出显示单词的开始结束索引的方式编辑文档。

At this point she presses the remove highlighting button .此时,她按下了删除突出显示按钮 My add-on should disable highlighting on all previously selected words.我的附加组件应该禁用对所有先前选择的单词的突出显示。 The problem is that I don't want to scan the entire document and find any highlighted text.问题是我不想扫描整个文档并找到任何突出显示的文本。 I just want direct access to those that previously selected.我只想直接访问以前选择的那些。

Is there a way to do that?有没有办法做到这一点? I tried caching selected elements.我尝试缓存选定的元素。 But when I get them back from the cache, I get TypeError: Cannot find function insertText in object Text.但是当我从缓存中取回它们时,我得到TypeError: Cannot find function insertText in object Text. error.错误。 It seems like the type of the object or something changes in between cache.put() and cache.get() .好像对象什么的变化之间的类型cache.put()cache.get()

var elements = selection.getSelectedElements();
    for (var i = 0; i < elements.length; ++i) {
      if (elements[i].isPartial()) {
        Logger.log('partial');
        var element = elements[i].getElement().asText();

        var cache = CacheService.getDocumentCache();
        cache.put('element', element);  


        var startIndex = elements[i].getStartOffset();
        var endIndex = elements[i].getEndOffsetInclusive();
     }
    // ...
   }

When I get back the element I get TypeError: Cannot find function insertText in object Text.当我取回元素时,我收到TypeError: Cannot find function insertText in object Text. error.错误。

 var cache = CacheService.getDocumentCache();
 cache.get('text').insertText(0, ':)');  

I hope I can clearly explained what I want to achieve.我希望我能清楚地解释我想要实现的目标。

One direct way is to add a bookmark , which is not dependent on subsequent document changes.一种直接的方法是添加书签,它不依赖于随后的文档更改。 It has a disadvantage: a bookmark is visible for everyone...它有一个缺点:每个人都可以看到书签......

More interesting way is to add a named range with a unique name.更有趣的方法是添加一个具有唯一名称的命名范围 Sample code is below:示例代码如下:

function setNamedParagraph() {
  var doc = DocumentApp.getActiveDocument();
  // Suppose you want to remember namely the third paragraph (currently)
  var par = doc.getBody().getParagraphs()[2];
  Logger.log(par.getText());
  var rng = doc.newRange().addElement(par);
  doc.addNamedRange("My Unique Paragraph", rng);
}


function getParagraphByName() {
  var doc = DocumentApp.getActiveDocument();
  var rng = doc.getNamedRanges("My Unique Paragraph")[0];
  if (rng) {
    var par = rng.getRange().getRangeElements()[0].getElement().asParagraph();
    Logger.log(par.getText());
  } else {
    Logger.log("Deleted!");
  }
}

The first function "marks" the third paragraph as named range.第一个函数将第三段“标记”为命名范围。 The second one takes this paragraph by the range name despite subsequent document changes.尽管随后的文档发生了更改,但第二个仍按范围名称使用此段落。 Really here we need to consider the exception, when our "unique paragraph" was deleted.真的在这里我们需要考虑异常,当我们的“唯一段落”被删除时。

Not sure if cache is the best approach.不确定缓存是否是最好的方法。 Cache is volatile, so it might happen that the cached value doesn't exist anymore.缓存是不稳定的,因此可能会发生缓存值不再存在的情况。 Probably PropertiesService is a better choice.也许PropertiesService是更好的选择。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM