First of all, there is no system for writing a game which does not require you, at some level, to think like a programmer. The “intelligent” responses of any game are, after all, being simulated by an idiot tin box with zero intelligence. You have to supply that lack, and have to supply it in a logical fashion, so that the responses will be logical. Furthermore, you have to do so in a pernickety detail-obsessive fashion, in order to communicate with said Idiot Tin Box. This style of thinking is the essence of coding, regardless of what language is being used, because until we have full Turing machines, this is the essential problem of interacting with them.
The deep-level problem with ADRIFT is that it doesn’t use the verb + object system. Each command in each room is a separate, unique thing. While this makes it easier to begin a game in ADRIFT, it makes it much harder to make a decent, reasonably playable game, and very easy to make a lousy, unplayable one.
For example, imagine a game: “Farm fries.”
The player has to make some french fries. As humans, we can immediately imagine the necessary situation, but the tin box can’t. So we have to supply it explicitly:
The player starts in the Farmhouse Kitchen, must go out to the Potato Field, pick a potato, then cut it up (with a knife), and drop the pieces into hot oil in the fryer (which is in the kitchen.)
Someone using a system such as Tads, Hugo, Inform (either 6 or 7), Alan etc., or any language which uses the verb + object system: code two rooms, and five objects: the fryer, the knife, the potato, the potato pieces, and the french fries. She codes the potato to respond to the verb “cut” by first checking that the player holds the knife, and then exchanging itself for the potato pieces object. Similarly, she codes the fryer to respond to the player putting potato in it by rejecting the whole potato, but exchanging the potato pieces for french fries. While “put pieces in fryer” would describe the intention, players would be more likely to try “fry potato.” “Fry” is not a standard verb, so she’d have to create it.
The diligent Adrifter also codes two rooms, Farmhouse Kitchen and Potato Field, puts a knife and a fat fryer in the first, and a potato in the second, and has a potato pieces object and a french fries object waiting offstage. He codes a “pick potato” action in Potato Field, and a “fry potato” action in the kitchen. But the “cut potato” action could logically happen in either room, unless the knife is somehow made non-portable. So an Adrifter has to code the “cut potato” action twice. Not much of an additional burden, you’d think. Particularly given that the verb + object system required a whole new verb, which Adrift doesn’t.
But now comes the hard part: making the game robust, and pleasant to play. The author has to think of all the different commands a player might use: “cut potato”, “chop spud”, “slice vegetable” blah blah, to avoid the player having to guess the author’s exact vocabulary, and it’s here that verb+object shines. The language’s structure naturally gathers synonyms for an object into one place, and synonyms for a verb into one place, so it’s easier to correct an oversight.
Now the downside of Adrift’s simplicity comes into effect: you must code all of those synonyms into each action in each room. Trivial in a two room game. In a larger game it’s very easy to think of a synonym, add it to the actions in all the obvious rooms, but forget a few un-obvious ones – and so bugs creep in.
If we now wanted to add another room, say Dining Room, the Adrift coder has to remember to write a “cut potato” action in there, too, whereas someone using any of the verb+object rules doesn’t even need to consider it: the system automatically takes care of the issue of potato cutting everywhere in the game. The larger a game becomes, the more significant this advantage becomes.
To be fair to Adrift, the various versions have tried to address this problem, but it’s a fundamental weakness of the language, and so will always be there to some extent.
I’d say that Adrift’s greatest advantage over other languages was its friendly interface, which hides the fact that you are doing coding by building the language’s logic into it. I still think that if you want to write menu-style conversations it’s very good indeed, letting you concentrate on what the NPC is saying rather than distracting you with all the logical nuts and bolts of needing to tell the Tin Box what to print out next, and that “some french fries” is plural.
Overall though, I’d say that the initial simplicity of Adrift is not worth sacrificing the long-term advantages of a (slightly) more complex language doing a lot of the heavy lifting for you.
For example, here’s the “game” I’ve just described, in Inform 7 code:
"Farmhouse Fries" by "Example"
[Text in square brackets like this, are comments.]
The Farmhouse Kitchen is a room. "Cream painted walls, and a ceiling of heavy oak beams. Against one wall, your new TatoFri 3000 gleams, giving off the scent of hot fat. The door to the east is open, giving you a pleasant view of the potato fields."
The deep fat fryer is scenery in the farmhouse kitchen. The description of the deep fat fryer is "The fat seethes and bubbles, already hot." Understand "hot", "TatoFri" or "3000" as the deep fat fryer. ["deep" "fat" and "fryer" are automatically recognised as synonyms, so we don't need to add them using Understand. Stating that something is "scenery" means it doesn't get described in the room description, and is fixed in place by default.]
A knife is in the Farmhouse kitchen. Understand "kitchen knife" or "blade" as the knife.
The Potato Fields is east of the Farmhouse Kitchen. "Bare hummocked earth, where, before the harvest, many potato plants grew. A rambling farmhouse is to the west."
A thing called a potato is in the Potato Fields.
Instead of cutting the potato:
if the player is not carrying the knife:
say "You've nothing to cut the potato up with.";
now the player carries some raw potato pieces;
remove the potato from play;
say "You cut the potato into pieces.";
Some raw potato pieces are nowhere.
Some french fries are nowhere. Some french fries are edible.
[Cutting is a standard verb, so we didn't need to add it. But "frying" is not something that's natively understood, so we have to create it.]
Frying is an action applying to one touchable thing. Understand "fry [something]" as frying.
Check frying something: [This is the general response.]
say "Frying [the noun] would achieve little.";
stop the action.
Check frying the potato:
say "You can't fry a whole potato: it would still be raw in the middle." instead.
["instead" is a keyword, meaning "stop the action". As you can see, it's more convenient.]
Check frying some raw potato pieces when the player cannot see the deep fat fryer:
say "The deep fat fryer isn't here." instead;
[we could check if the player is in the kitchen, but if we later made the fryer portable we'd then need to edit this check condition.]
Check frying some raw potato pieces:
now the player carries some french fries;
remove the raw potato pieces from play;
say "You toss the uninspiring pieces of raw potato into the seething hot fat. Mastering your impatience, you wait until they've cooked, and then, using a metal spoon, fish out the french fries." instead;
[I know it looks weird putting the game mechanics of frying in the check action: this is because "Frying" is a dummy action and doesn't have separate Carry Out and Report stages. It's not worth creating them when we're only going to allow one object in the entire game to be fried. We could write it as an instead rule -- "instead of frying some raw potato pieces:" followed by the same clauses underneath.]
[okay, it's not a full game unless the player can win it, so:]
Instead of eating the french fries:
end the story saying "Congratulations! You are now entitled to wear the traditional cardboard crown of the French Fry Chef!"
[code ends here]
If you download the current I7 package for either Windows, Mac or Linux, and paste the code above into the “Source” pane, it will compile into a playable game. Of course the package comes with a bunch of well written documentation, but even without that, simply looking at the code above, you can see what each bit of the code does: it’s pretty readable.
But although it looks like English, it’s really a specialised dialect: “Inform 7 English,” if you like. There are some subtle pitfalls: notice for example that “The Potato Fields is east of…” not “are east of…” because “Potato Fields” is a single object of the kind “room”. This goes back to what I was saying at the beginning of the post: there is no system for creating IF where you aren’t programming at some level.