1
00:00:05,270 --> 00:00:08,060
Hi, welcome to week 3.

2
00:00:08,060 --> 00:00:10,580
We're going to start
a brand new project.

3
00:00:10,580 --> 00:00:12,080
This is project 3.

4
00:00:12,080 --> 00:00:14,895
We're going to call it
the ecosystem simulation.

5
00:00:14,895 --> 00:00:17,440
Let's look at the premise of

6
00:00:17,440 --> 00:00:19,960
what we're going to be doing
throughout the whole week.

7
00:00:19,960 --> 00:00:22,360
In this project, we
really want to exercise

8
00:00:22,360 --> 00:00:25,920
the interrelation
between classes,

9
00:00:25,920 --> 00:00:30,640
but really how they give
rise to a dynamic ecosystem.

10
00:00:30,640 --> 00:00:32,660
We're going to do it
with simple graphics,

11
00:00:32,660 --> 00:00:34,260
but I think you could really

12
00:00:34,260 --> 00:00:37,180
extrapolate this two whole
different ser domains,

13
00:00:37,180 --> 00:00:41,025
and a whole series sets
of graphic environment.

14
00:00:41,025 --> 00:00:42,970
An ecosystem simulation is

15
00:00:42,970 --> 00:00:44,850
a computational model
that replicates

16
00:00:44,850 --> 00:00:49,125
the interactions of the
dynamics of living organisms.

17
00:00:49,125 --> 00:00:51,745
Also the relationship
to the environment.

18
00:00:51,745 --> 00:00:56,150
We're going to start
with a simple food class

19
00:00:56,150 --> 00:00:59,690
that is going to have
its own internal logic,

20
00:00:59,690 --> 00:01:01,920
like the logic of growth, decay.

21
00:01:01,920 --> 00:01:03,750
You could even go further and

22
00:01:03,750 --> 00:01:05,920
expand that class on
thinking of species.

23
00:01:05,920 --> 00:01:08,720
Then we're going to create

24
00:01:08,720 --> 00:01:11,860
a herbivore unit that
unlike a particle,

25
00:01:11,860 --> 00:01:15,860
instead of being ruled
by external forces,

26
00:01:15,860 --> 00:01:18,960
is going to be ruled by
its own internal logic.

27
00:01:18,960 --> 00:01:21,220
We're going to bring back the
notion of a state machine,

28
00:01:21,220 --> 00:01:22,640
what would be the
states in which

29
00:01:22,640 --> 00:01:24,060
this herbivore will move around

30
00:01:24,060 --> 00:01:27,880
the environment and
potentially access food,

31
00:01:27,880 --> 00:01:30,135
maybe reproduce or potentially,

32
00:01:30,135 --> 00:01:33,480
flee away from a
carnivore, a predator.

33
00:01:33,480 --> 00:01:36,225
We're going to create
another entity later.

34
00:01:36,225 --> 00:01:38,095
Or for you to

35
00:01:38,095 --> 00:01:41,730
explore the interrelationship
between the system and how

36
00:01:41,730 --> 00:01:44,810
the populations of each one
of these different entities

37
00:01:44,810 --> 00:01:46,970
might be at risk or

38
00:01:46,970 --> 00:01:49,940
change depending on the
behavior of the others.

39
00:01:49,940 --> 00:01:53,110
Let's start with the simplest,

40
00:01:53,110 --> 00:01:55,650
which is our food entity.

41
00:01:55,650 --> 00:01:59,030
That's the one we want
to write in this video.

42
00:01:59,030 --> 00:02:01,130
But for now, we're
just going to give it

43
00:02:01,130 --> 00:02:03,330
a lifespan similar
to a particle.

44
00:02:03,330 --> 00:02:07,110
It's going to grow, but it's
going to dictate a sense of

45
00:02:07,110 --> 00:02:10,360
its own a journey

46
00:02:10,360 --> 00:02:12,870
from a small sprout

47
00:02:12,870 --> 00:02:13,870
to something that might grow

48
00:02:13,870 --> 00:02:15,230
into a tree or
something like that.

49
00:02:15,230 --> 00:02:18,470
Again, think that I'm not
going to be focusing too much

50
00:02:18,470 --> 00:02:22,150
on the graphic representation
of this food item,

51
00:02:22,150 --> 00:02:25,975
which is thought to be a
plant of some sort or grass.

52
00:02:25,975 --> 00:02:28,150
But for the time being,

53
00:02:28,150 --> 00:02:29,030
that's something that you can

54
00:02:29,030 --> 00:02:30,450
replace very quickly
with some of

55
00:02:30,450 --> 00:02:31,790
the knowledge that
we've acquired

56
00:02:31,790 --> 00:02:34,075
in course 1 and course 2.

57
00:02:34,075 --> 00:02:36,850
Let's jump into
processing and start

58
00:02:36,850 --> 00:02:40,020
writing our ecosystem
simulation. Here we are.

59
00:02:40,020 --> 00:02:43,870
I'm starting from
our boiler plate

60
00:02:43,870 --> 00:02:46,525
Canvas so in processing.

61
00:02:46,525 --> 00:02:48,120
I've imported the random.

62
00:02:48,120 --> 00:02:52,240
I have a Canvas with Canvas
width and Canvas height.

63
00:02:52,240 --> 00:02:54,880
I'm going to create a new tab

64
00:02:54,880 --> 00:02:57,560
here and I'm going to
call the tap food.

65
00:02:57,560 --> 00:02:59,940
It's going to be the first class

66
00:02:59,940 --> 00:03:02,430
we are going to be writing.

67
00:03:02,540 --> 00:03:06,330
This class for now,

68
00:03:06,330 --> 00:03:08,350
it's going to be rather simple.

69
00:03:10,940 --> 00:03:15,700
Let's define its constructor.

70
00:03:30,700 --> 00:03:33,640
We're going to have a
position that could be

71
00:03:33,640 --> 00:03:41,660
just position and
then the food size.

72
00:03:44,510 --> 00:03:47,060
As we have done with particles,

73
00:03:47,060 --> 00:03:52,500
we will have a
reference to all foods.

74
00:03:54,080 --> 00:03:56,600
I'm skipping ahead a little bit.

75
00:03:56,600 --> 00:03:58,540
But what we're doing
is creating a position

76
00:03:58,540 --> 00:04:00,965
and a size for this food entity.

77
00:04:00,965 --> 00:04:03,520
This part, we could actually
write it a little bit later,

78
00:04:03,520 --> 00:04:06,980
but we'll actually
maybe start here.

79
00:04:07,210 --> 00:04:14,100
Let's do as we do equalize
some of these positions to.

80
00:04:17,390 --> 00:04:21,015
There constructure counterpart.

81
00:04:21,015 --> 00:04:26,865
The food size as such.

82
00:04:26,865 --> 00:04:28,490
Then as we have done before,

83
00:04:28,490 --> 00:04:30,830
let's just create a function,

84
00:04:30,830 --> 00:04:32,690
which we'll call run,

85
00:04:32,690 --> 00:04:34,350
which is going to
be a shortcut for

86
00:04:34,350 --> 00:04:36,415
all the main functions.

87
00:04:36,415 --> 00:04:40,185
What I want to write here
is a function for grow,

88
00:04:40,185 --> 00:04:43,390
and a function for display.

89
00:04:47,680 --> 00:04:50,030
Let's write the
display function,

90
00:04:50,030 --> 00:04:52,250
which is the simplest one.

91
00:04:52,250 --> 00:04:59,255
Let's define display as self.

92
00:04:59,255 --> 00:05:05,075
Then we're going to
do fill, 0, 255.

93
00:05:05,075 --> 00:05:09,080
You can here's some green color,

94
00:05:09,080 --> 00:05:14,580
no stroke, and an ellipse.

95
00:05:16,540 --> 00:05:19,460
Let's copy paste this.

96
00:05:19,460 --> 00:05:21,650
We did a description
a little bit longer

97
00:05:21,650 --> 00:05:25,890
for position.x, position.y.

98
00:05:25,930 --> 00:05:29,870
The size, we're going to
use it for the size of

99
00:05:29,870 --> 00:05:35,600
this ellipse both the x and y.

100
00:05:35,600 --> 00:05:39,540
Nothing really fancy yet,

101
00:05:39,610 --> 00:05:43,985
and we could actually call
already the display function.

102
00:05:43,985 --> 00:05:48,840
Let's replace this
comment, so self.display.

103
00:05:52,690 --> 00:05:55,830
Great. We have our food.

104
00:05:56,290 --> 00:06:00,275
Sorry about that. Great.
We have our food.

105
00:06:00,275 --> 00:06:04,330
I'm not going to have,

106
00:06:04,330 --> 00:06:09,520
in this case, the food called
directly into the canvas.

107
00:06:09,520 --> 00:06:10,910
As a matter of fact,

108
00:06:10,910 --> 00:06:13,650
this is probably a line
that you shouldn't have.

109
00:06:14,770 --> 00:06:17,135
We want to create a world class,

110
00:06:17,135 --> 00:06:20,405
something that would
hold the collections.

111
00:06:20,405 --> 00:06:25,265
We're going to do
it as a new tap.

112
00:06:25,265 --> 00:06:27,920
As we have done vector
fields in the past,

113
00:06:27,920 --> 00:06:30,965
we're going to do world class.

114
00:06:30,965 --> 00:06:35,040
We're going to call
this the World_Manager,

115
00:06:37,060 --> 00:06:40,115
and let's just write
our world class.

116
00:06:40,115 --> 00:06:43,685
The first thing that
our world will have is

117
00:06:43,685 --> 00:06:49,110
the class called World_Manager.

118
00:07:00,130 --> 00:07:05,070
Let's define its construction.

119
00:07:10,510 --> 00:07:12,680
Here, I'm going to
pass the variable,

120
00:07:12,680 --> 00:07:16,850
so how big the canvas of the
screen is for the world to

121
00:07:16,850 --> 00:07:22,050
be aware of a certain
graphic, main.

122
00:07:47,290 --> 00:07:51,065
Here, the manager will be

123
00:07:51,065 --> 00:07:55,380
the entity that will be
able to create food.

124
00:07:55,390 --> 00:07:58,925
For now, it's just probably
manage the collections.

125
00:07:58,925 --> 00:08:04,800
It will have internally
list of all the food,

126
00:08:10,270 --> 00:08:13,595
so all the entities
from the food class.

127
00:08:13,595 --> 00:08:16,940
Being aware that
the manager eats

128
00:08:16,940 --> 00:08:19,655
a class that will interact
with the food class,

129
00:08:19,655 --> 00:08:26,360
we're going to import
from the food file,

130
00:08:26,360 --> 00:08:29,900
import the class, food.

131
00:08:29,900 --> 00:08:32,390
Also, let's import

132
00:08:32,390 --> 00:08:36,510
random to be able to
work with random.

133
00:08:38,500 --> 00:08:41,570
Similarly, what we have
done with the food class,

134
00:08:41,570 --> 00:08:43,085
we're going to create
a run function,

135
00:08:43,085 --> 00:08:46,340
which is going to be shortcut

136
00:08:46,340 --> 00:08:51,510
for all the runtime
functions, so self.

137
00:08:52,210 --> 00:08:55,850
What we're going to do
with the World_Manager,

138
00:08:55,850 --> 00:09:06,125
the manager will create food
over time and run the food.

139
00:09:06,125 --> 00:09:09,600
Just call the run function

140
00:09:10,480 --> 00:09:13,595
for each one of the collection.

141
00:09:13,595 --> 00:09:17,480
We're going to do that for
other entities in this world.

142
00:09:17,480 --> 00:09:20,975
Let's start with the food.

143
00:09:20,975 --> 00:09:23,915
The creation of the food

144
00:09:23,915 --> 00:09:28,980
would be something
like create food.

145
00:09:30,740 --> 00:09:33,240
Let's define a rate of

146
00:09:33,240 --> 00:09:35,895
creation. It's something
that is going to happen.

147
00:09:35,895 --> 00:09:39,465
If we're adding the creation
of the food in the run,

148
00:09:39,465 --> 00:09:42,360
that means that we're
constantly creating food.

149
00:09:42,360 --> 00:09:44,250
This could be a function
of food itself.

150
00:09:44,250 --> 00:09:45,450
We could start with, let's say,

151
00:09:45,450 --> 00:09:48,935
just two or three nodes of
food and those food can

152
00:09:48,935 --> 00:09:53,030
pollinate and potentially
create new food sources.

153
00:09:53,030 --> 00:09:56,000
They could have its own
internal cycle of reproduction.

154
00:09:56,000 --> 00:09:58,885
But for now, just we're
going to keep it simple.

155
00:09:58,885 --> 00:10:02,445
Out of this world, there's
going to be an emergence of

156
00:10:02,445 --> 00:10:06,245
food supply that is going
to have its own cadence,

157
00:10:06,245 --> 00:10:09,965
its own rhythm to exist.

158
00:10:09,965 --> 00:10:12,305
Let's create food.

159
00:10:12,305 --> 00:10:18,300
We're going to use that
rate in an if frame count.

160
00:10:22,280 --> 00:10:25,275
If the frame count
equals the rate.

161
00:10:25,275 --> 00:10:26,355
This is a technique that we've

162
00:10:26,355 --> 00:10:28,245
done already a couple times.

163
00:10:28,245 --> 00:10:30,540
This modular function is

164
00:10:30,540 --> 00:10:33,330
used in conjunction
with equal zero,

165
00:10:33,330 --> 00:10:36,390
meaning that are we
hitting the exact rate?

166
00:10:36,390 --> 00:10:37,635
If that rate is five,

167
00:10:37,635 --> 00:10:40,080
does five fits perfectly
in frame count?

168
00:10:40,080 --> 00:10:43,390
Every five frames,
we're doing something.

169
00:10:45,020 --> 00:10:47,535
If so, we need an x variable,

170
00:10:47,535 --> 00:10:49,650
which is a random.uniform

171
00:10:53,870 --> 00:10:59,590
from zero to self.size_x.

172
00:11:03,140 --> 00:11:07,000
Let's copy all that for y.

173
00:11:17,810 --> 00:11:20,655
Create a bit more space.

174
00:11:20,655 --> 00:11:29,100
Now we could say that the
position equals p vector x, y.

175
00:11:29,100 --> 00:11:33,540
The new food would be equals

176
00:11:33,540 --> 00:11:38,745
to one entity of the food
class with a position,

177
00:11:38,745 --> 00:11:41,055
a size of five,

178
00:11:41,055 --> 00:11:43,110
and that's it for now,

179
00:11:43,110 --> 00:11:46,750
actually, and self.all_food.

180
00:11:50,120 --> 00:11:52,260
We're going to append.

181
00:11:52,260 --> 00:11:54,300
We're adding to the
list of all food,

182
00:11:54,300 --> 00:11:57,070
the new food item
that we just created.

183
00:11:57,800 --> 00:12:00,750
That's the creation of the food.

184
00:12:00,750 --> 00:12:03,630
The rate, we cannot do this too

185
00:12:03,630 --> 00:12:05,160
quickly because we
will end up with

186
00:12:05,160 --> 00:12:07,635
too many food items
in the screen.

187
00:12:07,635 --> 00:12:10,455
When we call this function,

188
00:12:10,455 --> 00:12:15,790
create food, let's just
do it every 50 frames.

189
00:12:21,320 --> 00:12:24,340
Self.create_food.

190
00:12:24,770 --> 00:12:28,830
Every 50 frames we create
one new food element,

191
00:12:28,830 --> 00:12:30,810
and now let's just also

192
00:12:30,810 --> 00:12:33,150
add the function for
running the food,

193
00:12:33,150 --> 00:12:38,950
so if run_food.

194
00:12:41,420 --> 00:12:49,120
This is for an entity
f in all_food.

195
00:12:50,210 --> 00:12:53,500
Let's f.run.

196
00:12:54,770 --> 00:12:58,050
Then now this function which

197
00:12:58,050 --> 00:13:02,620
executes all the food
collection that we have.

198
00:13:06,740 --> 00:13:12,060
Basically, we have a world
that contains the food list.

199
00:13:12,060 --> 00:13:14,385
We have a function that
creates some food,

200
00:13:14,385 --> 00:13:16,590
and we have a function
that just make sure

201
00:13:16,590 --> 00:13:18,900
that we call the run function
within all this food.

202
00:13:18,900 --> 00:13:23,850
The food class here,

203
00:13:23,850 --> 00:13:25,845
currently, is just a display.

204
00:13:25,845 --> 00:13:28,350
It's a glorified ellipse,

205
00:13:28,350 --> 00:13:31,065
that it's a green ellipse
that doesn't do much.

206
00:13:31,065 --> 00:13:33,360
We're going to add a few
more lines here just to

207
00:13:33,360 --> 00:13:35,790
have our base food
class working,

208
00:13:35,790 --> 00:13:38,410
but let's see if we're
running into errors.

209
00:13:41,270 --> 00:13:43,740
Well, we don't seem to have

210
00:13:43,740 --> 00:13:45,645
an error because we're not
calling the world yet.

211
00:13:45,645 --> 00:13:48,180
We're not constructing a
version of this world.

212
00:13:48,180 --> 00:13:50,620
Let's just import it

213
00:13:58,300 --> 00:14:01,620
from world manager.

214
00:14:02,410 --> 00:14:05,295
That's the file.

215
00:14:05,295 --> 00:14:08,410
Let's import world manager.

216
00:14:13,460 --> 00:14:15,780
With that in mind, we can create

217
00:14:15,780 --> 00:14:19,360
a new world now, so my world.

218
00:14:20,360 --> 00:14:27,605
It's going to be world
manager between the Canvas.

219
00:14:27,605 --> 00:14:29,410
Let's just use these
variables here.

220
00:14:29,410 --> 00:14:31,330
This is going to be
the information of

221
00:14:31,330 --> 00:14:35,465
the Canvas width
and Canvas height,

222
00:14:35,465 --> 00:14:37,815
that is going to be
passed on to the world

223
00:14:37,815 --> 00:14:41,070
in case the world needs
that information.

224
00:14:41,070 --> 00:14:48,370
Finally, we can
call the world.run.

225
00:14:55,050 --> 00:14:57,070
We are running into some issues.

226
00:14:57,070 --> 00:14:58,930
Let's see the mistakes before we

227
00:14:58,930 --> 00:15:02,840
actually execute this correctly.

228
00:15:02,910 --> 00:15:05,050
I found a few errors.

229
00:15:05,050 --> 00:15:08,080
I think I was missing
a self.all_food here,

230
00:15:08,080 --> 00:15:12,200
and I think we had, like,
a c instead of an x here.

231
00:15:13,260 --> 00:15:18,310
Just a few small
mistakes here and there.

232
00:15:18,310 --> 00:15:21,895
But we should have
now our world,

233
00:15:21,895 --> 00:15:24,415
as you can see, gradually grows.

234
00:15:24,415 --> 00:15:28,570
If this dots are too
small for your screen,

235
00:15:28,570 --> 00:15:31,250
I think we can just
make them bigger,

236
00:15:31,260 --> 00:15:36,440
which is 15 for the food size.

237
00:15:37,200 --> 00:15:39,760
These are too big. I'm just

238
00:15:39,760 --> 00:15:41,785
going to keep them
somewhere in 10 or so.

239
00:15:41,785 --> 00:15:47,420
We have our food class
appearing on the screen.

240
00:15:47,610 --> 00:15:50,365
Let's just wrap it up with
just making sure that

241
00:15:50,365 --> 00:15:53,380
the food has a bit
of functionality,

242
00:15:53,380 --> 00:15:56,770
which is this grow function
that we discussed.

243
00:15:56,770 --> 00:16:00,715
The growth function is
actually rather simple.

244
00:16:00,715 --> 00:16:09,820
We need to give a
variable of age.

245
00:16:09,820 --> 00:16:14,290
It's going to be
zero, self.lifespan.

246
00:16:14,290 --> 00:16:18,085
It's going to be let's say 400,

247
00:16:18,085 --> 00:16:28,240
and we can create

248
00:16:28,240 --> 00:16:38,930
the function grow, by

249
00:16:40,290 --> 00:16:42,880
just increasing the age.

250
00:16:42,880 --> 00:16:46,900
Self.age += 1.

251
00:16:50,580 --> 00:16:53,980
We can make the die
function within this,

252
00:16:53,980 --> 00:16:58,075
which is if the age gets
above the lifespan,

253
00:16:58,075 --> 00:17:01,435
we can kill the food item.

254
00:17:01,435 --> 00:17:03,415
We're going to do
that maybe later.

255
00:17:03,415 --> 00:17:04,900
The only thing I want
to conclude with

256
00:17:04,900 --> 00:17:06,370
is let's just try to map

257
00:17:06,370 --> 00:17:10,710
the age of this food item,

258
00:17:10,710 --> 00:17:12,930
to the decoloring of.

259
00:17:12,930 --> 00:17:16,200
We can actually see dynamically
a little bit of this age.

260
00:17:16,200 --> 00:17:19,420
We can say that the
green color would be

261
00:17:19,420 --> 00:17:24,620
a map of the self.age.

262
00:17:30,390 --> 00:17:35,390
That goes between zero
and the lifespan.

263
00:17:39,960 --> 00:17:44,155
That will be mapped
to a value of,

264
00:17:44,155 --> 00:17:45,700
if the age is zero,

265
00:17:45,700 --> 00:17:47,890
meaning it's very young,

266
00:17:47,890 --> 00:17:50,740
it's going to be 255,
meaning very bright,

267
00:17:50,740 --> 00:17:52,600
and if it's get older and older,

268
00:17:52,600 --> 00:17:56,035
it's going to go all
the way down to 50,

269
00:17:56,035 --> 00:18:00,910
and we can use this
g value for green,

270
00:18:00,910 --> 00:18:05,900
in the green channel
of the food item.

271
00:18:06,450 --> 00:18:12,980
The final thing is let's make
sure that we call the grow.

272
00:18:14,550 --> 00:18:16,990
This grow function is so small,

273
00:18:16,990 --> 00:18:20,110
but rather we'll continue
expanding upon it.

274
00:18:20,110 --> 00:18:21,760
That's why actually,
I ain't just leaving

275
00:18:21,760 --> 00:18:23,350
one line for the grow.

276
00:18:23,350 --> 00:18:26,500
What it represents is
the grow of age of

277
00:18:26,500 --> 00:18:29,920
this food item. Let's
see what we have.

278
00:18:29,920 --> 00:18:32,200
We have this entity,

279
00:18:32,200 --> 00:18:36,775
and you can see the newer
entries are very bright,

280
00:18:36,775 --> 00:18:39,025
but then they gradually decay.

281
00:18:39,025 --> 00:18:42,070
There's this sense of growing

282
00:18:42,070 --> 00:18:44,050
older and they decay over time.

283
00:18:44,050 --> 00:18:47,005
We're starting to have some
information that we can use.

284
00:18:47,005 --> 00:18:50,395
Maybe herbivores
might be looking for

285
00:18:50,395 --> 00:18:55,150
plants that are within a
certain range of growth.

286
00:18:55,150 --> 00:18:58,495
Meaning, like, some of
the better tasting ones.

287
00:18:58,495 --> 00:19:00,490
There's a lot of decisions
that we can do when we start

288
00:19:00,490 --> 00:19:03,550
introducing this information
within our classes.

289
00:19:03,550 --> 00:19:05,140
We're going to
continue working on

290
00:19:05,140 --> 00:19:07,030
the different classes
in this ecosystem,

291
00:19:07,030 --> 00:19:09,050
so I'll see you in
the next video.