Skip to content
Canvas Quiz is a starter kit for developers to make custom, voice-enabled question-answer games for the Google Assistant.
JavaScript Other
Branch: master
Clone or download
Mike Lacher
Latest commit 05fa10f Oct 4, 2019
Type Name Latest commit message Commit time
Failed to load latest commit information.
client update debug helper content Oct 4, 2019
deploy initial commit Sep 23, 2019
.gitignore add .gitignore Oct 4, 2019 initial commit Sep 23, 2019
LICENSE.txt initial commit Sep 23, 2019 initial commit Sep 23, 2019 initial commit Sep 23, 2019
package-lock.json initial commit Sep 23, 2019
package.json initial commit Sep 23, 2019
setup.js initial commit Sep 23, 2019
webpack.config.js initial commit Sep 23, 2019

Canvas Quiz

Canvas Quiz is a starter kit for developers to make custom, voice-enabled question-answer games for the Google Assistant. It uses Interactive Canvas, so you can create your own custom graphics and animations. Just deploy the code, put your questions and answers in a Google Sheet, and you’ll have your own quiz up and running.

This is not an official Google product. It’s just an experiment designed to help developers get started building with Interactive Canvas. If you want to learn more about Interactive Canvas, check out the official docs.

Setting up

Prerequisites: Node.js and npm. A bit of familiarity with Actions on Google and Interactive Canvas is helpful.

  1. Make a copy of the example Google Sheet.
  2. Create a new Firebase project.
  3. Enable Blaze billing (necessary to use Sheets API and Dialogflow API).
  4. Create a new Dialogflow project. When it asks you for your Google Cloud Project, choose the Firebase project you just created.
  5. Install the Firebase command line tools.
  6. Run npm run setup from the root of this repo. You'll need the gcloud command line tools installed. (MacOS/Linux only)

If you ran the setup command successfully, you can skip all the steps below!

  1. Run npm run installall to install npm packages for the frontend and backend.
  2. In Google Cloud Console, create a service account. Name it whatever you want.
  3. For the service account’s role, choose Project > Owner.
  4. Click “CREATE KEY”. Choose JSON. Click CREATE. This will download a json file.
  5. Move the file into deploy/functions/modules/auth.
  6. Share the spreadsheet with the email address you just created (needs view access)
  7. In the Google Cloud APIs library, find the “Google Sheets API” and enable it.
  8. Also find the "Dialogflow API" and make sure its enabled.
  9. In the (Dialogflow Console) [] for your agent, click the gear icon in the upper left by your agent’s name. The click “Export and Import”.
  10. Click “RESTORE FROM ZIP”. Choose the file from the root of this repo. This will overwrite anything in this agent, and cannot be undone.
  11. Open deploy/functions/modules/config.js in an editor. Update these variables:
    • SERVICE_KEY should be the filename of the JSON key you downloaded.
    • CANVAS_URL should be your firebase hosting url + “/canvas”
    • AUDIO_URL should be where you want to store any sound effects (can use firebase hosting for this)
    • IMAGE_URL should be where you want to store any images (can use firebase hosting for this)
    • SHEET_ID should be the id of your Google Sheet. It's in the url:[ID_IS_HERE]/edit
  12. Open deploy/.firebaserc. Update $PROJECTID to your GCP project.

Building the frontend

npm run build will build the frontend into the deploy/public/canvas directory. npm run watch will watch for any changes and build automatically.

Deploying the frontend and backend

npm run deploy will deploy the frontend and backend to Firebase. It will also run a predeploy script that will parse the Google Sheet, update staticquiz.json, and update answer entities on Dialogflow.

Make sure to change your Dialogflow agent’s fulfillment URL to the URL of your cloud function.


Frontend The front end can be tested by running npm run frontend. The client/debug-helpers.js file exposes functions that simulate states sent from the backend, so you can see how the frontend looks and responds to backend changes by calling these functions from the console of your browser.

Backend The first time you want to run your action, go to your Dialogflow agent, and then click “See how it works in Google Assistant” in the right hand column. This will open the Actions on Google simulator.

In the Actions on Google console, go to Deploy > Additional Information. Set the category as “Games & Fun” and scroll down check the box labeled “Interactive Canvas”.

Styling the frontend

You can customize fonts, colors, spacing, and more in client/config.js. Make sure to build the frontend afterwards.

Working with the frontend

Frontend source files are in the client directory. They use LitElement to build HTML components.

Game.js is the primary controller that takes the state from the backend, sends data to components, and handles transitions.

Animations are handled using Greensock.

Working with the backend

Backend source files are in the deploy/functions directory. Index.js handles the main logic of the quiz.

Primary modules:

  • config.js: Holds important info like your project ID, url of the frontend, quiz settings, and spreadsheet settings.
  • DataManager.js: Handles reading the spreadsheet, putting answers into Dialogflow API, and making data available to the quiz at runtime.
  • History.js: Tracks what questions a user has seen and how many times they’ve gotten each question right and wrong. Persists across conversations. Used to prioritize questions the user hasn’t seen and questions the user has gotten wrong frequently.
  • Replier.js: Handles sending replies to the frontend. Detects device capabilities and adjusts for audio-only, screens without Interactive Canvas support, and screens with Interactive Canvas support. Generally better to use this than conv.ask().
    • You can chain spoken replies like this:
      conv.replier.addReply(“I want to say this!”);
      conv.replier.addReply(“And this!”);
      conv.replier.send(“One last thing”);
    • You can send state updates to the frontend like this: conv.replier.addCanvasUpdate({foo: “bar”});
    • You can access arbitrary rows in the spreadsheet like this: conv.replier.getMisc(‘value from id column’)
    • If a spreadsheet row selected with the conv.replier.getMisc function contains a value in the audio column, replier will look for the corresponding audio file in deploy/firebase/public/audio.


In the Actions on Google console, go to Deploy > Additional Information. Set the category as “Games & Fun” and scroll down check the box labeled “Interactive Canvas”.

Less-obvious voice commands

These aren’t directly exposed to the user but could be useful for navigation or testing. If you don’t want them, delete the intents from the Dialogflow agent and delete the corresponding intent-handlers in deploy/functions/index.js.

  • “Delete history” - This will clear everything in user storage, like what questions you’ve seen, your location, etc. If you start another conversation, it’ll be like your first time using the app.
  • “Go to question ___” - Jumps to a question number. Might mess up your progress, but useful for debugging content without having to reorder the spreadsheet. The number will be the row of the spreadsheet minus 2. So to go to the question on row 44 of the spreadsheet, say “go to question 42”
  • “Debug order linear” - If said on the homescreen, will force user to go through questions in linear order (useful for testing)
  • “Restart / start over” - Restarts the quiz
  • “What is this” - triggers an about page for the quiz
  • “Next question / last question” - Skips back and forth. Skipped questions are marked as wrong.
You can’t perform that action at this time.