gpt4 book ai didi

google-apps-script - 通过 Workspace 附加组件更改可见性设置后更新 Google 日历 UI

转载 作者:行者123 更新时间:2023-12-05 03:45:24 25 4
gpt4 key购买 nike

我有一个非常基本的 Google Workspace Add-on使用 CalendarApp class使用 setSelected() 方法在按下按钮时切换日历事件的可见性

可见性切换有效,但更改仅在刷新页面时反射(reflect)在 UI 中。在 UI 中手动切换复选框会立即反射(reflect)更改,而无需刷新页面。

有没有一种方法可以通过我的 Workspace 插件复制这种即时更新行为?

一个mwe在下面。

function onDefaultHomePageOpen() {

// create button
var action = CardService.newAction().setFunctionName('toggleCalVis')
var button = CardService.newTextButton()
.setText("TOGGLE CAL VIS")
.setOnClickAction(action)
.setTextButtonStyle(CardService.TextButtonStyle.FILLED)
var buttonSet = CardService.newButtonSet().addButton(button)

// create CardSection
var section = CardService.newCardSection()
.addWidget(buttonSet)

// create card
var card = CardService.newCardBuilder().addSection(section)

// call CardBuilder.call() and return card
return card.build()

}

function toggleCalVis() {
// fetch calendar with UI name "foo"
var calendarName = "foo"
var calendarsByName = CalendarApp.getCalendarsByName(calendarName)
var namedCalendar = calendarsByName[0]

// Toggle calendar visabilty in the UI
if (namedCalendar.isSelected()) {
namedCalendar.setSelected(false)
}
else {
namedCalendar.setSelected(true)
}
}

最佳答案

简而言之:创建一个 chrome 扩展

(2021-sep-2)原因:setSelected() 方法更改服务器上的数据。要应用它的效果,您需要刷新页面。但 Google Workspace Extension“出于安全原因”不允许 GAS 这样做。但是,在 Chrome 扩展中,您可以通过普通 JS 取消选中可见性复选框。 (左侧列表的类名已编码,但对我来说是稳定的。)我有一些用于 Chrome 扩展的代码来选择节点,尽管我没有解决(见最后一部分)。

(2021-jul-25)更坏的情况:getAllCalendars() 不会选择默认日历。我只是尝试了与您提到的相同的事情,结果更糟。我想隐藏所有日历,而且我仍然非常确定代码是正确的,因为我可以在控制台中看到日历名称。

const allCals = CalendarApp.getAllCalendars()
allCals.forEach(cal => {console.log(`unselected ${cal.setSelected(false).getName()}`)})

但是主日历、提醒日历、任务日历都没有在控制台中。

google apps script dev 应该自问:人们为什么使用 Calendar.setSelected()我们不想在下次运行时隐藏日历。

the official document , 这两种行为都没有被提及。

TL;DR部分(我不使用GAS的原因)

GAS(google-apps-script) 的功能较少。据我所知,谷歌正试图建立自己的生态系统,但 GAS 中可实现的一切也可通过 javascript 获得。我什至可以使用 typescript 并通过创建扩展来做任何我想做的事。

GAS 不容易学习。学习也很痛苦,我花了4个小时搭建了第一张样卡,9个小时后我就可以和打开的事件正确交互了。文档远未完成。

GAS 支持不佳。 native 基于 Web 的代码编辑器 ( https://script.google.com/ ) 不是为编写真正的应用程序而构建的,它在新界面中失去了版本控制自由。并且不支持跨文件搜索。而不是 import,代码在列表中从上到下运行,您需要自己找到它。 (传递没有扩展,没有更漂亮,我可以忍受这些)与其他在线 JS 代码编辑器(如 codepen/code sandbox 等)相比,它的功能较少。此外,VSCode现在也有在线版本(github codespaces)。

我希望我在 GAS 的 13 个小时没有完全浪费。至少,阅读本文的人可以避免遭受同样痛苦的考验。

这是禁用 Chrome 中所有检查的代码( typescript )。TRACKER_CAL_ID_ENCODED 是我不想取消选中的日历 ID。由于不是本题的主要部分,所以没有很仔细的评论。

(行更新:2022 年 1 月 31 日)意识到 mutationsList.length >= 3 不准确,我看不到 mutationsList.length 是如何工作的。

扩展名:


getSelectCalendarNode()
.then(unSelectCalendars)
function getSelectCalendarNode() {
return new Promise((resolve) => {
document.onreadystatechange = function () {
if (document.readyState == "complete") {
const leftSidebarNode = document.querySelector(
"div.QQYuzf[jsname=QA0Szd]"
)!;
new MutationObserver((mutationsList, observer) => {
for (const mutation of mutationsList) {
if (mutation.target) {
let _selectCalendarNode = document.querySelector("#dws12b.R16x0");
// customized calendars will start loading on 3th+ step, hence 3, but when will they stop loading? I didn't work this out
if (mutationsList.length >= 3) {
// The current best workaround I saw is setTimeout after loading event... There's no event of loading complete.
setTimeout(() => {
observer.disconnect();
resolve(_selectCalendarNode);
}, 1000);
}
}
}
}).observe(leftSidebarNode, { childList: true, subtree: true });
}
};
});
}

function unSelectCalendars(selectCalendarNode: unknown) {
const selcar = selectCalendarNode as HTMLDivElement;
const calwrappers = selcar.firstChild!.childNodes; // .XXcuqd
for (const calrow of calwrappers) {
const calLabel = calrow.firstChild!.firstChild as HTMLLabelElement;

const calSelectWrap = calLabel.firstChild!;
const calSelcted =
(calSelectWrap.firstChild!.firstChild! as HTMLDivElement).getAttribute(
"aria-checked"
) == "true"
? true
: false;
// const calNameSpan = calSelectWrap.nextSibling!
// .firstChild! as HTMLSpanElement;
// const calName = calNameSpan.innerText;
const encodedCalID = calLabel.getAttribute("data-id")!; // const decodedCalID = atob(encodedCalID);
if ((encodedCalID === TRACKER_CAL_ID_ENCODED) !== calSelcted) {
//XOR
calLabel.click();
}
}
console.log(selectCalendarNode);
return;
}

关于google-apps-script - 通过 Workspace 附加组件更改可见性设置后更新 Google 日历 UI,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/65854813/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com