Need-based AI in JavaScript

From RogueBasin
(Difference between revisions)
Jump to: navigation, search
Line 5: Line 5:
 
== Basics ==
 
== Basics ==
  
We are going to build the AI logic based on the famous [http://img.pandawhale.com/75824-Maslow-WiFi-4S8F.png Hierarchy of needs] (minus Wifi). To keep the code clean, all stuff related to AI will be put into a separate (pluggable) JavaScript object "AI". Mixing this AI with a Being will be shown later.
+
We are going to build the AI logic based on the famous [http://img.pandawhale.com/75824-Maslow-WiFi-4S8F.png Hierarchy of needs]. To keep the code clean, all stuff related to AI will be put into a separate (pluggable) JavaScript object "AI". Mixing this AI with a Being will be shown later.
  
 
First of all, let's define some "needs" our beings shall consider:
 
First of all, let's define some "needs" our beings shall consider:
Line 12: Line 12:
 
<syntaxhighlight lang="javascript">
 
<syntaxhighlight lang="javascript">
 
this._needs = {
 
this._needs = {
survival: 1,
+
    survival: 1,
health: 1,
+
    health: 1,
satiation: 1,
+
    satiation: 1,
revenge: 1
+
    revenge: 1
 
};
 
};
 
</syntaxhighlight>
 
</syntaxhighlight>
 
</div>
 
</div>
  
'''Survival''' is the basic need to survive, i.e. to maintain at least a minimal amount of hitpoints. '''Health''' is a need to be healthy, to regenerate as many hitpoints as possible. '''Satiation''' represents the need to fight hunger. Finally, '''''' is a need to avenge any damage that was done to us.
+
'''Survival''' is the basic need to survive, i.e. to maintain at least a minimal amount of hitpoints. '''Health''' is a need to be healthy, to regenerate as many hitpoints as possible. '''Satiation''' represents the need to fight hunger. Finally, '''Revenge''' is a need to avenge any damage that was done to us.
  
 
These needs are initially set to '''1''', meaning "satisfied". This article will only use '''1''' and '''0''' values (0 meaning unsatisfied), but for more complex scenarios, float values can be used to represent partially satisfied/unsatisfied needs.
 
These needs are initially set to '''1''', meaning "satisfied". This article will only use '''1''' and '''0''' values (0 meaning unsatisfied), but for more complex scenarios, float values can be used to represent partially satisfied/unsatisfied needs.
 +
 +
== Observing need change ==
 +
 +
The AI needs to do two major things: watch how the values influencing individual needs change and act accordingly. We can leverage the language used (JavaScript) to perform some major ''monkey-patching'' (code surgery). Assuming that our <code>Being</code> object exposes the canonical ''damage'' and ''heal'' methods, the <code>AI</code> part can implement its own version of these functions: 
 +
 +
<div style="padding:5px; background-color:#eee; margin-bottom:2em;">
 +
<syntaxhighlight lang="javascript">
 +
Being.prototype.heal = function() {
 +
    this._hp = 10;
 +
}
 +
AI.prototype.heal = function() {
 +
    this._needs.survival = 1;
 +
    this._needs.health = 1;
 +
}
 +
 +
Being.prototype.damage = function(attacker) {
 +
    this._hp--;
 +
}
 +
AI.prototype.damage = function(attacker) {
 +
    this._needs.revenge = 0;
 +
    this._needs.health = 0;
 +
    this._needs.survival = (hitpoints < threshold);
 +
}
 +
</syntaxhighlight>
 +
</div>

Revision as of 22:26, 24 September 2013

Warning: this is a work in progress! Do not read until finished.

This article describes an implementation of a need-based AI system in JavaScript. It is somewhat similar to Need driven AI.

Basics

We are going to build the AI logic based on the famous Hierarchy of needs. To keep the code clean, all stuff related to AI will be put into a separate (pluggable) JavaScript object "AI". Mixing this AI with a Being will be shown later.

First of all, let's define some "needs" our beings shall consider:

this._needs = {
    survival: 1,
    health: 1,
    satiation: 1,
    revenge: 1
};

Survival is the basic need to survive, i.e. to maintain at least a minimal amount of hitpoints. Health is a need to be healthy, to regenerate as many hitpoints as possible. Satiation represents the need to fight hunger. Finally, Revenge is a need to avenge any damage that was done to us.

These needs are initially set to 1, meaning "satisfied". This article will only use 1 and 0 values (0 meaning unsatisfied), but for more complex scenarios, float values can be used to represent partially satisfied/unsatisfied needs.

Observing need change

The AI needs to do two major things: watch how the values influencing individual needs change and act accordingly. We can leverage the language used (JavaScript) to perform some major monkey-patching (code surgery). Assuming that our Being object exposes the canonical damage and heal methods, the AI part can implement its own version of these functions:

Being.prototype.heal = function() {
    this._hp = 10;
}
AI.prototype.heal = function() {
    this._needs.survival = 1;
    this._needs.health = 1;
}
 
Being.prototype.damage = function(attacker) {
    this._hp--;
}
AI.prototype.damage = function(attacker) {
    this._needs.revenge = 0;
    this._needs.health = 0;
    this._needs.survival = (hitpoints < threshold);
}
Personal tools