 because it will be quite boring and I don't want to fall asleep during the presentation. This is a little bit about game programming and closures, but don't expect too much game programming or too much closure. This is just about the central part of a game's architecture, which is generally called the main loop. Or in similar interactive applications, you can also call it event loop. If you look at a typical game, what happens is something like a ripple, something like a loop where we see something or we perceive something, we hear something and then we react to it. And then based on our reactions, computer does some more calculations and then shows us something or plays a different sound and then we react again and so on and so forth, we keep looping through these events. If we take the simplest possible loop, but not maybe the most useful loop, but actually in practice quite commonly used loop, it looks like something a little bit like this, where update is basically changing our current state to a new state and then render is presenting the new state to the player. And this dt is the time delta. So every time this main loop, this function that is called, main loop is called, every time we need to know how much time has passed between the last call and this current call. But this one, since we are closure programmers and functional programmers, this one of course implies state. So my world is somewhere else and I am mutating it through some other means. If we improve on this and pass the world to our main loop now, we first call the update function with the old world to compute the new world. We render based on the new world and then we return the new world so that we leave keeping track of the new world to whoever is calling this main loop. This one is better, but user inputs are missing. So user inputs are kind of like a side effect in terms of input. If we improve it a little more, this time our main loop function can take the old world, the events since the last invocation and the delta time, then compute given the world events and dt to update function, the new world. At this point in time, we can forget about the events until the loop is called next. We have already consumed them, we are done with them. Then we render our world and then return the new world. This is a simple structure of the main loop. So games are supposed to be fun and they are supposed to be responsive to our actions. So maybe not the gold standard, but usually what is expected is that the game runs at 60 frames per second or more or less depending on the game. If you are building a roguelike, you may be okay with one frame per second or less. But usually you are aiming to go 60 frames per second, which means if a second is a thousand milliseconds, which means you need to be done with all this, generating the events, basically the entire call of main loop should complete within 16 milliseconds, which is not a lot of time, especially if your code is not optimized. So before I move on, I just want to illustrate what I mean by this. Let's take a 16 millisecond chunk. We haven't done anything yet. We first, we call our main loop. We call our update and let's suppose our update takes 5 milliseconds. So almost half of our allocation, time allocation is already gone. And then we call the render. Let's say it takes 3 milliseconds. So within 8 milliseconds, we are done. This is a happy scenario. But in another frame, maybe our update took less time, but render still hasn't finished when we have used up our allocation of 16 milliseconds. And then it goes to the next frame. It's still rendering. And then at some point in the next frame, it is done with the rendering. So what happens in this kind of design is we skip one frame. And if we keep skipping frames, the animations, the visual effect of the game will not be smooth. And also we skip updating our world, but that is less of a problem. How to approach this? I'm just going to ask the questions, not provide answers at this point. We can try scheduling an update right after render. In the first 16 millisecond slot, it ended up early, right? I can, without waiting for the empty slot, without waiting for the next 16 seconds, I can just call my update. In this case, I will be calling, most probably calling update more frequently. But it also has a downtime where you are also calling your render at unstable rates, sometimes faster, sometimes slower. So you're not fixing on your frame rate. The second consideration is we can try running our render and update in separate threads so that they don't compete for the limited time. But then they will be competing on the world because they both depend on world. So while update is updating, changing the world, render will try rendering the world at the same time. So we are a little bit closer to get this right. If we use a persistent data structure, we can give render the previous version while we are generating the newer version. But if you are building a game and you want to have a high frame rate, maybe the persistent data structures are not for you, maybe. So how do we do things? Simple case is how do we know what time is it now? This is very basic. System is some Java lang system. I think it will get imported in the closure environment. You can just call it like this. And it is going to give you the time as some sort of integer. I don't remember if it's int or not, but it's an integer number. Yes, okay. But usually you don't want a millisecond precision time. You want time with more precision. So instead you can call nano time and then it will give you a double and then divide it by a million to get the milliseconds. But these milliseconds will also have the fractions. The previous code we were just looking at what time is it now? What this structure does is it gives you a function and each time you call the function, it will give you a number that is the milliseconds past since the last invocation of the function. Anything interesting here? I'm looking, nothing interesting. On the contrary, I am not able to find, since I'm using an atom, I need to use swap, right? I'm not able to find a way to write this with swap. So I'm just using atom as a synchronized dump, like an atomic integer kind of thing. And the usage is I first call this function, I get another function, then I keep calling that function and every time I call, it gives me the time past since the last invocation or the generation. Here it is after emoking this, it is 0.12, something, something milliseconds. And I sleep for 1000 milliseconds. Then it gives me a delta time like 1000 plus plus milliseconds. And yes, here we can also use integers long, something like that. But it depends on whether you want to measure time precisely, how precisely. How do we exit the game? Again, I propose a simple way to do that. We can just use a promise and then check whether this promise is somewhat delivered or not. And then when I want to exit, I will just deliver the promise anything. It can be nil, it can be something else. And then the next time my main loop will be called, it will check for this and then exit if necessary. By the way, both the DTFN and this exit mechanism is thread safe. So there are also ways to do it without being thread safe. In the first section, we looked at the main loop, which is about your game. This is about calling that main loop and using all these other pieces that we just looked at to make it a sensible main loop. Coming back to the other 60 FPS discussion, there are two concepts that are kind of racing against each other. One is the update rate and one is the frame rate and they have different effects. Frame rate should be stable, but if it can be degraded as well or it can be higher, it will impact the experience of the player. Updates also should be stable, but not necessarily they are synchronized together. Most important thing is, since we are not looking on a particular frame rate or update rate, because it's not guaranteed in any way, especially in the update case, updates shouldn't depend on what time is it now. Updates should depend on rather how much time has passed or they shouldn't depend on how many times I have been called. For example, if I'm making something work, it shouldn't work according to just its speed and assuming that how many times I will update, divide it by this much and then every time step this much. Instead, it should look at the delta time and the speed and then calculate how much it should advance. And actually, suppose if it's a very fast moving object between the two calls to update, it may go through its target. Let's say I'm firing a bullet, it's supposed to hit something, I call update here, I call update here, I miss my target. So in those cases, what we want to do is we want to subsample. If it moves from here to here, I want to subsample the path a few times, maybe three, four times, to see whether it had hit the target in between my two calls of update. Last thing is, what I said earlier, it is likely that you will want mutability in your world to update it faster. And then the problem comes if you run your render thread in a separate thread. One potential solution, which is not ideal solution is to do double frame. You can have two worlds and if you have a fast way to copy one into another, you can have two worlds, you can update this one and then render this one and then start updating this one with the previous frame and the next frame or copy this one to this. And then you can swap what are you doing with which one, update render, update render and so on. But you need to have a fast copy. Okay, code example, this is a tight loop and it will never terminate. I generate my delta time, I create my world, I get my event somehow magically. And then I get my delta time and then I call my main loop, it gives me back the new world and then I loop. And this doesn't give the other threads to space to breathe. We can make a small change to this to allow the other threads, if there are any other threads, to get a chance to use the same core that this main thread is using by just calling yield on thread. By the way, this yielding is only at the JVM level, not on the OS level. On the OS level, if you are running other programs, other processes, they are fine. But on the JVM, if I don't yield and if I'm using all the cores, then some of the other threads will never get a chance to work. And the final step is to make it terminate. Just the same code that I showed earlier. I have my escape hatch. Again, I call my main loop, pass my escape hatch. I'm not changing my main loop. The only thing I expect from the main loop is that it's some point when it's time to finish to deliver this promise. And then I check if it is delivered. If it is delivered, this closure will end. If it is not, it will recur. Good question. Why do you have an escape hatch that's set for... Instead of like an exception. Well, no, can it be in the world state, like game over or state of the world? Yes, yes. It can be very, very, very fair. So for example, this is a very, very simple example. For example, I would rather not mix my, say, screen resolution, screen width and height, for example, or my audio level volume. These secondary things I wouldn't put in my world. I wouldn't like to do that. I would only like to put abstract things about my game in my world, ideally. But very fair question. So probably you will use a single state data structure and have these secondary things as well. But then in a real world example, you will have a world and in that world, you want just your entities in your game. Makes sense? Yeah. So like all the escape hatch could be triggered by something outside the world? Something up, yes, but something inside your main loop, right? Yeah. Okay. That makes sense. So most likely there will be an event like pressing the escape key or something like that. That triggers this escape. But yeah, there's nothing special about escape hatch. So going through this nice closure code, let's take a look at some real world examples. My first example is not exactly like closure. Like it's more like a 0% closure. But it's a very, very interesting library, very simple. It's called Love2D. It has a very, very simple structure and it is written in Lua. And it has a very good community as well. And one thing very important for me is it is not a framework, it's a library. So it doesn't become your master at any time. Its structure is quite simple. There is an initialization function. There is an update and there is a draw. So you know what should go where. Here's an example program. Does everything fit? Yeah. So during initialization, it says the phone size. And then I have some nice, evil global state here. And then my update function just takes the delta time and then increases this global state. And then it just prints something on the screen. Very simple. Of course, when you go into it and when you start writing actual game, you need to create a lot more things. But the top level structure stays the same. And I just want to show how they implemented their main loop. This is not fitting on the screen. I will not show you the entire thing. The slides are on my github. You can check the entire thing later. But I want to show you the abbreviated version. So here it does a bunch of things to get and process the events first. Then calculates the dt, then calls update, then calls draw, then blitz whatever is drawn off-screen to the screen, and then sleeps for one millisecond. This is in seconds. So in the beginning, when I showed you the simple but useless main loop, actually this is exactly that. The simple, nothing fancy kind of main loop. How do they solve the problem of 16 milliseconds? They don't. They leave that for the developers to solve, whoever is using it. So yes, they just call your update, they just call your draw, and then they just sleep for one millisecond. They don't synchronize their frames. Yes, and they don't synchronize their frames. They don't say, I will not run faster than this much. It is left to you. There's a function you can call to get the... You can use dt, you can use something to sleep more, so you stabilize your frame rate, but they don't do anything about it. They just keep looping. The second example has a little more closure in it. It's called PlayCLGS, which is something like a new form of PlayCLG, which used to be based on LibGDX, which is a very nice game library on Java, very capable. This one is based on some JavaScript framework called P5, which has something to do with processing, I think, as the processing rules. I don't know much about it. In PlayCLGS, and also in PlayCLG, which is not maintained anymore, they have two concepts, like screen and a game. Screen is like a stage or scene of your game, like a part of your game's life cycle. You enter the scene, you do something, and then you enter another scene. There's always one scene. And essentially, it says show, hide, and render, initialization, destruction, and update, right? As far as I understand, you don't need to deal with the game protocol directly too much. I just want to show you how it looks like. You call start on it, and then it starts. There are a bunch of functions that you need to call in your screen some of these functions. And another nice thing, let me show you, is that in their rendering code, they use a data structure. So they have this abstraction that gives you data-driven approach. This is an example of a screen. It is very similar to the love code that we have just looked at, the basic game. I want to now take a look at their main loop implementation. Here, it is quite undecipherable, but if you go through this, this is again a long piece of code. If you look at it from the draw function, draw is repeatedly called. It calls redraw is just one second. Request animation frame is basically the browser's mechanism to schedule something to happen just before they refresh the browser screen. You can avoid flickering and other similar problems. This function keeps rescheduling itself, and it keeps getting called. The browser decides when to call this function. And this function checks other stuff and calls redraw. And redraw does a bunch of things about the framework and calls user redraw, which is the draw function that you give this framework. So this is the PlayJS. I had to look at this is the P5 code. Yes, this is P5.js code. The link works, by the way, if you're interested later. So the third example I want to show is also a closure example. And this is one example that I can say that got me initially interested in closure or got me invested in closure, which is the caves of closure code. And there is, I think, 8 or 10 something like that part series about game programming in closure. I strongly suggest that this link goes there. And it's about using a terminal emulator and closure, the JVM-based terminal emulator closure to build a Rougelike. And for example, there are things like generating this very nice map. The algorithm that generates this map that makes it look kind of like a cave structure is quite interesting. Having said that, our topic is main loop. So let's look at the main loop part. This is the main loop for the caves of closure. It is quite different than what we have seen so far. It does something very interesting. It is, again, like a ripple. It's more like an apply-evolve cycle. There are two phases. In this phase, there are some inputs to process and it processes inputs and does nothing else. And then it recurs. When I process the inputs, I get back a world. And I recur with the world again. Or, sorry, game. In the second phase, if I don't have any events, this time I update, then I draw. Then these clear messages, I don't know what it does. And I call getInput. And getInput is blocking. So it stops that. It will not, again, try to read the events. This is a property of some of the ruglites. They don't do anything in real time. They always wait for some user action, even if it is do nothing action. They wait for user action. So it's kind of like chess in that sense. Every time you play computer plays, you play computer plays. Another interesting thing I want to mention is this part. So it doesn't do anything with the UIs. But here it checks whether UIs, whether in the sequence there's something in the sequence. So basically, they are designing the game as a stack of UIs. Stack of UIs. Think of it like model windows. So when you close the last one, when you get rid of the last one in the stack, it will exit. It will terminate and exit. So you start with one UI. You want to do something on top. Maybe this is the menu. You want to start the game. You start the game. And then maybe you want to show something model. You show that. And inventory maybe. Inventory is dismissed. You are back to the game. The game ends. You are back to the menu. You exit from the menu. Menu is gone. This is nil. And we terminate. Thank you very much. Yeah. I'm going to go glide. Is there a copy of that? No. It's independent implementation.