Shader Library | Game Engine series

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hello guys my name is the churner welcome back to my damaged series so last time we talked about shaders and we made them into asset files check out that video you can have it already and today we're gonna be continuing on with our shader journey making our shader API and library a little bit more robust a little bit more powerful because of course traders are pretty much the basis of all the graphics programming we'll be doing so they're gonna be taking a look at shader libraries that I mentioned last time briefly basically shader libraries are just it's a way for us to literally stall to store all of our shaders inside a library so instead of just kind of creating a shader and then having to deal having that burden of ownership on ourselves meaning that like okay well we've you know we need to store it like in a member phungster is a member or we need to pass it around certain functions or we need to make sure that you know we need we have like our Saanich adder that we want to render inside our mesh class for example but we also want to in sandbox we also might want it elsewhere in our code base instead of us having to do that and instead of us actually like forcing the user of the engine to deal with that themselves we're going to make we're going to basically write a system in hazal to deal with that for us so that we don't have to do that I think that in general it's good to have a robust engine API that provides the user of the engine so like the client application as many kind of as much help really as possible because if you're kind of writing an engine and it's kind of doing half of the job it's not providing a complete library to the user to actually be able to do a lot of these common tasks then it's just it's just not as good as it could be because you have to think about it this way right we've written this little engine called hazel and it's gonna be used presumably by a number of games to actually make those games so by us kind of drawing the line and saying that nor this kind of feature must be implemented by the user right who is who is that user you need to think about who that actual target audience is well presumably someone using hazel is going to be some who is probably not an engine programmer right I mean if they're an engine programmer likely they're going to either write their own engine or maybe like they would know enough about engine architecture and all of that to not even be relevant to this conversation but most likely it's been be someone who's one who wants to actually use the engine the vast majority of game developers out there are not engine programmers and so because of that especially nowadays especially with with with kind of both unity and unreal making it super easy to write games right you don't need to worry about anything really c-sharp will kind of take care of itself in unity and then blueprints and unreal will kind of do all of the heavy lifting for you anyway of course you might have to write custom C++ or whatever that's besides the point the point is if you make a beauty make a game without that and with hazel as well we will have a scripting language so eventually I guess my point is that it's gonna be really easy to make games and hazel so suddenly if you're kind of burdened with this kind of like okay it's really easy to make a game and hazel but if I want to do something with shaders which you might own which you might not even have to touch right like I made shaders shaders you shouldn't have to do anything with shaders if you want to make a game in hazel oh that's kind of you should just be able to draw something on the screen without touching a shader let's say you're a little bit more advanced you want to maybe write your own shader you want to kind of get into that land right just like unity lets you as well but then you have to have this shader library that you have to you have to kind of handle that stuff yourself now what's what's gonna happen from that is that a number of people are probably going to not know how to do this properly or not know how to do this well and they're gonna write a solution that isn't as optimal as something that we could kind of think about and design and create right now so what that's going to in turn produce for hazel is basically it's just gonna make the engine run worse it might be more error-prone might have more bugs it might just be slower in terms of performance it might not be perfect right because that is kind of a core system that we want to actually design ourselves because we have kind of quality control over that and then if someone who uses this again if we don't call that talked about like something called the pit of success which is basically the fact that no matter what you do you should fall into that pit of success meaning that if someone just completely misuses this API and just write something completely garbage or just just doesn't know how to use it and so they don't do half of the stuff the engine should still more or less succeed in giving them something that's actually not like the worst thing in the world right you shouldn't be able to put hazel into a state where it's just like a crash zone that's not water she should be easy right it should be easy it should be robust you should just work that's kind of the the goal I guess of this engine and probably most software projects that any of you guys should be working on but my point here is that since that's provided for you since that shader library is provided for you you can just kind of use that and of course you can still write your own as the user feel like I don't want this I want to work differently if you know what you're doing that's fine still want to give so when someone hazel to kind of provide that control to people but it's there if you want to use it and it's kind of the right way to do things and that's kind of why it's important to it take a step back think about these things as if you're kind of designing your engine and just um yeah just do as much work as possible for your users for your clients anyway before we continue to want to give a huge thank you to all the patrons that made this series possible patron Tom Vall said the Cherno you guys helped support the series you'll get access to a private development branch was a day in which I've done a lot of really cool stuff and I've also been releasing exclusive videos just for patrons which is just like a very casual kind of almost like a vlog type thing where I just kind of share my screen you know back up back up my office and I just talk about what I'm gonna do in the next episode of this series and I also show off a bunch of stuff from the Hegel development branch it's a great way to help support this series and to make sure these videos continue coming out I'm actually considering increasing the frequency of these game engine series episodes because as you can see like it's kind of we just don't have enough time to get this stuff done and like the kind of half hour or 40 minutes that I try and kind of make these episodes every single week so I would like to make these episodes twice a week so huge thank you to everyone does help support this stuff because it's you guys who even make that that possible all right anyway shader libraries let's dive in actually before we dive in and take a look at this kind of stuff I do want to mention that if you guys picked up on some things that I wrote in the last episode that were not not very good in terms of codes so I did ask the question to do with STD vectors if I was just jump in and take a look at the code I think that might be easier if we take a look at the OpenGL shader dual CPP file when we wrote this code to do with compilation we had this map that we took in and I created this sed vector and I used the shader sources size as a parameter for this actual standard vector and the reason that I did that was because I wanted to kind of have it I knew what size I wanted the vector and I didn't want it to dynamically allocate every time I push something back into it so I thought you know what let's just do this to resize it however upon reading your comments and then also actually reading the API Doc's for stem vector I was I realized that actually that's not what it does at all that actually physically like creates that many element it doesn't just resize this storage it actually like resizes their amount of elements that's basically the same as calling resize instead of reserved which is kind of what I would after so you could fix this and in fact if we run through this you'll see kind of what I mean the problem is that this actually and this will result in errors upon disruption because what happens is jail shader IDs already has a size of two and it's all they're both set to zero of course because you basically default constructor to integers but then when we go over here and we actually push back what we're doing is we're pushing back a third element and you can see that now at the end of this and when we actually use this stuff which is for this kind of unlinking stuff and detaching shader so let's go over here by the time we get down to that line of code this actually has four shader IDs in it - which is zero which are garbage so OpenGL is not gonna like the fact that you're trying to delete stuff that doesn't actually exist or might exist might actually be the wrong ones you know we're we're basically undefined behavior because we have no idea what's being stored at ID 0 and then 2/3 are our ones the ones that we actually want to detach or delete if the shedder compilation failed so obviously this is kind of not ideal at all to fix this really all you would have to do is come up here and either just get rid of the constructor at all just so that you don't have anything in there or if you still want to make sure that doesn't allocate and which is kind of what I was going for you could just type in a reserved and then a certain capacity which of course will be shaded sources outside and if we basically put a breakpoint here and we just run this code again and we see what we get here you'll see that we reserved this as you would expect the sizes until 0 the capacities 2 which is what I was after and then if we go all the way down to our detachment of the shade as you can see there's just two in there and you have the right amount but this got me thinking do we really need a vector for this and the answer is no because a vector as you guys should probably know if you not aware of how vectors work and how you can optimize the vectors and all that stuff I have a few sales boss series videos on that really important to check those out because the thing is a vector holds its storage dynamically means that when we actually create this vector it will dynamically allocate storage for it which is fine I think that people probably go a little bit overboard with saying that heap allocation czar bad I mean yes they are bad and we are designing a game engine so whenever we can avoid them even though this is certainly not the worst thing in the world I would never ever like look at this and be like this code cannot make it to production it's fine and in fact it's quite nice because it means that if we have it will work for any number of shaders right if we have to if we have one if we have three it's this car is gonna work it's just gonna work because it's a dynamically resizable array however if we want it to be a little bit more efficient what we could do is actually convert this to be a stack allocated array and you can do that either by just using a C style array or we can just use STD array which is what I'm gonna do right now the downside to that and look I mean if you you could still technically keep that dynamic size if you wanted to what you could do is and by dynamic size I'm not actually talking about the ability to resize because there isn't there shouldn't ever be an ability to resize really for this because if you think about it shader sources we're taking in an unordered map we know how big everything years we do it's it's we know that it's gonna be to shade as a vertex and fragment shadow right now because we obviously know about this because we're compiling the shaders now we know how many there are however we do we don't know that until runtime we don't know right now at in terms of like compile time how how many shaders we actually have and in in the c++ if you want to have a stack allocated array we need to know that stack size up front so in other words if i make an array right now i have to say i want an array of size two for example i can't be like i'll just have an array of sized shader sources dot size that's the dynamic runtime variable we don't know that data until runtime it just needs to be known at compile time however there is a way around that you could use a function called alakay what that does and i think i use that in the opengl series episode basically what that does is it performs a stack allocation it's like a malloc with the heap allocation except it does it on it it does it on the stack now it leads it's got a few differences I don't this videos not gonna be about allocate but it does have a few differences such as the fact that for example unlike stack allocations the scope of that allocation is discovered the function of the scarp that you're in which in this case if we allocated it well we did with the vector would be the same as the function scope but also some people claim that it doesn't it reduces to become it means that the compiler can't optimize things as well and that's I don't know I haven't personally run into any issues with that so I would say go ahead is probably gonna be better than this solution but because we don't really need to resort to allocate it's not like the difference is gonna be we might have one shader we might have 15 we might have a thousand it's not like that at all we basically are either gonna have two shaders maybe three shaders maybe if it's a computer we have one the point is that the variance is so slow so low and these are GL enums if take a look at what Jill Imam actually is it's an unsigned e it's a 32-bit integer however a 32-bit integer I'm not gonna have I'm not gonna cry about if we have like a basically four bytes of storage so one integer or if we have 12 bytes because we have three that's absolutely insignificant and it's gonna be way faster for us to allocate that on the stack and have too many so for example let's just get 12 bytes of stack allocated storage because that's three shaders right 3d nums three unsigned integers it's a lot better for us to just request 12 bytes from the stack it's literally like like you wrote three integers in your source code like you have a full loop that's one integer right maybe you have three full loops and just the indices that's three digits that's done right you don't think about that stuff but when you're making arrays it's tempting to be like nah it's too big or that's too small or whatever but my point is that if we just write some code here that says I want to allocate a stack array that has three integers or voyageurs or ten integers that is still going to be a lot faster than if we create this vector and then it does a heap allocation and it only allocates not a nerd to the integers worth or you know how many it needs so you shouldn't be worrying about that stuff let's just convert this into an array because that's what it really should be it should just be a stack allocated array so what I'll do is I'll include that because I don't think I'm not sure if we have that in the PCH we really should I'll include that in the PCH here so we'll have array my recommendation with this kind of stuff is try and use array whenever you can of a vector because using the vectors liberally is not a very good thing to do because of the hip allegations and of course since we are kind of making an engine it's really good to think about that kind of stuff so what we'll do is basically what we'll have is a city array we'll have GL enum and what I'm gonna do right now is actually write true for the size now this might be controversial so to speak because as I just mentioned we could have three shaders a bit of one whatever right we basically need this number to be the maximum number of shaders ever and to make sure that we never you know don't do our job correctly we're gonna make a coarser here the base says that data sources has to be less than or equal to two okay because if it's not if it's three for example this code is not going to work correctly at all so that's what we'll do then we'll be able just say that you know I don't know I am you know what to write up all message basically the only we only support true shaders for now or something like that I'm the owner I'll get rid of the inflammation markers it's really not that exciting okay cool so basically we'll just do something like this and of course it's gonna be shader sources sighs we're creating two of these here we get rid of this completely and now we need some kind of ID or index for them so the easiest way to kind of deal with this is just to make a little hint which is just gonna be our gel shader ID index or something like that all right we'll set this equal to zero and then every time we use it we just increment it so over here in jail shader IDs we just do share our ideas girl shader ID index plus plus so we do a post increment because of course we do want to actually use it at like the value zero first and then next time we run it it'll be one right that has to be that size and then we basically don't need to use it ever again right so that's kind of it because over here of course we just we can iterate through it as normal so what we've done is we've converted it to be a staff allocate an array we're just storing eight bytes on the stack now instead of eight bytes on the heap which is gonna be a lot faster especially like the allocation stage not to mention that technically whilst I would probably we are using a lot of stuff here you might expect the sed vector to have its stuff ready to go in the CPU cache but it might not be where is this definitely will because it's on the stack it's really hot and readily accessible memory which is what we want anyway um yeah this will work as expected I might be the only test that it's definitely gonna work but if we look over here when we detach them for example you can see that we have all of that stuff in there and of course when that gets destroyed we don't need to free anything from the heap either it's all kind of just part of this stack that belongs to this function okay cool so that was just something that I wanted to there was actually one other thing that I wrote that was incorrect very easy to make this mistake or if we look over at the file reading source code basically what we had here was I used STD iOS in and then I wrote a comma instead of a an org device all operator because this is actually all one parameter this is a bunch of bit flies it says what kind of input stream this is in meaning that we're opening the file as an input stream submitting read-only and then sed iOS binary meaning we're going to be reading it as a binary if you I don't even know what that other it just says in prod like I'm not sure what that is actually did look at the API here I didn't even find a third parameter to be honest all of these things have just two parameters so I'm not really sure what that does but anyway as you can see all of the modes all the applicable modes here it's a bit masked type so you can all them together of course and we have in which is open for reading and then we have binary which is open in a binary merge okay so that stuff is fixed up now that we've fixed up all of our code from last time we've kind of discussed why you needed fixing and especially like I really wanted to mention that kind of vector array thing because I feel like that comes up all the time we can finally get into our shader library so this is going to be very simple basically what this is going to be something that's owned by the renderer essentially and that's good because it enables us to automatically load all about default shaders all about kind of vital necessary shaders which might include like diagnostic shaders for example we can load all that all of that stuff up when the renderer initializes and then we can you know they'll be readily available in our program and if the client or if the user wants to like alert additional stuff that they're more than welcome to do that that will just work and of course because it will be kind of awed by the renderer it'll be all static which means that you can access it anyway in your code base so let's just dive in and write that code so what I'll do is I'll go to just normal shader h-file so all the shadow related stuff is going to be in this file I'm not going to create a bunch of files that are basically all going to be to do with shaders and call them like shader library or H I think that's just gonna make the readability kind of difficult and just having extra files is never a great yeah so what we'll do is underneath shader will make all right possible skater library and the core to all of this so we'll have we don't even really need to have constructors of these structures I think the core of all of this is going to be an unordered map of string through a Hazel reference of a shader right so this will be our shaders and I only include our unordered map okay that's gonna be basically all that this shader library is and then we'll have a nice API to make it really easily accessible so we'll have an odd function which just takes in a shader so that we can add a shader that it kind of exists already into there so we'll just say Const RAF shader isn't the reason I take the tin as a Const reference by the way is because the copy we don't really need to worry about copying this it'll get copied the actual smart point will get copied when we go into the unordered map that's at which point we kind of copy us so we're gonna bleeding to you know make an extra kind of rep count here for no reason that's why I like doing it this way because I think the back comes up as well sometimes so we can load a shader just straight up because that would be kind of convenient I think and this should just return a rack just in case we want it so the load will basically take in a file path so cons STDs string file path and then what we'll do optionally is will allow will allow people to just kind of name the shaders as well so by default the name that that's gonna exist is if we have a shader like textured or GLSL by default is going to store it as texture so in a stripped extension strip default path any kind of directories that we might have assets or whatever I'll strip that and we'll just get that texture name out and matter that's what the name will be and that's what this string is this string is going to be a unique name which identifies our shader and then that of course is going to be the shader pointer to support this naming so we will have to actually add some self true the shader API because of course at the moment if you add something with just a shader you know I don't want users tough to specified names or anything like that and then we'll have to have some kind of get function of course we'll have wrap shader guess and then this will just basically retrieve something from that unordered map by just the name it just like that that's our entire API let's go ahead and create all that stuff using the visual assist who I am NOT sponsored by by the way is your one room but if they would like to sponsor me I'm of course ready so really the add function is just what it needs to do is get the name of the shader out so basically something like share to get name this doesn't exist yet but we need to add that once this got it is going to need to check to make sure the map doesn't already have a shader with that name because if it does and you know the shader is already present we can't use that and then otherwise of course if it doesn't so I'm just writing some pseudo code here then we basically just write basically to store it so we'll say I'm shaders name equals share just like that so the biggest thing right now is we need to somehow get that name out of that shader file class so if we go to share it or age not everything has a name and that's probably fine what we can do is when we create a shader pair like this we can mandate to have a name so we'll say Const STD string name that's probably a good thing to do because now that we're kind of storing these things as actual like inside a shader library it makes sense that every kind of asset should have some kind of ID now you could of course just store this as an ID that's totally fine but the problem is we want people to be able to access that and if it humans strings are the way to go so that's why we're using strings here this is totally fine as well and then what I'll do is just make a virtual SC string it'll be a contest a string so I'll make a shadow store it get a name and then Constable's equals zero okay so that's gonna be our function so grab that I'll grab all of it and I'll go to jail shader the H and then over here maybe somewhere around yeah I will just do a Const override this will just return a mean name which is something that traders will now store so over here at city spring em name and then if we come over here actually what I'll do is I'll add name here just like that and then if we go into our source code I mean it's all source code but but I meant the dot CPP file so we'll have a name here and M name name okay that looks pretty good to me and then here we actually need to extract that name from the file pot so it's kind of easy to do all we really need to do is and I'm just thinking I might do this after everything gets compiled successfully it doesn't really matter there what I basically do is just do some basic string operations on that file path to get that stuff so the first thing that I'm interested in is getting the last slash out when you're doing stuff like this it's really nice to just be able to kind of write an example for yourself so you can actually see what's going on so we've had assets shaders text about GLSL that's kind of what we're looking at and we need to selected this so if you think about it what we need is that last slash right and then the last kind of will the last from the end that last dot so if we had like textured oh I don't know intentional shaded or jail cell we would want to probably select this right because that's part of the file name and then the last dot followed by some letters is the kind of extension of our file so if we have something like this the last slash we can get really easily or we all we need to do is just use the file name or file path dots find the last of make sure you use last toggle not last not off and then we can actually add a string here because the other thing you have to think about is on Windows someone could actually use a backslash right so we need to handle that as well so we'll just do fine last off full slash or a backslash so once we have that we'll need to just make sure that actually exists as well because if you think about it if we just have that there is no slash at all and that means the last slice will be equal to s to D string and class which means it wasn't found so in that scenario if it is embossed we just want to set it to zero otherwise we want to set it to last slash last one and the reason we want to do plus one is because if we don't do plus one then we'll have it'll just be the beginning index of course of this it'll be the index of the slash which is here not over here and we want it to be one past that so that's how we get our last lash the last dot thing is also quite easy to get all we need to do is do file paths we could just do find the last of as well but there is another function called our find it's basically the same as line last off with bone loss stuff will actually try and find any of the characters you give in your string whereas I'll find will kind of match it exactly and we just need to find a dot so it's better for us to use it in this case and then once we do find that last dot I want to use a function called so we'll use file path del substring a function call substring and what that takes is an offset and account not an officer not kind of a beginning and an end index so because of that we can't just use this but actually you should work out what the count is so the count will just be now the count of course depending on whether or not we do we even have a dot because totally a file doesn't have to have an extension so in that case if there is no exception so last dot doesn't exist rice the last R equals s D string and cause in that case we'll just use file pop sighs - that last slash so we're basically again if I bring back everything over here assets shaders texture what we're basically doing is if if it's if it's not found so there is no dot at all we're just so that would look like this we're basically just saying in the count here's the file pastel sighs - lost slash so this is last lashes file sizes so if we back which is selecting this many characters which in this case would be seven which is exactly what we want however if we do have a dot like we do here we're basically to go from the dot to the slash and that's our count because we're gonna we're gonna start this file path or substring we're gonna start that at last slash right because that's kind of here and of course we did we said last last a lot / + 1 so it'll be perfect and then we want to basically measure from that last dot to that last slash how many characters that we have so that simply becomes last dot minus last slash and then that's it we can just put that count in and we have our name just like that okay so this basically is through extract name on file month okay cool done that's all you have to do and we of course need to test this so what I'll do is just put a breakpoint in here and hit f5 and of course I forgot that we just multiply this whole API which is gonna wreck everything so what I'll do is just fix up all of the API changes of amazing we have file path over here sorry we had a name so we taking a name now if we create is like that so that's actually gonna require a bit of a refactor but that's fine it needed to be done let's see what else we have so array Lord okay this stuff needs to return stuff we have get name now so we can actually finish writing the shader library and let's will test the name stuff at the end so I just want to add a corset here which basically just verifies that that M shade is still find that our map doesn't actually contain that shadow already so if that doesn't equal M shadows dot M right that means that we actually have that inside the map already so we'll say shader already exists okay and then that way we know that we're trying to add something twice for Lord so this is a file path it takes in a shader and lo so this is kind of easy as well all we need to do is say water shader equals shader create and then of possible taking a file path then we'll have a name so we'll grab this and we can actually just through add with that shader once we have that and then once we've added a shader like that so this family still takes a pointer I thought we changed this stuff I guess we didn't that's actually weird maybe I accidentally I'm not synched up the repository correctly or maybe we didn't in which case we didn't if we didn't we just needed to change this stuff to be a ref I'm not a pointer so that's the kind of easy to do I think there might be some areas in which we forgot to do that and then this becomes I'm fairly sure we did this but again I don't remember 100 Sam Choy's and that we didn't sir make shared I'm Kirk in jail shade up um it doesn't matter if we already did this and that's fine as well but it's the same what's that not copy correctly at all make sure to let me know that I get cold so that looks pretty good to me so now we just do a kata and then we can just return the shadow because that's what load once so we basically create it and then we're at it in the maratona so lord with a name specifically he's gonna do the same thing it's just that instead of us adding it using the add function like at that what we actually have to do is add it by name just wondering it's probably better to make a movies because we want so that's maybe if we're taking a file path what we want to give it a custom name that's fine as well I guess what I'll do is I'll actually make another version of this that takes in a name and it's gonna be the same thing as the other one so we'll grab populace so that we can implement it ourselves and then what I'll do is so this will kind of be the I guess the the super ones will actually put it ahead because we'll get this ad to call that out so what this will do is I'll copy this it's just the difficult name so we don't have to worry about getting the name out of the shader at all so it's got a name and then this will basically just call add we've met with the name that it got an initiator so this way we support adding adding it without a name of queer and have a name or rather we support adding it with a custom name instead of relying on the file name if that's what you want and then finally get will be super easy basically we'll just return em shaders name but we should assert of course to make sure that it exists so we'll say that shader okay this is wrong actually so and I missed that so we're trying to make sure that it does equal and right so that means that we do not find the shader in this case we want to assert that it's not end which means that we do find the shader so if that actually assessed been stated or found and then that's it okay we don't want to waste time really doing stuff like if you know handling it and maybe returning like a null pointer you could do stuff like that but the problem is that businessart will be stripped out in release mode you probably should never have a state in which you request a shader and then it's not found if that's really like an issue we could easily add a function that you know that has something like exists shadow library dot you know exists and then just a name and then in that case what this will do and make this constant what that would do is just if I implemented quickly and then all that this could do is just return em chatters find name doesn't equal em chatters ends so if it doesn't eat land then it does exist and that returns true which is what we want and of course since you've written this code you can of course just do exists and then name to make sure that it actually you're asserting that it does exist and then in this case we'll replace this with doesn't exist so not exists name just like that okay cool and now we have a pretty functional shader library so where does this deserve to live technically speaking it should be something owned by the renderer as you can see we're in a situation here what we don't even have storage for the renderer so I'll show you how it works in sandbox and then when we actually get into how the renderer is going to store all of its variables which we haven't even covered yet that's when we'll kind of deal with that so yeah I think I know what happened here I am on a I must be on I don't know everything's fine but these are all yeah I was so sure that we replaced this stuff I met I may be on an old copy because what I did stupidly is I kind of mute to my repository because I thought I committed it but I didn't so I lost all of my local changes and that might have included fixing stuff from last episode so if that's happened then I'm sorry so this shader I don't even know what this is I don't think we are we using this anyway anyway I am shader we were using it for our triangle so I'll kind of I'll kind of call it our triangle shader see this is good because it forces us to actually call a shader something so we'll say vertex color triangle maybe because you can see that if you look at the source code he kind of has that color to be based on the vertex positions so you know vertex may be vertex position vertex positive color okay so that's that shader and in this shader with black color shader other names that flash color and I think everything else is good let's try and compile this card and see what happens we still have a few errors inside the urban GL shader stuff which is probably too fine I may have just forgotten to do some things so what's actually wrong with this thing about overloaded operators M name that should be okay not sure why it's complaining notices of overloaded function every judge try to match it matches so alright okay so i accidentally removed com2 yeah that was probably riddles you here because sometimes when you type stuff it likes to remove words around what you're typing it's really frustrating I should turn it off but anyway um well here are five and we'll see what this gives us okay cool so everything's kind of working one thing that I did want to check was whether or not that name was trips successfully so if we just look at this break point and we look at everything else here the name should be set it's just texture as you can see it was just perfect it's exactly what we want okay great so now to use this shredder library what you need to do is and this will be done in this will be done eventually of course in our actual renderer so this is not something that you would do in sandbox basically we include shader I think every child care to include shader so we actually don't need to need to even include this we basically set up a shader library so again really easy to do that and it can totally leave on the stack so just shade a library just like that and then what we need to do is every time we add a shader instead of having to worry about holding references to it and of course this is a haze little shader library instead of worrying about holding references to it like this you can see we've got like M shaded here for example we don't really need to worry about that at all for our texture shaders which is just as an example let's just get rid of that texture shader so let's see what we had here initially because we definitely had so we had our texture shadow where is that it's over here let's get rid of it so I'll show you guys kind of how like what this actually does so instead of having amped extra chatter what we really need to do is just do em share shared library and then we can just do large with just a file pod so we just kind of end up with something like this I'm sure the library Lord and then if we actually want to access it like we do here the Lord actually returns a rap so we're going to say order you know texture data or something like this if we want it to we put that we put that in here and then that's fine because that reference will die and that's totally okay what happens is when we needed our here to render stuff we just say order texture shader equals M shader library don't yet and then a texture just like that and then we just replace this like this so what does now gives us is the ability to actually store everything inside a shader library and then reference it as we need true now in this case it's kind of a step backwards because instead of having a nice reference inside sandbox app and just being able to render that and not have to worry about getting stuff out of an unordered map even though that is super fast instead of doing that and instead of having a member what kind of resorted to doing this stuff which is kind of not the best thing to do in this case but of course you have to imagine the fact that you're not going to have everything in one file in this one kind of example layer yeah example layer so instead of having all this stuff here you'll have it a whole round you're kind of engine code and all around your gang code and then now what we've done is a way to access this and of course you instead of having shader library we might have something like a renderer a shader library and then yeah just like that so it would be a little bit more static and a little bit more accessible than having to have something like this but you can see it works like this as well so if you really wanted to have segregated shader libraries of just various groups or chunks of shaders you can do that as well we should probably test this make sure it works if we get f5 then we should see that in action and you can see we get exactly the same as before so in a nutshell Danny's shredder libraries that's how they work I'm not gonna go ahead and replace every shader where we have with that specific like shadow library version of that shader because that's for this example it's not necessary probably wouldn't use it but when we do have like a standard kind of 2d shader or a standard like I don't know blur shade or some post-processing shader and it's standard like PBR shader in that kind of case that's when you actually would want to use the shader library you would have you have the renderer upon initialization actually load the load all those required assets and resources like the PBR shader that it uses for example and then that would actually store it in the shader library so that is accessible by your entire code base and that's actually what hazel dev does at them at the moment anyway I hope you guys enjoyed this video if you did hit that like button as mentioned earlier you can help support everything that I do here on YouTube by going to patreon Akhilesh at the Turner huge thank you to everyone who is graciously supporting this series next time look there's so many things that we have to think about I actually want to have a bit of a maintenance episode I might might have it is like a midweek thing we'll see if I get the chance true just because there are a few things we need to kind of clean up here and I want to deal with the repository a little bit as well so we will see but apart from that yeah well we might have like we are gravitating towards 2d so I think the very very soon will start kind of building up everything we need to get a nice tuna renderer into here I'll see you guys later goodbye [Music]
Info
Channel: The Cherno
Views: 19,131
Rating: undefined out of 5
Keywords: thecherno, thechernoproject, cherno, c++, programming, gamedev, game development, learn c++, c++ tutorial, game engine, how to make a game engine, game engine series, hazel, hazel engine
Id: Z9LE3ksHEQQ
Channel Id: undefined
Length: 41min 23sec (2483 seconds)
Published: Sun Sep 08 2019
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.