I’m back! Finally! It has in fact been over a month, but that means I’ve got plenty to tell. As the title suggests, I have continued my streak of Minecraft development over the past 2 weeks or so. I’m not sure if anyone actually looks at the categories for posts either, but this one sure has a lot of them. From a small, entirely new, plugin, to a short foray back into the Exaroton API, and of course, some ReLife. So, time for some updates!

Cafei SMP

Ok, first thing to talk about is that small plugin I mentioned. In case you don’t know, SMP (in this context anyway) stands for Survival Multiplayer, specifically meaning a Minecraft server that anywhere from a few to dozens of players can join and play the game on. Not all of them are “vanilla” Minecraft though, which means unmodded. My friends and I decided to start an SMP ourselves, and Cafei (kaf-ee), we wanted to add some superitems to the game. Of course, being the most knowledgable about serverside modding (aka plugins), I volunteered to code up a plugin for the server.

The goal was for it to be a fairly simple plugin: just add 5 unique superitems. Being superitems, only one instance will exist at a time, and only one person can have each superitem. Of course, since a plugin is serverside only, I can’t just add new items. Neither solely serverside, nor solely clientside mods can add items, because the item has to be registered on both sides for them to know what to do with it.

There is another option of course: overwrite an existing one. Now I don’t mean something like make every stick people create super powerful. What you can do, however, is add a tag to the item to identify it as one of your items. Essentially, for each of the 5 superitems, I instantiate a new item with a material (i.e. stick), and then in the instantiation method give it a custom tag for identification later.

By now I should probably mention what the superitems actually are:

Staff of Eternal Flame: a stick that you can right click to set the entity you’re looking at on fire, or use as flint and steel (right click to set the block you’re looking at on fire), and finally, it has the combat stats of a diamond sword, and when you attack an entity it will set them on fire and give them the poison and nausea effects.

Bane of the Mighty: a shield that while in use (in Minecraft you hold right click to hold up a shield) reflects projectiles back at the shooter and reflect the damage of melee attacks, so long as the projectile/attack actually hit the shield (shields don’t protect your whole body, just the direction you’re looking). It also has the combat stats of a diamond sword.

Heaven’s Wrath: a trident with the Loyalty enchantment (when thrown, it will return to its owner of its own accord), and when thrown, if it hits an entity, it will strike that entity with lightning, and if that entity is a player, it will make that player toss out the item they’re holding.

Helm of Boundless Vigor: a golden helmet with the Protection IV enchantment, that while worn will give you 10 extra health (5 extra hearts, your normal max health is 20, or 10 hearts), as well as slightly increasing your movement speed and attack strength, whilst also being invisible to other players when worn.

The Black Rain: a crossbow that you can simply hold down right click to fire extremely fast, and has the Multishot II enchantment which makes it shoot 5 projectiles at a time (in vanilla Minecraft, there is not a second level of Multishot, and it makes the crossbow shoot 3 projectiles rather than the usual 1)

Ok, there. Not only did I have to add those five items, but I had to implement them quickly because the SMP was planned to start just days after my family got back in town, and I couldn’t work on it beforehand. Here goes!

Staff of Eternal Flame

Ok, first, the Staff. The simplest thing to do first was to make it like a diamond sword. I actually originally start out by making it an iron sword, but the way I coded it made it very easy to change. The way Minecraft handles this sort of thing are these things called “attribute modifiers”. Essentially, any given living entity (not stuff like item frames, boats, minecarts, projectiles, etc.) have a bunch of generic attributes, and some (like horse jump height) have specific attributes. Items can have attribute modifiers on them, which activate when the item is in a specific equipment slot. In the case of weapons, it gives you a bonus to your base “attack damage” and “attack speed” attributes when held in your mainhand.

Because of that, all I had to do was create a new instance of a diamond sword item, and then copy its attribute modifiers and add them to the Staff instead. Quick as that, works like a charm, and for once, on the first try!

Next simplest thing was to make it set attacked entites on fire and give them the effects. This is also very easy, because I just have to add a listener for when an entity attacks another entity, check of the attacker is holding the Staff, and if so, give the attacked entity the effects and the fire. Done!

The flint and steel part is going to be the hardest, so for now making right clicked entities get set on fire. Thankfully, there’s already an event for when an entity right clicks another entity, so I just added a listener for that, and then set that entity on fire. Well, almost. I did have to add one more check because for entities such as villagers that do things when you right click them, I want it to prioritize interacting with that entity rather than setting it on fire.

Sadly that wasn’t as simple as I’d hope, but a small dip into NMS and I found the code I needed to steal. Don’t worry, there’s plenty NMS to come. Basically, I cancel the event to right click an entity 100% of the time and run the NMS that usually happens myself. Not my favorite solution because if something changes in the NMS, I won’t know to update my code. Since this is a relatively small plugin, I don’t need to worry about Minecraft updating before it goes out of use.

The short explanation is that I tell the player that it right clicked with the item, but what’s nice about the NMS code is that it tells me whether the right click was consumed (which would mean it opened an entity) or not. That’s it for this, now on to the most complicated, and most NMS-y, part.

Alright. So. While this is the most complicated part, and I had to delve into how the player interact packets work deep in NMS, the solution is rather simple and elegant. I won’t get into how the interacting code works, but my solution is to essentially tell it that on an interact block event, if the player is using the Staff, tell it that the player is using flint and steel.

Now, there are some blocks that when you right click them they do stuff, like chests, and same as the entities, I want to prioritize that. I initially was doing a lot of complicated stuff: trying to handle the prioritization myself, trying to copy flint and steel stuff, etc. Then I realized I could just call the method that told NMS that the player was trying to right click with flint and steel, and let it handle all that internally. Problem solved! And just like that, the Staff of Eternal Flame is done.

Bane of the Mighty

New item! Very exciting. This one only has two new functions: reflecting attacks. It also acts as a diamond sword, but I just copied the code for that from the Staff. Out of the two reflecting tasks, its a little hard to tell which one is easier initially, but the projectile one is simpler so I’ll start there.

Once again making use of my handy dandy Bukkit events, I add a listener for every time a projectile hits something. If it hits an entity, and that entity is holding the Bane, and their shield actually blocks it (it hits somewhere where the shield would normally block it and make it just bounce off), I just multiply it’s velocity by -1. Yup, that simple. That works, because the gravity will still apply going backwards, so it will follow the same trajectory.

For figuring out if it actually hits the shield, I just looked at what NMS does and made a single method call. The one hiccup with that plan was fireball projectiles, like that of ghasts and the ender dragon. Instead of just having velocity, those have a “direction”, so I have to multipy that by -1 as well. There, now done!

Reflecting melee damage takes a bit more effort, but still not too bad. The idea is that instead of just blocking the damage, similar to the projectile, it makes the attack take that same amount of damage. To do this, I add a listener on the entity damage by entity event, make sure the damaged entity is using the shield and actually blocks the attack (same as with projectiles), and if so, damages the other player for the damage amount. I do have to tell it that it’s being attacked by the entity holding the shield, because I need them to take knockback away from that player. Simple enough, that’s the shield done!

Heaven's Wrath

For the returning to the thrower part of this, I just add the loyalty enchantment on instantiation, and let Minecraft handle it. Honestly, the other parts are fairly simple too. On projectile hit entity, if that projectile is the trident, strike lightning at the hit entity’s position 5 times. Secondly, if the entity is a player, it has to knock out their item. Unfortunately I couldn’t just make it toss out the item in the mainhand, because I also wanted it to knock out their shield if they’re trying to shield it. Essentially the logic for when it chooses offhand vs mainhand is: if the offhand is being used (i.e. shield being held), or the mainhand isn’t holding anything, try the offhand.

Sadly, there was one more thing to do here, and this was what I had to spend the most time debugging about it. When lightning strikes at a location, it will destroy any items it hits. Now this is unfortunate because I really don’t want it just destroying the item it tosses out. I also can’t just toss the item out after the lightning is done because it strikes lightning 5 times over the course of half a second, and I don’t want to wait that long to toss the item.

Thus, I must do it the hard way. Luckily, when an item is destroyed, it sends out an entity damage event. So I added a listener for that, and made it so when it creates the item entity from tossing out an item, it tracks that entity’s ID (every entity gets a unique integer ID). It also tracks the lightning entities (yes, even lightning has an entity!), and in the event, if the damaged entity is in the tracked entity list, and the damager is in the lightning list, cancel the event.

I then add a handler for when an item entity is picked up or destroyed, so I can remove its ID from the list. Elsewise, I wait until all the lightning is done striking, then remove all the lightning and the item from their respective lists. Of course, that required a lot of debugging, but there’s nothing interesting to talk about there.

Helm of Boundless Vigor

This one has changed the most from the initial idea. Initially it was just a golden helmet with Protection IV that other people can’t see you wearing and also gives you 10 extra health, but then we realized that was really weak comparatively, so I made it buff your speed and strength as well.

The health, speed, and strength are all pretty simple so I’ll start with that. Essentially, all I have to do is give it more of those attribute modifiers. I just tell it that while it’s in your head slot, add 10 to your base “max health” attribute, and add some to your “movement speed” and “attack strength”, and voila!

The harder part is making it not show up. I knew that I’d have to use packets to lie to the other players and tell them that whoever’s wearing it wasn’t actually wearing a helmet, but I wasn’t yet sure how the equipment packet works. I thought I could just send one to tell the other players that the helmet slot was empty, but how it actually works is it sends them fairly often, any time you switch an item or anything, and for some reason sending it myself wasn’t working.

So, I decided that instead of trying to keep track of when you’re wearing it and not, and then sending a packet to say you’re not wearing it, I would just edit it out of any outgoing packets to the other players. For that, I needed to add a packet handler, but I already had some code from ReLife I could copy over. Basically it injects a listener into the connection between the server and client.

Inside that listener, it has a check for if it’s an outgoing equipment packet, and if so, it checks if it has any mention of the helm, and if it does, it edits it out. And it works! Better yet, it didn’t require to much debugging for it to work… once I set up the packet handler method anyway.

The Black Rain

This one is, by far, the most complicated. Whilst making you be able to hold right click to rapid fire arrows isn’t the simplest, it is where I’m going to start, because that’s the basis of this item. So what I need to do is on player right click, if the player is holding the superitem and the crossbow isn’t charged, I need to charge it.

I can’t just charge it immediately though, because while it will still set the crossbow to be charged with a projectile, the player will just keep trying to charge it, so they’d have to spam right click rather than just hold it. So, I set it to run this code 5 ticks (a quarter of a second) later. I then wrote some logic for picking which projectile to use (if you have multiple types of arrows, or fireworks, etc.), and had it load the crossbow, then tell the player to stop trying to load it (again, to fix them just trying to keep loading).

Again, that is the finished product, saying nothing of the extensive testing I had to do to figure out things like how I have to wait 5 ticks to charge it. That out of the way though, I have to add two mroe arrows to make it Multishot II. As stated, Minecraft can only do Multishot level 1 by default, and doesn’t have code in place to handle higher levels. What Multishot does by default is add two more arrows on either side of your normal arrow (or firework). So, I went into NMS and found that code, then extrapolated it for two more arrows, and boom! Multishot II working.

There! All of the superitems done. But what is this? It’s not quite another section yet? Nope, we’re not done with Cafei SMP just yet. In order to “win” the SMP, you have to aquire all 5 superitems, unlock the end portal, and get the dragon egg. But, as it currently stands, people can just keep items in their enderchest or bury them in some chest somewhere and never be able to be gotten. Thus enters the Zherral Tracker (the superitems are called Zherral).

Zherral Tracker

That’s right, the subheading is back for one more! So to figure this out, we all got in a discord call and decided on how this would work. So, by the time we were done, the item was a compass, and these were the requirements for me to code:

  • There is a different recipe for a tracker for each superitem, very similar, but with one item keyed to which item it tracks (i.e. it takes a stick for the Staff, shield for the Bane, etc.)
  • When you right click with it, it tells you whether the item is in storage (such as a chest), dropped (as a physical item on the ground), or if it is on a player, it tells you which player is holding it, but it costs some levels to make that check
  • When you right click *while crouching*, if it is in storage or dropped (notably, **not** if a player has it), the compass will point towards the location of the item
  • When it's not tracking, or if it stops being able to track (i.e. if a player picks up the item while you're in tracking mode), it should spin wildly, or do something else to signify it's not tracking (other than just defaulting to track towards spawn like compasses usually do)
  • To activate the tracking mode, you have to have at least 30 levels, and then it will drain all of your levels down to 10 into the compass, which will run down over time, but you can't disable the tracking mode until you find the item (it refunds your levels), or it runs out of levels
  • It has to show how long you have left to track somehow

So that’s quite a lot. And once again, I didn’t have long to implement it because people wanted it in game as soon as possible… thus began a few days of frantic coding.

Alright, dramatism aside, I did have quite a bit of work to do so lets get to it. The very first thing to do before I could start on any of the tracker’s frontend functionality was to get it to actually track the superitems in the backend. Doing that reminded me of doing kill credit for ReLife, but on a much smaller scale, because I essentially had to just try and think through every single way that the item could move around. Tossing it out, being picked up by a hopper, being moved around in inventories, etc.

Since I needed to be able to store the location of the item for tracking it, I made a new class that could store either an item entity, or a player, or a block that can hold an item. Of course, I don’t want restarting the server to clear that list, and I can’t loop through the entire world looking for all the items on startup. So, I have to write it to a file. There’s already an API for saving configuration files, so I just used that to serialize that location class and then read it back in at startup. Not terrible.

Having debugged that, which wasn’t too bad, it was time to move onto making the actual tracker. I handled instantiating the item very similarly to the superitems, but that’s about all they have in common. For this, I had to actually add a recipe so you can get it in survival, whilst for the superitems I just spawned them in using a command.

So to make it craftable, I have to register a recipe. Initially, I tried to just add an event handler on when you try to craft something, and if it matches the recipe for the Zherral Tracker, manually set the result to be one. And it worked great… but it didn’t show up in the recipe book. In Minecraft, there’s a recipe book that lets you easily just click and have a recipe be autofilled from your inventory. It wouldn’t have been the end of the world if I left that out, but I’m a little bit of a perfectionist sometimes and I couldn’t leave it.

While the Spigot API is great, there are still some things that it would be nice if they added. For instance, there’s a nice method called Bukkit.addRecipe that will add a recipe and make the server handle crafting it. The issue is that said method won’t automatically update all the players’ recipe books. The issue is that the recipe book packet only gets sent when the player joins the game, because Bukkit expects you to only be registering recipes when the server starts up, and when the server’s starting up, no players could already be online, so they’ll all have to join and get sent the packet correctly.

The issue is that sometimes I run a command called /reload, that will update the plugin, but won’t make all the players leave and rejoin… meaning they don’t get the updated recipe book packet. So, after some Googling, I figured out what I had to do, sent the packets, and saved the day. Ok maybe not that last part, but I was very happy when it worked.

Alright, easiest part done, woo hoo! Now for the difficult stuff. And I mean difficult, I spent many a late night fixing bugs that players would probably never even find under normal circumstances.

I’ll start by talking about the two different activation methods: right clicking, and sneak + right clicking. The simpler one is just right clicking, because that just has to immediately tell you something. The main thing to decide there is how I want to give the player the information. To get the information I just have to consult the map I created earlier, then decide whether to say it’s in storage, dropped, or which player has it.

The options for information medium is fairly limited, however:

Title, subtitle, and bossbar are too flashy, but I’ll be using bossbar later, and text feels unprofesional, crude. So, actionbar it was. I made a simple util method to send the right packets, and tehre we go. Works! Well.. for now, we’ll be coming back to pinging (right click activation) later.

Now the tracking option (sneak + right click) is a bit more difficult, for a few reasons. Initial activation isn’t too hard, it just makes sure you have enough levels (you need at minimum 30 to start it tracking), and then drains your levels to a predetermined number (10 levels). Of course, I want it to be able to stay active across server restarts, so I stored it in what’s called “persistent data”, which essentially is a purely Bukkit API that adds it to NBT.

So, it stores the game time (ticks since game creation) to be used in calculations later, and the number of levels that were put into it. Now, just like a lot of things I’ve talked about today, I started by doing it one way, then changed to doing it a better way. Initially I was storing an ItemStack object, but that didn’t work for some technical reasons I won’t get into.

What I ended up doing was, when you activate a tracker, it starts some code that runs every tick. That code then goes and checks if the thing holding their item (again, using that map) is a player, and if so it needs to tell them how long they have left on their tracker.

This is when I first considered using a resource pack (forcing the players to download custom textures, so I could make the compass look different from a normal one). I thought about having something visual on the compass item for how long it has left, but decided against it as that would be fairly difficult, but remember that resource pack idea for later.

Now you may remember from geometry, or maybe not, what an arithmetic sequence is. Essentially, you plug in n, the index in the sequence, and you get out a number. That’s essentially what I’m trying to do with this bossbar, I give it how long has passed, in ticks, and then it gives me how full it should be.

To get a value from a sequence, you have two options: the recursive formula, and the explicit formula. The recursive formula is based on the previous number, say “previous number + 3”. Now, that was what I initially wanted to do, but that would require storing another thing on server restart, because after the restart it wouldn’t remember what the previous number was.

Instead, I went with the explicit formula, which is why I need the start time: I plug in how long has passed, how many levels were stored in it, and calculate the percentage each time.

Aside from the bossbar, the code also checks if it has finished (if all the time is up), so that it can reset it’s compass to the dormant state - not pointing to any Zherral. And… that leads us into the next problem, which I saw coming since the beginning, but didn’t wnat to do anything about it until I had to.

And that is: the dormant state of the compass. By default, since it’s technically a compass, it’ll point to world spawn. Now that has many problems, not the least of which is people might think it’s still tracking. Another property of compasses, however, is that if it’s trying to track a location in another dimension, it will spin wildly: anyone who saw that would know it wasn’t working.

The problem with that, is that when I give it a location, it makes the compass look enchanted (something I can’t change), and I want it to only look enchanted when it’s in use, not while it’s dormant. And so, we return to the idea of a resource pack. With a resource pack you can add your own textures and overwrite existing ones.

Now you might be asking, how can you add your own textures without your own items or blocks! You just (relatively, ok, I know this is a long post) said you can’t overwrite things because it won’t be registered on the client! And, though having annoyingly interrupted me, you would be right. But, there are things called “predicates” you can use in resource packs. There are a lot of different ones, but one is called “custom model data”, which essentially means: I can give an item an NBT value, and then have it look like a custom texture without overwriting every single compass.

So, I talked to a friend about doing some textures, who obliged, and so I came out with something similar to a recovery compass, but looks a bit more.. tech-y. Of course, my impression of it may be skewed by what I did next, but before I get to that, what I did to make it look dormant is literally just take off the compass needle. Because I could. So now, if it’s not in use (anytime it’s not in tracking mode), it won’t have a needle. Simple!

But something happens when you introduce a resource pack. Something that’s kept me from doing it in ReLife as of yet. It just opens so many possibilities. You can suddenly change absolutely everything about how Minecraft looks, which is kind of daunting. Now, here, it’s not so big because it just lets me add some more things to the tracker, but in ReLife, I have no idea what I might do. I could add custom particles, for instance. I may end up using one on ReLife anyway, but that’s why I haven’t yet. It’s just duanting.

So, back to the Cafei plugin. With a custom resource pack, I can add some fun animations to the tracker. The first one I did was with the ping action, where it runs a little pinging gif. Then, I added a static one. This one runs anytime it error’s, like if you don’t have enough levels or something, or when you start tracking mode. It’s supposed to be like, it’s static while it’s finding it, then the needle pops into existance to show you the way.

Now those are rather simple, and not too hard to add: more custom model data (which is an integer), and I can dictate when it’s in which animation. The unfortunate thing is, this introduces a lot of issues where it could get stuck in an animation and then you won’t be able to use it. I tried to to playtesting and bugfixing, but the fact of the matter is that I couldn’t just tie it up nicely and say I was sure it wouldn’t break, so I had to add a command (/fixtracker) that would fix it.

I generally don’t love including catch-all solutions like that in finished products, because it feels unprofessional, but in this case I couldn’t be sure there wouldn’t be unforseen bugs, so I just added it. If you’re curious, here are the different states: off, pinging, static, tracking

Alright, zherral tracker done! And you can’t really tell from those images, but, personally, I think it looks rather professional in game. Anyway, that’s it for the Cafei SMP plugin, I left out a ton of debugging, partly because I don’t think it would be interesting, and partly because it was long enough ago I don’t remember them all. Regardless, onwards! Whew, this may be my longest post yet.

Cafei Discord Bot

You didn’t think we were done with Cafei yet, right? That would be silly. But don’t worry, this is going to be a significantly shorter section. We have a discord server, of course, and one of the other members coded a discord bot that allows users to enter private channels to discuss things. Yes, direct messages exist, but in my opinion this is more fun. Regardless, since we’re using Exaroton to host the server, I decided to add a status messsage thing, where it shows who’s online, and the state of the server.

However, since the discord bot was coded in python, I had to use that, and there is no Exaroton API for python, unfortunately. It wasn’t terribly difficult though, I just had to tinker around with the websocket library. Essentially, I open a websocket connection to Exaroton, and then Exaroton will send me the updates. The larger issue, though, is that both the discord bot and the websocket connection are what is called “blocking”.

Essentially, when I call the bot’s run method, it won’t execute any of the code after that until the bot is closed, and when I call the websocket’s connect method, same thing. Now, this is an issue when I need both running at the same time. What I ended up having to do was run another thread which started the websocket. Sounds really simple when I put it that way, but it was a bit painful to figure that out intially. Involved a lot of googling.

Anyway, that should be about it for that. I may update it with a few things if I feel like it, but I’ll talk about that in future posts if I end up doing it. As promised, much shorter, and that’s largely because the Exaroton API makes it so easy. I just connect to an address, and every time a player leaves/joins, or the server changes states (i.e. stopped, loading, starting, open, stopping, saving, etc.) it notifies me, and I just have to update the message. Almost done, hang in there!

Harpoons!

I wouldn’t go so far as to say that this is my favorite part of modding Minecraft, but it is pretty fun. Getting to add some just totally new functionality. Not a big minigame like ReLife, rather just.. some random item, that’s new. Anyway, with the Zombie Invasion zone, I believe I mentioned a few types of zombies I was working on last time, but unfortunately, I had to scrap a lot of those ideas. The zombies I was making was better if you’re forced to stay there, and defend against them, but really the idea is that you’re running from them. Hence, harpoon.

The idea of the harpoon is that it’ll be a zombie shooting a crossbow that has a fishing bobber on the end of the arrow when it’s launched, and then it will try to reel you back towards it (and ideally, a swarm of zombies). Alas, it’s not so easy.

Again, we need to break up the problem, then we can tackle each part as a module, then combine the modules at the end to have a finished product. This method is nice for many reasons, not the least of which because it lets you feel like you’re accomplishing something when you’re working on one of those modules.

So, the modules here are: summoning the fishing bobber on the arrow, reeling you back if it catches you, or have the arrow fly back through the air like it’s reeling it back in if not. Sadly, at the time of writing I have only (kind of) completed the first part, so I’ll talk about that.

Unfortunately, it’s not so easy as just adding a fishing bobber entity to the world. How fishing bobbers work in Minecraft, is that they render a line from them back to the owner (the person who cast the fishing rod), which is extremely important for me because I want it tobe very obvious that the harpoonist zombie has you.

However, the way it does that is by storing a player. Not an entity, a player. Things just got a bit more complicated. What I ended up doing was making a new class that extends a player. Within that class, it’s essentially just a wrapper for the zombie entity. All the methods that handle getting the position, rotation, and anything else, just return the same call the the zombie. The final step for that, is telling the client that the fake player exists. I learned from painful experience that the client needs to know the player is there so that it can draw the line to it.

Unfortunately telling the client that a player exists means that it will add that player to the tablist, which I don’t want, but fortunately I can tell it to add the player, then remove the player info, so the entity still exists, but it doesn’t add the player to the tablist. A small amount of packet finagling later, and it launches the fishing bobber.

Since I haven’t coded anything else with that, that’s all on it for now! Also, if anyone is curious what IDE (integrated development environment, lets you code easier) I’m using, I got the JetBrains student pack. Very simple process, I just sent a picture of my school ID to GitHub to get the GitHub stutent pack, which is the same as GitHub Pro, and then logged into GitHub on the JetBrains website and I get all of their IDEs for free.

Wrapup

That’s all for today! I know this post is reaaaally long, so thank you if you stayed till the end. I had a hard time finding motivation to write a post for a couple weeks, and before that was on vacation, so it’s been a bit, but hopefully it at least won’t be quite a month till the next one. Also, I didn’t mention this last time, but my blog officially turned 1 while I was on my 5 month blogging hiatus! Big thank you to anyone who has read it this whole time, the purpose for writing this is to document my work, so I can look back on it in the future, but it’s the people who read it that make it fun. Over the past year, when I’ve taken breaks, a few people have asked where the post was when it didn’t come on schedule, and that’s why I like this, I like writing for people who enjoy it. That being said, this is me signing off, so see you all next post.