Skip to content

Commit 1e4d064

Browse files
committed
Add templates
2 parents df6ef41 + 6e9df3e commit 1e4d064

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+3559
-0
lines changed

templates/README.md

+73
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
Templates for Google Apps Script
2+
================================
3+
4+
Templates that provide an initial, working framework for Apps Script
5+
projects.
6+
7+
Introduction
8+
------------
9+
10+
Google Apps Script allows developers to extend and maniplate Google
11+
Docs, Sheets and Forms. For those just starting with Apps Script, it
12+
can be useful to have a template to work from -- a framework that
13+
developers can learn from and modify to suit their needs.
14+
15+
This collection hosts the following templates:
16+
17+
* Custom Functions for Sheets
18+
* Google Docs Add-on
19+
* Google Sheets Add-on
20+
* Google Forms Add-on
21+
* Script as Web App
22+
23+
24+
Within these templates the following Google Apps Script concepts are
25+
illustrated:
26+
27+
* [Dialogs and Sidebars](https://developers.google.com/apps-script/guides/dialogs)
28+
* Using [Templated HTML](https://developers.google.com/apps-script/guides/html/templates)
29+
* Responding to HTTP GET requests with doGet(e)
30+
* Using IFRAME sandbox mode
31+
32+
33+
Getting Started
34+
---------------
35+
36+
Templates can be accessed from the Apps Script editor Welcome Screen
37+
(which is shown when the editor is first opened or by clicking the
38+
"Help > Welcome screen" menu item. Selecting a template from the
39+
Welcome Screen will create a new project pre-populated with the code
40+
you need to get started.
41+
42+
Alternatively, the code provided in this repository can be manually copied
43+
into the Apps Script editor. Note that certain templates need to be used
44+
in a container-bound script (that is, the template is meant to be in a
45+
script attached to a Doc, Sheet or Form, rather than a standalone script).
46+
47+
48+
49+
Learn more
50+
----------
51+
52+
To continue learning about how to extend Google Docs, Sheets and Forms
53+
with Apps Script, take a look at the following resources:
54+
55+
* [Overview of Apps Script](https://developers.google.com/apps-script/overview)
56+
* [Guide to Add-ons](https://developers.google.com/apps-script/add-ons/)
57+
58+
59+
Support
60+
-------
61+
If you've found an error in this sample, please file an issue:
62+
https://github.com/googlesamples/apps-script-templates/issues
63+
64+
Patches are encouraged, and may be submitted by forking this project and
65+
submitting a pull request through GitHub.
66+
67+
68+
General questions about Apps Script can be asked on
69+
StackOverflow: [google-apps-script on StackOverflow](http://stackoverflow.com/questions/tagged/google-apps-script)
70+
71+
72+
General Apps Script bug reports or feature requests should be directed to the
73+
Apps Script Issue Tracker: [google-apps-script-issues](https://code.google.com/p/google-apps-script-issues/issues/list)

templates/custom-functions/Code.gs

+142
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,142 @@
1+
/**
2+
* Copyright 2014 Google Inc. All Rights Reserved.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
/**
18+
* @OnlyCurrentDoc Limits the script to only accessing the current spreadsheet.
19+
*/
20+
21+
/**
22+
* A function that takes a single input value and returns a single value.
23+
* Returns a simple concatenation of Strings.
24+
*
25+
* @param {String} name A name to greet.
26+
* @return {String} A greeting.
27+
* @customfunction
28+
*/
29+
function SAY_HELLO(name) {
30+
return 'Hello ' + name;
31+
}
32+
33+
/**
34+
* A function that takes an input cell or range of cells and returns a cell or
35+
* range of cells.
36+
* Returns a range with all the input values incremented by one.
37+
*
38+
* @param {Array} input The range of numbers to increment.
39+
* @return {Array} The incremented values.
40+
* @customfunction
41+
*/
42+
function INCREMENT(input) {
43+
if (input instanceof Array) {
44+
// Recurse to process an array.
45+
return input.map(INCREMENT);
46+
} else if (!(typeof input == 'number')) {
47+
throw 'Input contains a cell value that is not a number';
48+
}
49+
// Otherwise process as a single value.
50+
return input + 1;
51+
}
52+
53+
/**
54+
* A function that takes an range of values and returns a single value.
55+
* Returns the sum the corner values in the range; for a single cell,
56+
* this is equal to (4 * the cell value).
57+
*
58+
* @param {Array} input The Range of numbers to sum the corners of.
59+
* @return {Number} The calculated sum.
60+
* @customfunction
61+
*/
62+
function CORNER_SUM(input) {
63+
if (!(input instanceof Array)) {
64+
// Handle non-range inputs by putting them in an array.
65+
return CORNER_SUM([[input]]);
66+
}
67+
// Range processing here.
68+
var maxRowIndex = input.length - 1;
69+
var maxColIndex = input[0].length - 1;
70+
return input[0][0] + input[0][maxColIndex] +
71+
input[maxRowIndex][0] + input[maxRowIndex][maxColIndex];
72+
}
73+
74+
/**
75+
* A function that takes a single value and returns a range of values.
76+
* Returns a range consisting of the first 10 powers and roots of that
77+
* number (with column headers).
78+
*
79+
* @param {Number} input The number to calculate from.
80+
* @return {Array} The first ten powers and roots of that number,
81+
* with associated labels.
82+
* @customfunction
83+
*/
84+
function POWERS_AND_ROOTS(input) {
85+
if (input instanceof Array) {
86+
throw 'Invalid: Range input not permitted';
87+
}
88+
// Value processing and range generation here.
89+
var headers = ['x', input + '^x', input + '^(1/x)'];
90+
var result = [headers];
91+
for (var i = 1; i <= 10; i++) {
92+
result.push([i, Math.pow(input, i), Math.pow(input, 1/i)]);
93+
}
94+
return result;
95+
}
96+
97+
/**
98+
* A function that takes a single input cell that is Date- or Date time-formatted.
99+
* Returns the day of the year represented by the provided date.
100+
*
101+
* @param {Date} date A Date to examine.
102+
* @return {Number} The day of year for that date.
103+
* @customfunction
104+
*/
105+
function GET_DAY_OF_YEAR(date) {
106+
if (!(date instanceof Date)) {
107+
throw 'Invalid: Date input required';
108+
}
109+
// Date processing here.
110+
var firstOfYear = new Date(date.getFullYear(), 0, 0);
111+
var diff = date - firstOfYear;
112+
var oneDay = 1000 * 60 * 60 * 24;
113+
return Math.floor(diff / oneDay);
114+
}
115+
116+
/**
117+
* A function that takes a single input cell that is Duration-formatted.
118+
* Returns the number of seconds measured by that duration.
119+
*
120+
* @param {Date} duration A duration to convert.
121+
* @return {Number} Number of seconds in that duration.
122+
* @customfunction
123+
*/
124+
function CONVERT_DURATION_TO_SECONDS(duration) {
125+
if (!(duration instanceof Date)) {
126+
throw 'Invalid: Duration input required';
127+
}
128+
129+
// Getting elapsed times from duration-formatted cells in Sheets requires
130+
// subtracting the reference date from the cell value (while correcting for
131+
// timezones).
132+
var spreadsheetTimezone =
133+
SpreadsheetApp.getActiveSpreadsheet().getSpreadsheetTimeZone();
134+
var dateString = Utilities.formatDate(duration, spreadsheetTimezone,
135+
'EEE, d MMM yyyy HH:mm:ss');
136+
var date = new Date(dateString);
137+
var epoch = new Date('Dec 30, 1899 00:00:00');
138+
var durationInMilliseconds = date.getTime() - epoch.getTime();
139+
140+
// Duration processing here.
141+
return Math.round(durationInMilliseconds / 1000);
142+
}

templates/custom-functions/README.md

+23
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
Template: Custom Functions for Sheets
2+
=====================================
3+
4+
This template provides a framework for creating custom functions
5+
in Google Sheets. It shows the structure needed to define a
6+
custom function and its autocomplete documentation, and provides
7+
a few examples.
8+
9+
The examples provided here demonstrate:
10+
11+
* How to create custom functions that accept arguments of different types
12+
* How to document a custom function to generate correct autocomplete
13+
information in Sheets
14+
15+
Note that this template must be added to a container-bound script
16+
attached to a Google Sheet in order to function.
17+
18+
19+
For more information, see [Custom Functions in Google Sheets](https://developers.google.com/apps-script/guides/sheets/functions).
20+
21+
In addition, developers of Sheets custom functions should be aware of
22+
the [known issues specific to Google Sheets](https://developers.google.com/apps-script/migration/sheets).
23+

templates/docs-addon/Code.gs

+111
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
/**
2+
* Copyright 2014 Google Inc. All Rights Reserved.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
/**
18+
* @OnlyCurrentDoc Limits the script to only accessing the current document.
19+
*/
20+
21+
var DIALOG_TITLE = 'Example Dialog';
22+
var SIDEBAR_TITLE = 'Example Sidebar';
23+
24+
/**
25+
* Adds a custom menu with items to show the sidebar and dialog.
26+
*
27+
* @param {Object} e The event parameter for a simple onOpen trigger.
28+
*/
29+
function onOpen(e) {
30+
DocumentApp.getUi()
31+
.createAddonMenu()
32+
.addItem('Show sidebar', 'showSidebar')
33+
.addItem('Show dialog', 'showDialog')
34+
.addToUi();
35+
}
36+
37+
/**
38+
* Runs when the add-on is installed; calls onOpen() to ensure menu creation and
39+
* any other initializion work is done immediately.
40+
*
41+
* @param {Object} e The event parameter for a simple onInstall trigger.
42+
*/
43+
function onInstall(e) {
44+
onOpen(e);
45+
}
46+
47+
/**
48+
* Opens a sidebar. The sidebar structure is described in the Sidebar.html
49+
* project file.
50+
*/
51+
function showSidebar() {
52+
var ui = HtmlService.createTemplateFromFile('Sidebar')
53+
.evaluate()
54+
.setTitle(SIDEBAR_TITLE)
55+
.setSandboxMode(HtmlService.SandboxMode.IFRAME);
56+
DocumentApp.getUi().showSidebar(ui);
57+
}
58+
59+
/**
60+
* Opens a dialog. The dialog structure is described in the Dialog.html
61+
* project file.
62+
*/
63+
function showDialog() {
64+
var ui = HtmlService.createTemplateFromFile('Dialog')
65+
.evaluate()
66+
.setWidth(400)
67+
.setHeight(150)
68+
.setSandboxMode(HtmlService.SandboxMode.IFRAME);
69+
DocumentApp.getUi().showModalDialog(ui, DIALOG_TITLE);
70+
}
71+
72+
/**
73+
* Returns the existing footer text (if any).
74+
*
75+
* @return {String} existing document footer text (as a plain string).
76+
*/
77+
function getFooterText() {
78+
// Retrieve and return the information requested by the sidebar.
79+
return DocumentApp.getActiveDocument().getFooter().getText();
80+
}
81+
82+
/**
83+
* Replaces the current document footer with the given text.
84+
*
85+
* @param {String} footerText text collected from the client-side
86+
* sidebar.
87+
*/
88+
function setFooterText(footerText) {
89+
// Use data collected from sidebar to manipulate the document.
90+
DocumentApp.getActiveDocument().getFooter().setText(footerText);
91+
}
92+
93+
/**
94+
* Returns the document title.
95+
*
96+
* @return {String} the current document title.
97+
*/
98+
function getDocTitle() {
99+
// Retrieve and return the information requested by the dialog.
100+
return DocumentApp.getActiveDocument().getName();
101+
}
102+
103+
/**
104+
* Changes the document title.
105+
*
106+
* @param {String} title the new title to use for the document.
107+
*/
108+
function setDocTitle(title) {
109+
// Use data collected from dialog to manipulate the document.
110+
DocumentApp.getActiveDocument().setName(title);
111+
}

templates/docs-addon/Dialog.html

+43
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
<!--
2+
* Copyright 2014 Google Inc. All Rights Reserved.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
-->
16+
17+
<!DOCTYPE html>
18+
<html>
19+
<head>
20+
<base target="_top">
21+
<!-- Use a templated HTML printing scriptlet to import common stylesheet -->
22+
<?!= HtmlService.createHtmlOutputFromFile('Stylesheet').getContent(); ?>
23+
</head>
24+
<body>
25+
<!-- Below is the HTML code that defines the dialog element structure. -->
26+
<cursor></cursor><form id="title-form">
27+
<div class="block" id="dialog-elements">
28+
<label for="dialog-title">
29+
You can set the document title here:
30+
</label>
31+
<input class="width-100" id="dialog-title">
32+
</div>
33+
<div class="block" id="dialog-button-bar">
34+
<button type="submit" class="action" id="dialog-save-button">Save</button>
35+
<button id="dialog-cancel-button" onclick="google.script.host.close()">Cancel</button>
36+
</div>
37+
<div id="dialog-status"></div>
38+
</form>
39+
40+
<!-- Use a templated HTML printing scriptlet to import JavaScript -->
41+
<?!= HtmlService.createHtmlOutputFromFile('DialogJavaScript').getContent(); ?>
42+
</body>
43+
</html>

0 commit comments

Comments
 (0)