Concepts
Introduction
Shields

Code
Check shields
computeRetreatPoint()
Retreat if shields low

Game hints
Shield mastery

Lesson 6 - Shields

Introduction

Congratulations on making it this far! We've come a long way since Lesson 1 :) As a reward, your Dragons have been upgraded with a new ability: Shields. This will come in handy, because in this quest... enemy Dragons shoot back.

In this Lesson, you will learn how to master your Dragon's Shields. If you succeed, you will be able to defeat two enemy Dragons with only one Dragon.

Shields

Dragons have health points and shield points. Shields absorb damage first, but when shields are gone, damage starts eating up health points. Shields can regenerate when a dragon is not taking damage. When a dragon has no more health points, it falls out of the sky and is out of the game.

So, since shields regenerate, it is a good idea to manage your Dragon's shield energy. As much as possible, you want to absorb damage with your shields and save your health points.

Check shields

Your Dragon's shields can absorb quite a bit of damage. But they can only take so many hits before they run out of energy. So, you probably want to keep an eye on your shields so that you can get out of trouble before your shields fall.

First, some info on shields:
With these ingredients, we can make a new function to check if a Dragon's shield energy is low:

function isShieldEnergyLow(dragon) { if (dragon.maxShields == 0) { // this Dragon has no shields at all return true; } // compute percent of shield energy remaining var shieldPct = dragon.shields / dragon.maxShields * 100; // if shield energy is less than 20%, // say that shields are low if (shieldPct < 20) return true; // shields are greater than 20%, // say that shields are not low return false; }

Helper.computeRetreatPoint()

Now that we have a way to check if a Dragon's shield energy is low, what do we do if we notice a Dragon in trouble? Yup, EVASIVE MANEUVERS! Retreat. Escape danger. Live to fight another day.

To do that, we can use the functon below:

Helper.computeRetreatPoint(unitPos, enemyPos)

Retreat if Dragon has weak shields

Remember our friend if-else from the last lesson? That's what we'll use to tell your Dragon to retreat... if its shield energy is low. We'll combine the two functions we just saw above:

if (isShieldEnergyLow(dragon)) { var escapePos = Helper.computeRetreatPoint(dragon.pos, enemy.pos); Game.moveTo(dragon.id, escapePos.x, escapePos.y); }

Shield mastery

The trick to improving your Dragon's defense is to take advantage of your shields' regenerative powers. Find the balance between offense and defense. If you can keep escaping danger, your shields can keep regenerating to save your health points (which don't regenerate). And the more Dragons you keep alive, the better your chances of winning each game.

Now let's update your Dragon A.I. code with everything we've learned in this lesson:

function isShieldEnergyLow(dragon) { if (dragon.maxShields == 0) { // this Dragon has no shields at all return true; } // compute percent shield energy remaining var shieldPct = dragon.shields / dragon.maxShields * 100; // if shield energy is less than 20%, // say that shields are low if (shieldPct < 20) return true; // shields are greater than 20%, // say that shields are not low return false; } function run(state) { // get array of all my units var myUnits = Helper.getMyUnits(state); // get the first Dragon in the array var dragon = myUnits[0]; // get first Dragon's ID var dragonId = dragon.id; // get this Dragon's closest enemy var enemyFound = Helper.getClosestEnemy(state, dragon); if (!enemyFound) { // yay! no more enemies -- nothing left to do. // calling "return" stops this function from // executing any other code below. return; } // get enemy Dragon's ID var enemy = enemyFound.unit; var enemyId = enemy.id; // ******** NEW! ******** // Choose offense or defense. // Decide to move Dragon toward or away from enemy if (isShieldEnergyLow(dragon)) { // shield is low, retreat! var escapePos = Helper.computeRetreatPoint(dragon.pos, enemy.pos); Game.moveTo(dragon.id, escapePos.x, escapePos.y); } else { // move Dragon to enemy Dragon's position // (but only if enemy is too far away) if (enemyFound.dist > 350) { // move toward enemy -- it's more than 350 units away Game.moveTo(dragonId, enemy.pos.x, enemy.pos.y); } } // attack! Game.attack(dragonId, enemyId); }
Awesome, young master :) Your Dragon is getting powerful...

Cheatcode

Spoiler alert! Click to reveal full solution.
<!DOCTYPE html> <html> <body> <div id="display">hello</div> <script> function isShieldEnergyLow(dragon) { if (dragon.maxShields == 0) { // this Dragon has no shields at all return true; } // compute percent shield energy remaining var shieldPct = dragon.shields / dragon.maxShields * 100; // if shield energy is less than 20%, // say that shields are low if (shieldPct < 20) return true; // shields are greater than 20%, // say that shields are not low return false; } function run(state) { // get array of all my units var myUnits = Helper.getMyUnits(state); // get the first Dragon in the array var dragon = myUnits[0]; // get first Dragon's ID var dragonId = dragon.id; // get this Dragon's closest enemy var enemyFound = Helper.getClosestEnemy(state, dragon); if (!enemyFound) { // yay! no more enemies -- nothing left to do. // calling "return" stops this function from // executing any other code below. return; } // get enemy Dragon's ID var enemy = enemyFound.unit; var enemyId = enemy.id; // ******** NEW! ******** // Choose offense or defense. // Decide to move Dragon toward or away from enemy if (isShieldEnergyLow(dragon)) { // shield is low, retreat! var escapePos = Helper.computeRetreatPoint(dragon.pos, enemy.pos); Game.moveTo(dragon.id, escapePos.x, escapePos.y); } else { // move Dragon to enemy Dragon's position // (but only if enemy is too far away) if (enemyFound.dist > 350) { // move toward enemy -- it's more than 350 units away Game.moveTo(dragonId, enemy.pos.x, enemy.pos.y); } } // attack! Game.attack(dragonId, enemyId); } Game.register(run); </script> </body> </html>