WEBVTT

﻿1
00:00:00.000 --> 00:00:02.360
Hello, welcome to Scripting for Artists.

2
00:00:02.460 --> 00:00:06.380
My name is Sybren, and today we will look at for and while loops.

3
00:00:06.780 --> 00:00:10.500
On Twitter Roger asked, I see you have for loops.

4
00:00:10.640 --> 00:00:12.820
When is it better to use while loops instead?

5
00:00:13.260 --> 00:00:16.240
I think it's a very good question, so let's take a look at that.

6
00:00:16.620 --> 00:00:20.020
So in this video first we will look at for loops and while loops.

7
00:00:20.060 --> 00:00:20.820
How did it work?

8
00:00:20.980 --> 00:00:22.460
What's the difference between them?

9
00:00:23.420 --> 00:00:27.500
We've seen for loops before, so we're going to take another look at while loops

10
00:00:27.501 --> 00:00:31.238
to see several reasons why you would use them, and I

11
00:00:31.239 --> 00:00:34.100
will go over a few more ways to control your loops.

12
00:00:34.780 --> 00:00:38.580
Because the question is a bit more abstract, we will start in a more abstract way.

13
00:00:39.000 --> 00:00:42.320
In a few minutes we will look at a concrete example that combines both a for

14
00:00:42.321 --> 00:00:44.847
and while loop, but first let's take a look at

15
00:00:44.848 --> 00:00:47.721
both of them side by side and see how they differ.

16
00:00:48.500 --> 00:00:51.452
We've seen a bunch of for loops already, so

17
00:00:51.453 --> 00:00:55.341
they look like for thing and bunch of things.

18
00:00:57.760 --> 00:01:02.921
And a while loop is slightly different, it's simpler and it looks a bit like an if.

19
00:01:07.260 --> 00:01:09.675
The for loop iterates over a bunch of things,

20
00:01:09.676 --> 00:01:12.780
and iterating basically means asking next please.

21
00:01:13.640 --> 00:01:17.640
It works well when you have a sequence of things, like the selected objects or the

22
00:01:17.641 --> 00:01:21.340
numbers 0 to 600, like we saw in the grid of monkeys.

23
00:01:21.920 --> 00:01:23.260
The while loop is more primitive.

24
00:01:23.460 --> 00:01:27.240
Instead of asking next please and expecting Python to understand and provide

25
00:01:27.241 --> 00:01:30.480
the next thing, it asks should I keep looping?

26
00:01:30.880 --> 00:01:32.848
And this is very useful when you want to keep

27
00:01:32.849 --> 00:01:35.921
repeating until you are at a certain point.

28
00:01:36.200 --> 00:01:38.664
Another way to think of it, as I mentioned already, it looks

29
00:01:38.665 --> 00:01:41.800
like an if, and it's basically a repeating if statement.

30
00:01:43.040 --> 00:01:44.864
So you've already seen plenty of examples

31
00:01:44.865 --> 00:01:46.780
of for loops, so let's look at a while loop.

32
00:01:47.520 --> 00:01:53.660
Let's say you want to simplify the mesh until it has 10,000 vertices or more.

33
00:01:54.380 --> 00:01:55.900
So this will be one way to do it.

34
00:01:55.920 --> 00:01:57.920
We can first start looking at the mesh,

35
00:02:01.190 --> 00:02:07.910
which is given to us by bpy context, active object dot data.

36
00:02:09.210 --> 00:02:13.054
And mesh has vertices, and we can inspect the

37
00:02:13.055 --> 00:02:16.050
length of that to get the number of vertices.

38
00:02:16.051 --> 00:02:19.650
So in this case Suzanne has 507 vertices.

39
00:02:20.330 --> 00:02:23.322
To subdivide we need to go to edit mode, but object dot

40
00:02:23.323 --> 00:02:26.390
data is only updated after we go out of edit mode again.

41
00:02:26.830 --> 00:02:29.170
So this means our code has to do the following.

42
00:02:31.850 --> 00:02:36.097
First we go to edit mode, then everything is selected

43
00:02:36.098 --> 00:02:39.111
now, but just to be sure we select everything.

44
00:02:40.790 --> 00:02:45.910
Then we subdivide, and then we go back to object mode.

45
00:02:46.590 --> 00:02:50.650
And now when we look at len mesh dot vertices, we can see that it has

46
00:02:50.651 --> 00:02:54.130
increased, because the edit data has been flushed back to the actual mesh.

47
00:02:55.470 --> 00:02:56.770
So let's put this in a script.

48
00:02:57.570 --> 00:02:58.850
Let's get rid of this.

49
00:02:59.910 --> 00:03:02.830
Start with import bpy and start by getting the mesh.

50
00:03:04.230 --> 00:03:09.610
And then what I always do, well not always, but what I sometimes do when I'm

51
00:03:09.611 --> 00:03:12.185
not too sure about my while loop, because

52
00:03:12.186 --> 00:03:14.410
there is a risk that you get an infinite loop.

53
00:03:14.870 --> 00:03:18.480
If you say while true, well true is always true,

54
00:03:18.481 --> 00:03:21.651
and code here will just keep on repeating forever.

55
00:03:22.710 --> 00:03:25.010
That's not so nice, because it will actually hang blunder.

56
00:03:26.510 --> 00:03:28.790
So instead of while, write if.

57
00:03:31.900 --> 00:03:40.520
So if the number of vertices is less than 10,000, we need to do a subdivision.

58
00:03:41.040 --> 00:03:43.860
And for now we can just test one subdivision.

59
00:03:44.220 --> 00:03:47.074
And if that works, we can change the f to a

60
00:03:47.075 --> 00:03:51.081
while and have a loop until we need to stop.

61
00:03:51.460 --> 00:03:53.500
So we need to go to edit mode.

62
00:03:53.980 --> 00:03:58.460
So hover there, ctrl C and ctrl V.

63
00:03:59.600 --> 00:04:04.060
Then once in edit mode we need to select everything just to be sure.

64
00:04:04.280 --> 00:04:07.340
Hover and ctrl C, then here ctrl V.

65
00:04:12.900 --> 00:04:18.260
Then do the subdivision, hover, ctrl C, there ctrl V.

66
00:04:19.460 --> 00:04:22.140
And then we go back to object mode.

67
00:04:26.470 --> 00:04:28.130
And this should work.

68
00:04:28.170 --> 00:04:28.890
Famous last word.

69
00:04:29.010 --> 00:04:32.370
So we start with the object in object mode.

70
00:04:35.440 --> 00:04:39.260
And there you see, it has done one level of subdivision and we can keep going.

71
00:04:39.960 --> 00:04:42.840
And now you can see that the code no longer works.

72
00:04:43.340 --> 00:04:44.360
And why is that?

73
00:04:44.980 --> 00:04:50.660
Well, the number of vertices has gone over 10,000 and it will stop subdividing.

74
00:04:51.380 --> 00:04:58.500
And this tells us that once we change the f to a while, it will also stop.

75
00:05:01.060 --> 00:05:03.300
As you can see, the code doesn't do anything.

76
00:05:04.040 --> 00:05:08.520
And that means this condition is checked first.

77
00:05:08.940 --> 00:05:10.860
So it's at the top of the loop.

78
00:05:11.380 --> 00:05:13.400
So it makes sense that it's also checked first.

79
00:05:14.420 --> 00:05:15.480
So first is the check.

80
00:05:15.740 --> 00:05:18.800
If the check is true, then there's a loop iteration.

81
00:05:18.801 --> 00:05:20.880
Then again, there's a check.

82
00:05:21.160 --> 00:05:24.580
If the check is true, there's another loop iteration and so on.

83
00:05:25.160 --> 00:05:30.760
So let's throw out this Suzanne and add a new one.

84
00:05:31.340 --> 00:05:36.560
Now we'll click once and immediately we end up with the final subdivision level.

85
00:05:37.120 --> 00:05:40.880
So this is how you can use while to loop until some condition is met.

86
00:05:41.480 --> 00:05:44.540
So I already mentioned that it's possible to create endless loops.

87
00:05:44.840 --> 00:05:48.680
And I will show you a way to control the number of iterations.

88
00:05:48.681 --> 00:05:50.080
As a sort of safety net.

89
00:05:50.780 --> 00:05:53.660
And this may not be useful for your situation and maybe overkill.

90
00:05:53.720 --> 00:05:56.080
But it's a nice tool to have in your toolbox anyway.

91
00:05:57.180 --> 00:05:59.700
So what we want to limit is the number of subdivisions.

92
00:06:00.380 --> 00:06:02.260
So just let's keep count of them.

93
00:06:03.860 --> 00:06:05.240
We start counting at zero.

94
00:06:06.900 --> 00:06:08.440
We keep the code as it is for now.

95
00:06:08.500 --> 00:06:11.260
And then here at the end we say.

96
00:06:13.100 --> 00:06:14.700
Subdivs plus equals one.

97
00:06:15.280 --> 00:06:20.401
And what this means is that after the subdivision is done, one is added to subdivs.

98
00:06:20.460 --> 00:06:22.120
And we keep looping.

99
00:06:23.320 --> 00:06:24.360
So far we only count.

100
00:06:24.500 --> 00:06:25.820
We don't respond to it yet.

101
00:06:25.860 --> 00:06:28.600
The loop doesn't break when subdivs get too big.

102
00:06:29.360 --> 00:06:34.260
So it needs to keep looping while the number of vertices is still too small.

103
00:06:34.320 --> 00:06:35.320
Of course.

104
00:06:39.120 --> 00:06:40.160
And while...

105
00:06:40.700 --> 00:06:42.840
I will make this a little bit smaller.

106
00:06:44.320 --> 00:06:46.520
While subdivs is less than three.

107
00:06:47.560 --> 00:06:49.660
So now it will only subdivide three times.

108
00:06:49.900 --> 00:06:52.580
For subdivs it's zero, one and two.

109
00:06:53.820 --> 00:06:56.400
All of those times subdivs is smaller than three.

110
00:06:57.020 --> 00:07:00.120
And once we've done the third, subdivs will be three.

111
00:07:00.240 --> 00:07:01.520
Which means the loop will break.

112
00:07:02.200 --> 00:07:04.317
So now that we have a situation where we're counting

113
00:07:04.318 --> 00:07:07.200
things, we can actually rewrite this to a for loop.

114
00:07:07.580 --> 00:07:10.020
And much the same way we did when creating the monkey grid.

115
00:07:11.140 --> 00:07:15.400
So instead of keeping track of the number of subdivisions ourselves.

116
00:07:15.720 --> 00:07:19.580
We can say for subdivs in range three.

117
00:07:21.180 --> 00:07:24.200
And this will only do it three times.

118
00:07:25.500 --> 00:07:27.737
So the only thing we need to do now is stop

119
00:07:27.738 --> 00:07:30.761
early if the number of vertices is big enough.

120
00:07:31.300 --> 00:07:35.760
So instead of saying while the number of vertices is smaller than a certain number.

121
00:07:35.761 --> 00:07:44.660
We say if the number of vertices is bigger than or equal to that number.

122
00:07:44.700 --> 00:07:46.580
So we flip the condition.

123
00:07:48.740 --> 00:07:49.840
We break out of the loop.

124
00:07:50.560 --> 00:07:53.940
And break means just stop right now with that loop.

125
00:07:54.100 --> 00:07:56.260
Don't execute anything else in that body.

126
00:07:56.540 --> 00:07:57.840
Break out of it.

127
00:08:00.760 --> 00:08:02.040
And then we can remove this.

128
00:08:02.120 --> 00:08:03.340
We can remove this.

129
00:08:04.140 --> 00:08:05.480
And here we have our code again.

130
00:08:06.120 --> 00:08:09.300
So we replaced a while with a for.

131
00:08:09.500 --> 00:08:11.860
We moved the condition from a while into an if.

132
00:08:12.680 --> 00:08:16.260
And the for makes sure that this only happens three times.

133
00:08:16.580 --> 00:08:18.560
So let's take a look at what that looks like.

134
00:08:21.940 --> 00:08:23.260
Let's start with a fresh Suzanne.

135
00:08:25.820 --> 00:08:30.160
And we can't reuse this mesh because that still refers to the old one.

136
00:08:30.161 --> 00:08:39.280
So let's say len context.object.data .vertices 507.

137
00:08:40.060 --> 00:08:42.000
And we execute this code now.

138
00:08:44.520 --> 00:08:47.320
And now we can see that the result is exactly the same.

139
00:08:47.520 --> 00:08:51.340
Which we kind of expected because it reached the limit of the number of

140
00:08:51.341 --> 00:08:53.462
vertices before it reached the limit of the

141
00:08:53.463 --> 00:08:55.880
number of subdivisions it was allowed to do.

142
00:08:56.180 --> 00:08:58.840
So let's try with a fresh Suzanne.

143
00:08:59.580 --> 00:09:03.540
And set this limit to a million.

144
00:09:04.280 --> 00:09:07.858
It probably won't reach a million vertices in three

145
00:09:07.859 --> 00:09:11.160
subdivisions so we should end up with something less.

146
00:09:13.540 --> 00:09:16.100
And there we are exactly the same result again.

147
00:09:16.780 --> 00:09:19.840
Let's increase the limit of the number of subdivisions.

148
00:09:23.060 --> 00:09:24.000
Start with a fresh Suzanne.

149
00:09:24.001 --> 00:09:33.040
And it has done one subdivision more but it did not reach that million because we

150
00:09:33.041 --> 00:09:36.000
had a limit on the number of subdivisions it was allowed to do.

151
00:09:36.740 --> 00:09:41.180
So this is another way you can rewrite your while loop into a for loop and an if.

152
00:09:41.780 --> 00:09:45.120
And then you have a limit on the number of iterations that it does.

153
00:09:46.200 --> 00:09:48.820
So this is it for this episode of Scripting for Artists.

154
00:09:48.920 --> 00:09:50.750
If you have any questions or remarks please

155
00:09:50.751 --> 00:09:53.361
leave a comment below and I will see you soon.


