D22 - 如何用 Apps Script 自动化地创造与客制 Google Slides?(三)一次看完所有档案的预览

今天的目标:

当要整理 Google Drive 时,会发现好多的档案、文件不确定哪个要怎麽做。一个个开好麻烦,如果可以一次开完知道里面有什麽有多好。而今天就算是要帮大家做好「预览整理」,在 Google Slides 上列出档案的预览图、档名与连结。

预计今天的结果是长这样——

而对应的关键问题——

  1. 如何在 Google Slides 上列出指定资料夹中档案的「档名」与「预览图」?

好,那就让我们开始吧!

Q1. 如何在 Google Slides 上列出指定资料夹中档案的「档名」与「预览图」?

让我们借用一下 D15 生出的案例页面。当我们在整理档案时,常常会有这样的画面——一个个点开,慢慢找、慢慢整理。

但通常这样会花不少时间。所以今天我们会带大家来看看怎麽加速这流程。

输入

  • 目标资料夹的 ID:当然可以选择从根目录开始,但我们这边先带来比较常用的「指定资料夹」
  • 指定的 Google Slide:我们这次选择「绑定 Google Slide」来进行(参阅 Step 1)

输出

  • 一页页附有「档案名称」、「档案连结」与「档案预览图的」Slides,资料夹中有多少档案就生出多少张对应的 Slide。

预计会变成这样一张张的档案 Slide。

Step 1 从 Google Slides 进入 GAS 并设定指定资料夹 ID

那这次我们用 Google Slides 进入 GAS,借用一下 D20 的影片。

一样第一次按下 GAS 中的「执行」会有「存取验证」需要大家按一下。这边仍是借用一下 D2 的影片。

那接着,我们来抓出 Google Drive 的 ID。一样复习一下,每一个 Google 产品都有特定的 ID 如下图。

可以用我们下列的方式简单取得,如果想复习完整内容,在 D9: 如何用 Google Apps Script 自动化对 Google Drive 的操作?(一)列出所有档案 ID 与相关资讯 有完整的介绍可以参考。

这边我们就如法炮制将要更动的 Google Drive ID 抓入。

var target_folder_ID = "your_drive_id_here"

接着,就是如何读取里面的档案了。

Step 2 取得资料夹中的档案

接着要列出里面全部的档案们,在 D9 - (一)列出所有档案 ID 与相关资讯 我们有完整的文章,这边一样让大家迅速复习一下。

function showAllFiles(){
  let folder = DriveApp.getFolderById(target_folder_ID);
  let files = folder.getFiles();
  while (files.hasNext()) {
  	let file = files.next();
	Logger.log(file.getName())
  }
}

再搭配 D15 的资料夹作为 Target Folder,跑起来会长这样——

好,那接着就是要抓出档案的「预览图」了

Step 3 用 getThumbnail() 抓出档案的预览图并用insertImage放入 Slide 中

要抓出预览图,要使用 getThumbnail() 这项 DriveApp 的 API,这边做的事很简单:

  1. 抓出档案後,在回圈中用 let preview = file.getThumbnail() 抓出预览图的档案
  2. 把预览图的档案用 new_slide.insertImage(preview) 放入 Slide
  3. 把预览图用一个 border 设定黑色外框(hex color code: '#000000')让视觉上更容易看见
function showPreviewOnSlides(){
  let folder = DriveApp.getFolderById(target_folder_ID);
  let slide = SlidesApp.getActivePresentation();
  let files = folder.getFiles();
  while (files.hasNext()) {
    let file = files.next();
    let preview = file.getThumbnail();
    let new_slide = slide.appendSlide();
    let image = new_slide.insertImage(preview);
	image.getBorder().getLineFill().setSolidFill('#000000')
  };  
};

跑起来长这样——

这边要补充一下,我们从 getThumbnail() 抓下来的档案格式是 BLOB(Binary Large Object) 是一种档案格式,通常抓下来 png、 pdf 或影片都有机会。在 GAS 的 Blob 中,大多都是 pdf,但也可能是 GIF, JPEG 或 PNG 等档案。而我们这边就是用其抓影像的 PNG 档案。

好,接着我们要插入「档案名称」和「档案连结」,这边就有更多有趣之处了。

Step 4 插入文字方块并「乔位置」

如果我们在原本的程序码,再插入一个文字方块会发生什麽事?

new_slide.insertTextBox("档案名称")

会长这样——

会发现——

  1. 我们生成的物件是 First-In, Last-Out,後创造的会在越上层,以上面的案例为例,比较晚创造的「档案名称」会在「预览影像」之前*
  2. 文字方块会在预览图之下,且都是以左上角作为基准点。

*(在这边用 FILO 是方便记忆,强调可以第一个从 Slide 上拿到的意思,实际上是资料型态 Stack 的特性)

换句话说,如果没有特别设定,我们生成的物件会全部挤在左上角。那到底要设定什麽呢?要设定「放置位置」。在这边,我们使用的 API 是 slide 中的 insertTextBox(text, left, top, width, height)。用法如下——

new_slide.insertTextBox("档案名称", 10, 20, 30, 40)

其中四个参数分别意思是——

  1. left 距离投影片最左边多少 pt?上面程序码的案例是 10pt
  2. top 距离投影片最上边多少 pt?上面程序码的案例是 20pt
  3. width 这个物件要多宽?上面程序码的案例是 30pt
  4. height 这个物件要多高?上面程序码的案例是 40pt

这四个数据要全有全无,换句话说要马就一次包含长宽都设定,要马就不要设定,目前的 API 不许我们胡来。这边要特别说一下一个单位叫 pt,比较常在设计物件时会用到这单位。而今天我们主要要知道它怎麽换算成公分即可,以下是一份简单的换算图。

所以实际上我们要怎麽用呢?我们可以透过点取「随意 Page Element 物件」的「格式选项」,就可以看到一个「位置」,来看其中的数值,抓出你大概想放哪。

影片中的范例,则是 X 要为位於 11.29 cm。所以代表我们的 left 要设定为 11.29 * 28.3 大概是 320,这边我就抓 300。宽与高也是如法炮制,这边就直接设定为——

new_slide.insertTextBox("档案名称", 300, 0, 300, 300)

那再加上要得到的文字与资料夹位置,完整的程序码如下——

function searchAllPreviewInTheFolder(){
  let folder = DriveApp.getFolderById(target_folder);
  let slide = SlidesApp.getActivePresentation();
  let files = folder.getFiles();
  let folder_name = folder.getName();
  while (files.hasNext()) {
    let file = files.next();
    let preview = file.getThumbnail();
    let new_slide = slide.appendSlide();
    let file_name = file.getName();
    let image = new_slide.insertImage(preview);
    image.getBorder().getLineFill().setSolidFill('#000000')
    new_slide.insertTextBox(folder_name+'\n'+file_name + '\n\n' + file.getUrl(), 300, 0, 400, 400);
  };  
}

跑起来长这样——

好,那今天就到这边。今天我们主要学了:

  1. 如何读取 Google Drive 中档案的预览
  2. 如何将图片插入到 Google Slides 上
  3. 如何将文字方块插入到 Google Slides 上并调整位置

今天进入了 Slide 的第三天,希望对大家有所帮助。如果还有问题,透过留言之外,也可以到 Facebook Group,想开很久这次铁人赛才真的开起来,欢迎来当 Founding Member。如果不想错过可以订阅按赞小铃铛(?),也欢迎留言跟我说你还想知道什麽做法/主题。我们明天见。


<<:  有感表达,需要多P

>>:  TypeScript 能手养成之旅 Day 6 物件型别-基础物件型别

【Day13】[资料结构]-二元树Binary Tree

二元树(Binary Tree)是最广泛被使用的树状资料结构,简单来说即为每个节点最多只能有两个子节...

全端入门Day19_前端程序撰写之JavaScript

说完了HTML跟CSS了,就剩下JavaScript了! JavaScript入门 要让网页能够有动...

Logo 语言和你 SAY HELLO!!

第二十六天 各位点进来的朋友,你们好阿 小的不才只能做这个系列的文章,但还是希望分享给点进来的朋友,...

[13th][Day7] func -1

不定长度参数 Variadic Functions Golang 中,有些函式的参数长度是不固定的,...

Day 30. 要怎麽动

啊哈,所以理论上我的第一个菜单做好了,但是因为我做的是VR菜单,所以移动手臂要靠Tracked Po...