Author: John Stewart (Page 1 of 30)

What I’m Reading: The Power

Over the last week, I read a novel called The Power by Naomi Alderman (link to a NY Times interview with Alderman). The general premise of the book is that women develop the power to harness electrical energy. This manifests in various ways like being able to shoot lightning from their fingertips, send blasts of electricity through various conductors, disrupt electronics, and manipulate the electrical systems in the human body.

Cover of the book, The Power, depicting a hand with electrical tendrils ringing the hand

The book talks both about empowerment of women and the fear that men feel as women wake up to this power. There’s fear of physical harm, fear of loss of structural (social, political, economic, militaristic, etc) power, fear about the reconceptualization of personal relationships, and just a general fear within daily life.

Alderman uses this sci-fi alternate history to demonstrate the real fear that women feel on a daily basis. I love how strange and fantastical she makes the very real issues of patriarchy and misogyny seem. The book depicts horrible acts of violence that made me squirm, but they feel warranted in that they are direct critiques of the violence inflicted daily upon women.

The story itself weaves together an ensemble cast. Alderman plays with the narrative structure, so that even though the reader feels like they’re accumulating the momentary insights and motivations of the various protagonists, they don’t really know what the end game is for anyone. Ultimately, Alderman is just using the characters to play with the religious and historical archetypes that serve as the foundation of our modern culture. The feeling of inevitability in watching these thin archetypes play to and with expectations is part of the point.

I really enjoyed the book and hope others will read it, so that we can revel in both the gory details and the grand vision that Alderman offers.

AirTable Review

I have been trying out different project management tools over the last few weeks. So far, I’ve used Notion, Trello, and AirTable and also looked at half a dozen others. I also tried a notebook and paper, but I definitely prefer the digital.

via GIPHY

My first goal is to try to find something that can help me keep track of the various projects that I’m working on. I have a habit of saying yes to literally everything anyone proposes, and then losing track of my commitments. So I need something that will tell me what projects I’m already working on, when they’re due, and some sense of how much bandwidth I have to spare.

The second goal is seeing if any of these tools also make sense for adoption by the Office of Digital Learning. We are in the process of hiring new IDs, a new instructional technologist, and a new video person. We’ve been using a combination of Trello and excel to track things for a while, but in an OLC Live conversation with Clark Shah-Nelson, I realized that we could probably do better.

AirTable

This week I’ve been trying out AirTable at the recommendation of Angela Gunder. As the name suggests, AirTable is a lightweight tool for building tables. My guess is that many people are put off by tables due to repressed memories of having to look at MS Access in a poorly thought out computer class as a kid. I, however, love tables. Working with websites as much as I do, everything now looks like a table. Each webpage is a table. A website is just a table of webpages. And I manage big tables of all the OU Create websites. I’ve organized my research notes into online tables and I’ve built tables for history undergrads to do the same.

For a couple of weeks, I was using Notion.so, and I like how it lays everything out in linked webpages with embedded spreadsheets. Any record that you put into the system can become it’s own little wiki page with embeddable images, spreadsheets, and links to other pages.

However, I eventually decided to abandon Notion, because it was not enough like a table. It was difficult to create two-way links between records for quick movement around the note system. Updates on one page rarely carried over to related pages, so you had to enter the same information on every relevant spreadsheet, rather than just updating a single table.

I spent about two days back in Trello, before remembering that Trello doesn’t do anything other than Kanban charts. There’s no interrelation of information across different charts, and once you’ve completed an item, you just archive or delete it or live it sitting taking up space.

So what I wanted, was something that combined Trello’s Kanban to-do charts with a broader table layout with multiple ways to drill down into the data. AirTable has Kanban charts taking care of my need for visual to-do lists:A screen shot AirTable's Kanban chart viewWhen you update the status (or any other information) of a card in the chart, that update carries throughout the rest of the system. You can view all of your items in a set of spreadsheets that can be tied together with relational tables:

Screenshot of AirTable's table view

In my “To-Do List” database, I have created a table of tasks. Each task can be tied to a broader project, and I can see information about those projects in their own spreadsheet. I also made a spreadsheet for ‘Ongoing’ tasks that I do daily or weekly or monthly, the types of things that can’t just be checked off and removed.

My table also includes a spreadsheet for readings, and these can in-turn be linked back to tasks or projects.

Conclusions

For my own usage, AirTable is brilliant. I’m happy to put in the time and energy to build a table to keep track of all of my stuff. The sheets are interrelated, so my updates propagate through all of the various views and sheets easily. I can sort by deadline to see what’s urgent or by impact to see what the big, important projects are. When a task is done, I can change it’s setting and then hide completed tasks. This is similar to the archival feature in Trello, but it’s much easier to unhide all of my completed AirTable tasks and analyze the amount of work I did in a given week or on a given project.

For my group’s usage, I think AirTable has a lot of power but also several drawbacks. We could easily set up a spreadsheet of all of the programs around campus that we are working with and list out points of contact and notes. We could then create a related spreadsheet of the courses we are developing and have developed. A task list might then list out all of the pieces of content and meetings and design work we are doing for the various courses. We could even set up a separate media table of all of the video and image assets we have acquired and created for the courses. I think in terms of keeping track of all of the stuff that the Office of Digital Learning is working on, this would be a really great tool.

However, my usage so far has been free, but I think we would need to pay about $5 per user (about 15 of us) per month. That’s not a ton of money, but it’s a new cost as compared to our current free usage of Trello or Basecamp which we already have access to.

Also, I felt very comfortable playing with tables, but I anticipate most people will want to stay on their views of the main tables, especially as the database gets much bigger and less comprehensible. It’s easy for me to modify my tables to my exact needs, but it will necessarily be harder to design a set of tables that fit everyone’s needs. My guess is that we will end up with a few tables that are only used by one person, so that they can organize their information as they want. As long as those tables are related back to the main tables, that’s not too big of a problem, but the system will grow ever larger and more complicated.

But, those are all tasks to worry about next week. For now, I will change the status of “Write-up on AirTable” to done, and call it a day.

Twine Game Data to Google Sheets via Javascript version 2

Using Twine, a free, open-source, text-based game software, you can build choose your own adventure games that explore the untaken paths in literaturepromote empathy through simulated experiences, and provide role-playing adventures in historical scenarios. Twine games are often used in the classroom, because you can quickly build an educational experience about whatever subject you choose. They are also heavily used in the interactive fiction world as a medium for short stories and novels.

I wrote the first version of this post back in October, while Keegan and I were the XP Twine workshop. In this post, I explained how to capture game data from Twine and push it into a Google Sheet. However, in discussing how to implement the original post with @hpkomic, I found out that the javascript code that I wrote back then was invalid because of something called CORS. There are many protections on the web to prevent people trying to inject malicious material into sites. CORS protections kick in when someone is trying to make changes on one domain from another domain, or “cross-origin.” My old code was not CORS compliant, so it didn’t work properly.

The first section of the code as the same as it was back in October. It’s the second section, “Twine Game Code,” that’s new.

Twine games take the form of HTML files with embedded CSS and JS. In my latest round of tinkering, I figured out how to use javascript within a Twine game to send an HTTP post message to pass game-play data to a Google Spreadsheet, thereby creating a database that records each game-play.

Google Sheet/Apps Script Code

In order to track this game data, I suggested that we push the data from Twine to a Google Spreadsheet. Following the lead of Tom Woodward, I’ve found that Google Spreadsheets are a relatively easy place to collect and analyze data. I wanted to use Google Scripts, which are mostly javascript and a few custom functions, to receive data and parse it into the cells of the Google Sheet.

Martin Hawksey wrote a blog post a few years ago called “Google Sheets as a Database – INSERT with Apps Script using POST/GET methods (with ajax example).” Martin had set up an Ajax form that could be embedded in any website that would pass data to his Google Script which would then record it in his Google Sheet. Martin’s code (below) receives an HTTP Get or Post call generated by an Ajax form, parses the parameters of that HTTP call, and stores those parameters in a Google Sheet. Martin also provides comments in his code to help users customize the Google script and initiate it as a Web App.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
//  1. Enter sheet name where data is to be written below
        var SHEET_NAME = "DATA";
 
//  2. Run > setup
//
//  3. Publish > Deploy as web app 
//    - enter Project Version name and click 'Save New Version' 
//    - set security level and enable service (most likely execute as 'me' and access 'anyone, even anonymously) 
//
//  4. Copy the 'Current web app URL' and post this in your form/script action 
//
//  5. Insert column names on your destination sheet matching the parameter names of the data you are passing in (exactly matching case)
 
var SCRIPT_PROP = PropertiesService.getScriptProperties(); // new property service
 
// If you don't want to expose either GET or POST methods you can comment out the appropriate function
function doGet(e){
  return handleResponse(e);
}
 
function doPost(e){
  return handleResponse(e);
}
 
function handleResponse(e) {
  // shortly after my original solution Google announced the LockService[1]
  // this prevents concurrent access overwritting data
  // [1] http://googleappsdeveloper.blogspot.co.uk/2011/10/concurrency-and-google-apps-script.html
  // we want a public lock, one that locks for all invocations
  var lock = LockService.getPublicLock();
  lock.waitLock(30000);  // wait 30 seconds before conceding defeat.
 
  try {
    // next set where we write the data - you could write to multiple/alternate destinations
    var doc = SpreadsheetApp.openById(SCRIPT_PROP.getProperty("key"));
    var sheet = doc.getSheetByName(SHEET_NAME);
 
    // we'll assume header is in row 1 but you can override with header_row in GET/POST data
    //var headRow = e.parameter.header_row || 1; Hawksey's code parsed parameter data
    var postData = e.postData.contents; //my code uses postData instead
    var data = JSON.parse(postData); //parse the postData from JSON
    var headers = sheet.getRange(1, 1, 1, sheet.getLastColumn()).getValues()[0];
    var nextRow = sheet.getLastRow()+1; // get next row
    var row = []; 
    // loop through the header columns
    for (i in headers){
      if (headers[i] == "Timestamp"){ // special case if you include a 'Timestamp' column
        row.push(new Date());
      } else { // else use header name to get data
        row.push(data[headers[i]]);
      }
    }
    // more efficient to set values as [][] array than individually
    sheet.getRange(nextRow, 1, 1, row.length).setValues([row]);
    // return json success results
    return ContentService
          .createTextOutput(JSON.stringify({"result":"success", "row": nextRow}))
          .setMimeType(ContentService.MimeType.JSON);
  } catch(e){
    // if error return this
    return ContentService
          .createTextOutput(JSON.stringify({"result":"error", "error": e}))
          .setMimeType(ContentService.MimeType.JSON);
  } finally { //release lock
    lock.releaseLock();
  }
}
 
function setup() {
    var doc = SpreadsheetApp.getActiveSpreadsheet();
    SCRIPT_PROP.setProperty("key", doc.getId());
}

I edited Martin’s original code in lines 39-41. In his code, he’s looking for Post data in a slightly different format than what I generate. Rather than using the parameters from the HTTP Post, my code uses the data from the Post.

Twine Game Code (newer version)

Unlike the earlier version, this code now uses Ajax and jquery, to pass variables that had been collected during gameplay in a Twine game. Twine is built on javascript, so I decided to replace Martin’s Ajax form with a javascript HTTP Post function embedded in Twine. Based on research on how Twine works, I decided that the best way to do this would be to write the javascript code directly into a Twine game passage. My passage, called PostData, would presumably come at or very near the end of my game after all interesting variables have been set:

Screen shot of a Twine game passage showing the code explained in the surrounding post text.

Dan Cox provided me with sample jquery code and explained it. We then wrap the code in Twine’s script syntax <script></script>. This code sends an HTTP Post to whatever url is provided (like the url for your Google Script Web App) with a json package defined in the var data line.

First you need to reference the jquery library in the head of your file:

<script src=”jquery-3.3.1.min.js”></script>

Once that’s been loaded, you place this code at the end of your game (please note that you need to add the <script></script> modifiers in Twine:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var sendData = JSON.stringify({
"var1": harlowe.State.variables['var1'], 
"var2": harlowe.State.variables['var2'], 
"var3": harlowe.State.variables['var3'], 
"var4": harlowe.State.variables['var4'], 
"var5": harlowe.State.variables['var5']
});
 
$.ajax({
url:"Your Url",
method:"POST",
dataType: "json",
data: sendData
}).done(function() {});

However, in order to pull variables out of the Harlowe version of Twine that I was using, I also needed to add the following code by editing the Story Javascript:

Twine Javascript Screen Shot

This bit of Javascript passes all variables defined within the Twine game into an array (window.harlowe) that is accessible by Javascript code that is embedded in the game. Here’s the code in case you want to try this out:

1
2
3
if (!window.harlowe){
	window.harlowe = {"State": State};
}

I hope this work will be useful in studying any Twine game to see how players are moving through the game. You could record any variables in the game and also the games ‘history’ to see which passages each player went through. This has obvious uses for educational games in being able to provide feedback to players, but it also has implications for game design more broadly with the increased use metrics.

Implement in your own game

In order to implement this for your own game, I would suggest following these steps:

  1. Copy the Javascript code above (starts with if (!window)) into your Twine game’s Javascript panel
  2. Copy the PostData code above and paste it into a TwinePost passage towards the end of your game
  3. Then replace the variables in the TwinePost passage so that harlowe.State.variables[‘var1’] becomes harlowe.State.variables[‘your variable name here’] for each of the variables you want to track
  4. Click this link to get a copy of my Google Spreadsheet
  5. Make sure the column headers in the spreadsheet match your variable names from the TwinePost passage
  6. Share your Google Sheet, so that anyone with the link can edit it. This will allow the incoming data to post
  7. In the Google Sheet, click on Tools->Script Editor and follow Martin Hawksey’s instructions for steps 2-5
  8. When you publish your Script as a Web App, it will give you a URL for the Web App. Copy this URL and paste it into the URL variable in your TwinePost passage code.
  9. You’re done. Play your game and see if everything works. If it doesn’t work, tweet at Tom Woodward. He’s good at fixing code and has nothing but free time on his hands.

I am excited about this code because it answers a question for several of our faculty members and makes Twine games more useful as formative assessments. Hawksey did an excellent job in keeping his code very generalized, and I’ve tried to preserve that, so that you can track whatever variables you want.

You could also use the HTTP Post javascript code outside of Twine in any other web site or web app to pass information to your Google Sheet. Tom has blogged a couple of times about using code to send data to Google Forms and autosubmitting into a Google Spreadsheet. I think the process described above denecessitates that Google Form pass through and moves us a step closer to Google sheets as a no-SQL data base alternative.

Page 1 of 30

Powered by WordPress & Theme by Anders Norén

css.php