Chapter 4: Paintball

In this set of exercises, you will program more complex behavior and interactions.

Learning Objectives:

  • Use keyboard controls to move an agent
  • Use conditional blocks in the context of keyboard controls
  • Explain how “if... “ blocks work in the context of keyboard controls
  • Demonstrate how one agent can create another

New terms:

  • Collidee

New blocks:

  • if ...
  • key held?
  • take camera
  • comparison blocks (>, <, =, etc.)

Try to write the code without 'peeking' at the sample code.

Read the description of each part and see if you can figure out how to put the blocks together. If you get stuck, put your mouse over the gray block to see the actual code. Test your program often to make sure that each chunk of code you add works before moving on to the next part.

Part 1: Create Turtle agents

Use what you've learned in previous chapters to build some code.

Steps:

  1. Create a new blank project and rename the project title to "Paintball"
  2. On The World page, use a "When ___ pushed" block to create 50 Turtle agents and set the color (ex: brown) and shape (ex: Cube), then scatter.
  3. Do not forget to do some basic housekeeping by deleting all agents before creating the 50 new agents

Check your code:

  1. Click the "Run Code" and "setup" buttons
  2. You should see 50 scattered Turtle agents with the color and shape that you chose

You can get the blank NetLogo template file here.

Note that we need to create a separate breed called "target". This is because, in NetLogo, the breed "turtle" applies to all agents no matter the species.

The Net Logo code for this would be:

breed [targets target]

to setup
  clear-all
  create-targets 50 [
    set color brown
    set shape "box"
    set xcor (random 32) - 16
    set ycor (random 32) - 16
  ]

Part 2: Create Player Breed and Player agent

The skills for this can be found in "Catching Flies".

Steps:

  1. Click on "Add Breed" and create a new breed called "Player"
  2. On The World page, add to the existing "When setup pushed" a block to create one Player agent.
  3. Set the color and shape of the agent as you prefer.
  4. Drag the "take camera" block from the "Agents" drawer and place it so that the Player will take the camera - so you can see Spaceland from the Player's point of view.

The Net Logo code for this would be:

Note that there is no "Take camera" in NetLogo.

breed [players player]
breed [targets target]

to setup
  clear-all
  create-targets 50 [
    set color brown
    set shape "box"
    set xcor (random 32) - 16
    set ycor (random 32) - 16
  ]

  create-players 1 [
    set color blue
  ]

end

Check your code:

  1. Click the "Run Code" and "setup" buttons
  2. You should see 50 scattered Turtle agents with the color and shape that you chose from the point of view of your player agent.

Part 3: Program controls for the Player agent

Program the Player agent to move in response to holding down the arrow keys

Steps:
  1. In the "player" panel, drag in a "while ... toggled" block and choose "forever" from the pop-up menu.
  2. Drag in four "if ..." blocks from the "logic" drawer and plug in "... key held" blocks from the "keyboard" drawer.
  3. Drag in a specific block from the "movement" drawer so that:
    • W moves the player forward 1
    • X moves the player backward 1
    • A turns the player left 10 degrees
    • D turns the player right 10 degrees

In NetLogo, this takes 2 steps. First, make 4 buttons like the one below. Give them names and commands like "goForward", "goBack", "turnLeft", "turnRight", and assign action keys as appropriate.Then, write code for each button in the code pane (note that you must ask the players even though there's only one player):

to goForward
  ask players [
    forward 1
  ]
end

to goBack
  ask players [
    forward -1
  ]
end

to turnLeft
  ask players [
    left 10
  ]
end

to turnRight
  ask players [
    right 10
  ]
end

NetLogo will fuss if the names of the commands (e.g. "goForward") on the buttons don't match the code.

Check your code.

  • Scroll up to Space Land, click "Run code", then "setup", then "forever"
  • Press the W, X, A, and D keys and see that the view from the player agent changes as you move and turn in SpaceLand.

Part 4: Create the paintball agents

Create a Paintball breed and Program the Player agent to launch them.

Steps:
  1. Use "Add Breed" to create a new breed called "Paintball"
    • Make sure that a Paintball tab appears in the Workspace
  2. In the "Player" tab, add an "if..." block to bottom of the list of the blocks that determine what pressing various keys do.
    • Set it so that, if the "s" key is held down, it creates a new paintball agent, sets its size to 0.5, its shape to "sphere", and its color to a random color.

You will need to create a button as above called "Shoot" with the command "shoot" and the action key "s".

You then add the code below:

to shoot
  create-paintballs 1 [
    move-to one-of players
    set heading [heading] of one-of players
    set shape "dot"
    set color one-of base-colors
  ]
end

The "move-to" and "set heading" are required in NetLogo to have the paintball start at the player and facing the same direction. In NetLogo, new agents are created at 0,0 with random headings.

Check your code:
  • Click the "Run Code", "setup" and "forever" buttons. Then press the "s" key.
  • When you press the "s" key, a paintball should be created; you will need to move the player using the other keys to see the paintball since the paintball is made in the space where the player was when you hit the s key.

Part 5: Program the behavior of the paintball agents.

Write code so that the paintballs fly in straight lines and are deleted when they leave SpaceLand.

Steps:
  1. In the "Paintball" pane, drag in a "While... toggled" and set the pop-up menu to "Forever".
  2. Add code to make the paintballs move forward one unit with each time step. Note that there's a problem with SLNova - if you make an agent move more than one step at a time, it "hops" over anything in between without colliding with them. As a result, you should NEVER have any agents move more than "forward 1" if you want your collisions to work properly.     
  3. Add code below this to delete paintballs if they reach the edge of Spaceland.
    • SpaceLand is a coordinate grid with x going from -50 to 50 and y going from -50 to 50 and (0,0) at its center.
    • Use a series of "if..." statements to "delete" paintballs when they get to the edges of Spaceland.
    • Also, since agents bounce when they reach the edge, they might never land exactly at 50. That's why it's beter to test for x > 48 or x > 49 instead of x = 50

Add this code to the "to Forever" block:

to forever
  ask paintballs [
    forward 1
    if xcor <= -15 [die]
    if ycor <= -15 [die]
    if xcor >= 15 [die]
    if ycor >= 15 [die]
  ]
end
		  

Spaceland in NetLogo extends from -16 to 16 in the x direction and -16 to 16 in the y direction with 0,0 in the center. You can change this by clicking the "settings" button at the upper right of the controls in NetLogo.

Note that, in NetLogo, you write code for specific agents by putting it inside an "ask..." block rather than in the agent's tab as you do in SLN.

Test your code:

Be sure that your code can do all of these things (you should learn to push it hard and try to "break" it - better to find bugs early):
  • You should be able to move the player around spaceland with the A, D, W and X keys.
    • If this does not work correctly in SLN, check your code in the "player" tab.
    • If this does not work correctly in NetLogo, check the button settings and the "toForward" etc code.
  • Pressing the "S" key should shoot a single paintball in the direction you're facing.
    • If this does not work correctly in SLN, check your code in the "paintball" tab.
    • If this does not work correctly in NetLogo, check the button settings and the "toShoot" code. Note that you may need to slow the simulation down to catch the paintball moving.
  • Paintballs should disappear when they reach the edge of spaceland. Try this for all four edges to be sure.
    • If this does not work correctly in SLN, check your code in the "paintball" tab - especially all the "if.." blocks and the "<=" etc.
    • If this does not work correctly in NetLogo, check the toForever code and look - especially at the if statements.

The complete code so far is:

breed [players player]
breed [paintballs paintball]
breed [targets target]

to setup
  clear-all
  create-targets 50 [
    set color brown
    set shape "box"
    set xcor (random 32) - 16
    set ycor (random 32) - 16
  ]

  create-players 1 [
    set color blue
  ]

end

to goForward
  ask players [
    forward 1
  ]
end

to goBack
  ask players [
    forward -1
  ]
end

to turnLeft
  ask players [
    left 10
  ]
end

to turnRight
  ask players [
    right 10
  ]
end

to shoot
  create-paintballs 1 [
    move-to one-of players
    set heading [heading] of one-of players
    set shape "dot"
    set color one-of base-colors
  ]
end

to forever
  ask paintballs [
    forward 1
    if xcor <= -15 [die]
    if ycor <= -15 [die]
    if xcor >= 15 [die]
    if ycor >= 15 [die]
end

Part 6: Program the Collision between Paintball and Turtle

Write code so that, when a turtle is hit by a paintball, the paintball disappears and the turtle gets 'painted all over'.

Steps:

  1. Drag a "On collision with ... do..." block from the "Detection" drawer to the Turtle page and choose "paintball" from the pop-up menu.
  2. Into that block, put in blocks to set the Turtle's color to the color of the "collidee".
    • The "collidee" block can be found in the "Detection" drawer - it corresponds to the agent which hit the Turtle.
  3. Add in a "delete agent..." block from the "Agents" drawer and plug a "collidee" block in so the collidee will be deleted on collision.

In NetLogo, it is necessary to look at the collision from the point of view of the paintball, not the target. (This is because there isn't a "kill" command in NetLogo, only "die")

First, the paintball looks for any targets it has hit. If they exist, they are told to turn the color of "myself" (the paintball that made the ask). Then, the paintball is told to die. You can try moving the "die" command around to see what happens and get a feel for how this works.

to forever
  ask paintballs [
    forward 1
    if xcor <= -15 [die]
    if ycor <= -15 [die]
    if xcor >= 15 [die]
    if ycor >= 15 [die]
    
    if any? targets in-radius 1 [
      ask targets in-radius 1 [
        set color [color] of myself
      ]
      die
    ]
  ]
end
	
Test your code:

You should be sure that your code does all of these things:
  • It should do all of the things it used to do - be sure you didn't accidentally 'break' anything. If you need to, go back and fix it.
  • You should be able to aim and shoot paintballs at turtles (or targets) and if you hit one, the turtles should change to the color of the paintball and the paintball should disappear.

You can download a working version of this project here.

Part 7: Extensions

Get creative and see what you can do.

Here are some things to try:

Part 8: NetLogo Extensions

There are some cool things you can only do in NetLogo.

Here are some things to try:

Use comments to document your work.

Anything on a line of code after two semicolons (";;") will be ignored by NetLogo but visible to you. You can use this to leave notes to yourself so you don't have to remember:
  • why you did something a particular way
  • what a non-obvious piece of code does
  • what this trait represents
  • warnings to yourself like "don't make this number bigger than 5 or the simulation crashes!"

Comments can also be on lines by themselves.

The comment below explains the 'weird xcor code'

to setup
  clear-all
  create-targets 50 [
    set color brown
    set shape "box"
    ;; this is the equivalent of "scatter"
    set xcor (random 32) - 16
    set ycor (random 32) - 16
  ]

  create-players 1 [
    set color blue
  ]

Use comments to make easy-to-undo changes to your code.

There isn't a good 'undo' button in SLN, so if you wonder what happens when you remove a block of code, it can sometimes be a pain to put it back in the right place if you change your mind.

In NetLogo, you can comment out code, see what happens, and then 'un-comment' it easily.

Here, you can see what happens if you take out one of the 'weird xcor' lines in the setup code by adding 2 semicolons. Try it and see what happens. Just delete the semicolons to put it back to the way it was.

to setup
  clear-all
  create-targets 50 [
    set color brown
    set shape "box"
    ;; this is the equivalent of "scatter"
    set xcor (random 32) - 16
    ;;set ycor (random 32) - 16
		
Use the Command Center to test the effect of individual lines of code.

If you look at the bottom of the "Interface" pane, you'll see "Command Center" and a line marked "observer>".

Using this, you can execute individual commands to experiment with what they can do. For example, after clicking "setup", you could enter "ask players [set color red]" (without quotes).

If you type that in the "observer>" box and hit return, you'll see the player turn red. The command you entered will then appear in the "Command Center". The commands you enter here will not become part of your code - you can see this by clicking 'setup' and you'll see that the player starts off blue.

This can help you if you want to experiment with new code without editing your main code. You can also let the simulation run to a specific point and then enter a command to see what's going on right then.
Inspect and Alter Individual Agents.

If you right-click or hold the control key while clicking any of the agents on the screen, a menu pops up. If you choose the name of the agent, another menu pops up and you can "inspect" that agent.

In the window that pops up, you can:
  • see a close up of the agent
  • see all of the agent's traits
    • You can edit any of the traits and the results appear immediately on the screen
  • send commands to just that agent by typing them in the box at the bottom (where you see I've typed "set color red"

This can be very useful, especially when you add custom traits to agents, in debugging your code and being able to see "what would happen if...".