Work Post

Jul. 9th, 2021 01:59 am
relee: Picture of Relee Starbreeze, Wizard (Default)
2:01am - Well, I had been hoping to do a great many things today, but mental illness said no. But then I said, I'll do some coding ANYWAY.

It's two in the morning and I'm going to see what I can do about that unintended diagonal movement.

...

Actually, on testing it, it's not so bad. I think I'll leave it in, and keep my alternate movement key in for precision movement.

And that's already in also so I guess the next step is to start stripping down the GreenEnemy class into a generic Enemy class. It'll need to have some way to determine its proper graphic though.

The sprite sheet I'm using now is set up as an atlas texture. Different sprites are selected by only showing part of the picture, so basically all the sprites are the same picture repeated, showing only a tiny window of it.

The problem is, what if I want to put in custom sprites for characters or something? Or use this in some other way? I've been thinking about really open sourcing the project at some point, or using the engine elements in other games. I'd like to have the sprites be seperate, so that I can pick and choose them freely.

Ultimately it would be nice to be able to pick files from outside of the project and use them for sprites, but I'm not sure if that would be sensible at this protype stage.

For now I'm going to split up the tile sheet into individual images to use. I might also switch to the colour version of this sheet, which was something I was considering before, because I realized that the black and white sheet didn't use full black and white, so tinting wasn't an option. I could recolour the black and white sprites, but I'm not sure tinting was ever a good idea, given how it works.

4:13am - Well I did all the art stuff and now the game has nice looking colour sprites and tiles. I was going to start work on peeling the Green out of the Enemy class but it's a little too complicated to start at four am on a night before work.

Work Post

Jul. 7th, 2021 01:56 am
relee: Picture of Relee Starbreeze, Wizard (Default)
1:56am - Well it's late and I have work tomorrow but I'm not sleepy in the slightest so I might as well squeeze in a bit more work.

Last time, I made the PlayerAICore. I could make a BasicMonsterAICore now, but I think I'll skip that for now. I have a lot of other modifications on the TODO list for my GreenEnemy already, and I shouldn't need monsters in the world to test the basic movement of the player I'm implementing.

So! Let's remove the monsters for now...

There's been a longstanding error warning since I took the actor_list out of Level and put it into GameMap, so I should fix that. It's in the restart algorithm, and it should be moved to GameMap, for when the GameMap is restarted.

2:19am - I just eliminated more than half the code in the Level.gd class. The _input() function is gone, the input moved to the player actors for now. Later I'll have to include some for handling the GUI, but it's good for now.

GameMap is fricking huge now though. LOL I moved so much of the code from Level to GameMap and ended up with a longer GameMap class. Well, it works. The Level class just holds the Turn pump and restart method now, and I'm planning to add the Action pump next while refactoring the old Turn pump.

I think once I get the turn pump and action pump working, I should be able to test the game again. I wonder if it'll work after this overhaul?

2:26am - I've run into a snag. The Turn Pump was using the on_turn() method of the Actor to reduce the action_points directly. Now I want it to do a think() first, and reduce action_points based on doing Actions. Is there anything for on_turn() to do anymore?

Well, it'll be where the think() comes in, since an Actor begins its turn by thinking, but then what? It's not going to return action_points spent anymore, now it's just passing the Action Array from the AICore down to the Level. Why not go straight to the source? Hmm... I get the feeling this extra level of seperation will be important later, but I can't put my finger on why. So I'll leave it for now.



3:22am - I've finished it up and corrected lots of little errors and changed lots and lots of things and it should work now but there's a very strange problem. It's unable to load one of my scripts, and I can't figure out why...

It's very puzzling. The error says that I should make sure resources have been imported by opening the project in the editor at least once, and I have done that a few times. Sometimes reloading the editor fixes bugs like that. But it's persisting...

I'll try asking on the Godot Discord.

3:30am - Ahh, while I was typing it into the Godot Discord to ask, I realized that it was searching for it in the wrong place, and so I started opening every class to see what looked for it there, and I solved that problem.

Now there's no errors, but it doesn't work. Seems to be stuck in an infinite loop...

4:20am - Had to do a bunch of remodeling of the Turn and Action pumps. It looks like I really do need to seperate out the player controlled characters, since otherwise they'd be blocking, and if they weren't, then only one actor would run per frame.

4:55am - I've stayed up way way way too late but I did it. I can move around the player on the map again. There's some unexpected behavior where the player can move diagonally without holding a modifier key, but I should be able to fix that next time.

Then I'll overhaul the enemies, and add them back in, and I'll be back to where I started, but with a better foundation. <3

Work Post

Jul. 6th, 2021 07:48 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
7:48pm - Today's been kinda weird, but relaxing. I'm going to start working now, too.

I'm going over the logic for handling player input to see how I got it working before, and figure out how to move it into the AICore system.

It looks like right now in the _process function, it starts by checking if the action timer is stopped. That's a timer that runs after every turn to slow the action down to a speed the player can see.

Then, if it's not the player's turn, it pulls out the Actor on top of the actor_timing_list. It checks if that's a player controlled Actor and if it is, it sets the players_turn property to true, and updates the player's vision.

Then if it's not the player's turn after that, it runs through the current actor's on turn method.

If the current actor is still alive after its turn, it's put back on the actor_timing_list at the back.

Then if they're not still alive, and not the player, it removes them from the game.

Then it starts the action_timer, which counts down until the next turn.

So basically it just loops endlessly when it's the player's turn, until the player's Actor has less than or equal to zero action points.


That's not far from what I wanted it to be, but right now the _input function is setting properties of the Level class depending on what's recently been pressed or released, and then based on what's pressed, it runs a method on the player by a reference.

I want to get rid of that player reference since there is going to be potentially more than one player Actor. So how do I tell the PlayerAICore about input in order to get it to behave properly?

8:46pm - Took a short delay as our groceries were brought up, and read a bunch of documentation on Input in Godot to refresh myself.

One thing I noticed is that while I can handle input in the _input() function, I can also handle it elsewhere, like the _process function, by polling. So, I could make it so that when the player's turn comes up, it sends the input to the Actor, and the Actor can send it on to the AICore perhaps?

The way I've got it now I have to constantly change the state of internal properties for each input type, but I really only need to know the input that's being pressed at the time the process function is running for the Actor in question.

Heck I could put it in the Actor's process function; they're subclassed from Node, so they have one. But I don't think that's wise. I want to centralize my game inputs so I can see them all in one or two places. (Two if I've got UI elements)

So, what about if during the Level._process() function, I check the inputs, during the Player's Turn section? Right now it just loops until the Player's action_points run out. I could switch it from using the player reference to checking if the Actor has a PlayerAICore, and if it does, it passes that info up to the PlayerAICore...

Hmm...

Let's examine an example.

Actor List pops an Actor with a PlayerAICore!

PlayerAICore is detected, set players_turn to true!

Input detected "Move Left"!

Input value is passed to PlayerAICore?

...

Hang on. Maybe it IS a good idea to put the player controls in the PlayerAICore itself? Like, when the turn pump brings up an Actor with a PlayerAICore and runs its think() method, it tests the input in there. Then I'd have the input code localized in the PlayerAICore instead of in the Level, which makes a heck of a lot more sense. Plus, if it doesn't detect any input at all, it doesn't have to reduce action points, so it just returns to the player's turn again and again until they make a move.

That means I wouldn't have to make special exceptions for the player's turn in the turn pump, simpifying it a bit too.

I like this plan! I'm proud to be part of this plan. The part that came up with it and is going to implement it.

Hmm... Now that I think of it, when I implement SenseMap later on, I can use that to show the player what they can see through this system too. Everything is coming together.

Now I guess I just need to code up the AICore base class.

9:16pm - Okay base AICore class made. Next comes the AICore subclasses. But first, I realized that for the AICores to reference the Actions they either need class_name declarations or they need to be referenced in the AICore base class. So, I'm gonna do the former, and that'll take a minute or two...

9:22pm - Or six minutes I guess. Now onto the PlayerAICore.

Now the basic idea is that the think method will test each input action and output an array of Actions matching the player's input.

10:42pm - Well the guys call started suddenly while I was working, so I got in and that slowed me down a bit, but I managed to get the PlayerAICore made, I think. It'll require testing when all of this is ready. ^.^;;

For now I'm done 'cause the guys and I are gonna watch some shows together.

Work Post

Jul. 6th, 2021 02:05 am
relee: Picture of Relee Starbreeze, Wizard (Default)
1:54am - So my TTRPG game was postponed this week since one of my friends and players had family problems. That led to the night ending relatively early, but I'm still up and active. It's hot and my computer's having troubles dealing with the heat and playing video games without locking up, I still don't know if that's really the problem but it seems like a lot of coincidences so far. ^.^;;

Anyways I was saying earlier that the next thing I want to do is the AI scripting.

The idea is to have plug-in scripts for the AIs. That way, I can put in a PlayerAICore that takes its commands from the input and puts them in command stacks, and a BasicMonsterAICore that generates command stacks and returns them... And I can make more as needed. There'll be AIs for all the actor types. But I still need to figure out how they'll work logically. I've got a pretty general idea and I don't think it'll be a problem, but I want to make sure I do it right.

So! In order to be a pluginable AI script, there needs to be a base class for each of the AI scripts to inherit from, thus making them interchangable. The most basic thing the base class needs is a method that all the kids will overload, which returns an Array of commands.

Should it be called think() or get_commands() or what? I'm not sure.

The other thing I'm thinking about, should it directly access the Actor it's connected to's properties, or should it be passed a bundle of info? I know I was thinking of having the AI take a sort of SenseMap from the GameMap that showed what it could see. But I don't have something like that implemented yet. Well, maybe I could make a basic one pretty quick by just giving it a rectangle or square mini map version... Anyways I'm not entirely sure there.

The point is that the AI needs to analyze things outside of it.

I think that means I should pass it the Map that the AI haver is on, at the very least. And maybe a reference to itself as well. That way it'd have access to all the properties of the AI haver...

So it might be like, aicore.think(self, map) and that returns an array of Actions.

I think that's all it would need. Now let's go inside and see how it works...

In the case of the BasicMonsterAICore I think it would start by analyzing the Map to choose its action.

If an enemy is in sense range, attack or move towards them. If an enemy is not in sense range, random wander or idle.

In the first case, it returns a melee_attack or move action in an array.
In the second case, it returns a random move action or an idle action.


And now it occurs to me that these actions are going to have to have an action point cost as well, since that was how the energy system works. I'll have to figure that out as well.

Hmm... I suppose when the Actor runs its action methods, they'll have to include action point decreases.


Alright, that all makes sense. Now what about the PlayerAICore? It's not too hard to change where the input source is for the Monster AI, but the Player's input comes from a whole other system.

Hmm... Part of the reason I'm doing this is to open the game up for the potential of controlling more than one character in the game, so I should reconsider how input is handled.

I'm not really fond of the way the input works right now so I'll probably end up changing it too. It was kind of a kludge.

So let's see. There's a few ways I could make it work, but what's best? I want it to be reactive, but not do the wrong thing. Ideally the player should be able to hold down a movement key to move on subsequent turns. They can do that in the working version I had before, but I don't think that will work with the new Action system, and the AICore system.

Basically when the PlayerAICore gets its think() function run, it should wait for input, unless there's one already waiting, and there should be a delay on how fast it can take a new input. I've already got a Timer for the input like that, it shouldn't be hard to connect. Basically the tricky bit will be looping without locking the program while waiting for input.

I think this part I really need to look at the code for, but it's getting really late and my friends are chatting again, so I might stop here for the night.

3:03am - I think I've got some good ideas in here so far. I should be able to implement something next time.

Work Post

Jul. 5th, 2021 09:05 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
5:49pm - While I might like to spend my Monday afternoon working on my Roguelike Project, I've been ruminating about something I've been procrastinating on for a long time, a story I owe to a friend. So I'm going to take a swing at that first.

6:45pm - I edited some of what I had written before, but things got complicated. The package my Roommate and I were waiting for arrived, and I was thinking of going out to do the errands I had planned. But I realized it was too late to do all of them, so I'm postponing them to tomorrow.

I've also gotten involved with someone in chat, so I'm not sure how much I'll be able to write properly. ^.^;;

8:55pm - Time is fleeting. I've added a few paragraphs to the story but I also had to deal with a lot of other stuff. Now it's getting close to time for my weekly TTRPG game with the guys, so I want to do at least a little coding today too.

9:13pm - It took me a bit to get set up but now I'm ready to code. So my next step is to make the Action class that is the base class for all the other actions.

10:55pm - Alright I've put in an Action class and all the other Action classes. They each have a constructor that takes the Actor doing the action, plus any other neccesary information, and then in their execute function they use that information and the appropriate method on the actor. It should work with any Actors.

Next I can either do the action pump, which will go through the actions on the action stack before passing the turn to the next actor, or I can do the AI system, which generates the action stacks for each Actor. They're both neccesary components before I can test any of this, and they're pretty seperate.

I guess I'll do the AI next unless I change my mind by the time I work again. For now it's time to stop and get on with The Guys.

12:52pm - I forgot to post this until now. :P

Work Post

Jul. 2nd, 2021 12:42 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
12:43pm - Well, I've got an hour and 15 minutes before work, I've had a nice breakfast and prepared a salad for lunch for later, I could either get back into bed and nap for an hour or work on my game.

I'm in a good mood so I'm going to work on my game.

Previouciously on Work Post, I figured out that I needed to make a series of methods in my Actor base class to line up with a series of Action classes I'll make later. They're kinda tied together, coupled we say, but I don't know a way to uncouple them any further and still get the functionality I want, so there we go.

In my Actor class I have a few 'action' functions already from the previous version. attack_actor, attack_for, and move_actor, which I'll have to change or remove. They were direct call methods instead of the command-called method type I'm aiming for.

I think I'll keep the _actor suffix though because all these methods are about actor interactions, and it'll help differentiate a move_actor from things like moving the object.

1:26pm - Okay I've put the stub functions into Actor.

Next I need to make the Action class and its children, one for each action function. Then I make the action function overrides on the Actor subclasses, and then after that, well, let's not get ahead of ourselves.

For now I've set two alarms and I'm going to lay down for about 20 minutes before work. Wish me luck!

Work Post

Jul. 1st, 2021 12:42 am
relee: Picture of Relee Starbreeze, Wizard (Default)
12:43am - With help from some friends I've added to my Actions list.

Move, Idle, Use, Melee Attack, Ranged Attack, Pick Up, Drop, Throw, Wield, Contain, Remove, Receive Attack, Affect, Receive Effect, Talk, Steal, Give, Accept

Most of the ones I added are 'social' Actions, for interacting with other actors in other ways. Talking to, Stealing from, Giving to, and Accepting from. Talking is a heavy lifter like Use since I can connect it to a whole GUI system if I want. I'm not sure how much social stuff I want in the game, though, at least at start. It's a dungeon crawling game, so you should mostly be smacking monsters and grabbing loot. But, what is loot for if not to trade?

Anyways the really important additions are Recieve Attack and Recieve Effect. I concieved of these after I logged off for the night and went to bed last night. When an Actor uses Melee Attack on another Actor, the Action would want to modify the target actor's state, but it's the attacker's action. He shouldn't modify someone else's state directly, in case they have special properties that the Attack doesn't take into account. So, when an Actor attacks another Actor, the First Actor does an Attack Action against the Second, and the Second Actor does a Recieve Attack action from the First. The Attack action determines what effect the Attacker has, and the Recieve Attack action determines what mitigation the Reciever has.

Recieve Effect on the other hand is a more generic form, which could do any sort of changes to stats. It's coupled with Affect, which is what an Item does after you Use it, or an Effect Actor does when it works it's mechanics. It Affects an Actor, and they Recieve Effect to modify their state within their parameters.

1:01am - I think I'm pretty close to being able to start coding again. Which is awkward since I'm typing this on my Chromebook while relaxing in bed. Well let's finish this off first.

My next task, now that I've figured all this out, is to make an Action class, with subclasses of all the action types, so as to reify the Actions like the Command pattern. Also, I must create methods for each action type in the Actor class, so that its children can override them and determine how they will work.

I think I should also peel back the GreenEnemy class into an Enemy class, and use the ActorFactory to make it a Green Enemy by assigning its values, rather than making a different class for every enemy.

1:19am - Alright I think the last thing to do tonight is to put that in my TODO list for later.

Good night everybody!

Work Post

Jun. 30th, 2021 02:02 am
relee: Picture of Relee Starbreeze, Wizard (Default)
2:02am - Well I spent most of the day in bed napping or just beating the heat, and now it's night and I have to do _something_ right? So I'm going to work on my programming projects, specifically the Roguelike Project.

2:29am - I went to the online book Game Programming Patterns to refresh myself on the Command Pattern and I noticed something was off; the thing I'm doing is subtly different.

The command pattern is somewhat tied to the type of actor it's acting on. That is to say, all the actors that can recieve commands must contain the execution code for every command.

I was hoping to seperate the actors from the execution code, but it occurs to me now that it doesn't make sense. Even the way I was going to do it, it would only work on Actors that had the right properties.

I was thinking I'd make Commands that modified the state of Actors directly, but the Command pattern described in Game Programming Patterns runs a method of the Actor class.

Implementing every possible action an actor can take in a single Actor class, and possibly overriding some of those in subclasses, would make for a very lengthy Actor class!

On the other hand, decoupling the things an actor can do from that actor would make it confusing, what could the actor do? You'd have to go down all the commands and figure it out.

2:34am - Let's put this on hold for a bit and try something else. How many things do Actors need to do?

Well for starts there's the steering behaviors. They work a little different in turn based games but they're still relevant.

Seek, Flee, Arrive, Wander, Pursue, and Evade. I know what those mean, so I won't go into detail, but if you're curious do a search for ai steering behaviors.

Those will do movement, and they're pretty generic. Speaking of Generic, what about "Use"? The Use function on Actor could be blank, and overridden on any 'item' Actors that can be used. Then I can program unique behaviors in the class for each item. Could I then import those unique behaviors from a text file along with the stats for Actors? Hmm...

Maybe, if I load in a list of submethods to call when "Use" is run?

Like in the textfile it would be something like

OnUse: "Heal" "Self" "5"

And that would be a healing potion that heals five hp? But what about something more obtuse, like a wand of fireballs maybe?

OnUse: "Shoot" "Target" "AoE" "3" "Fire" "5"

That would run a shoot function that lets you choose a target, and then at that target it makes an AoE of radius 3 that does 5 Fire damage?

I think I could do that for the player's use okay, but what about a Monster or NPC? It would be hard for them to understand what that was in AI. Maybe if the info in the file also included type, it would work. Like, Food and Potion would be different, but similar, and Wand might be another type.

It does seem pretty overcomplicated for this stage of development, though.

Maybe I will stick to hard coding the Actors for now, instead of putting them in a file.

3:00am - Time is fleeting, but I'm not done yet.

So, I've got the steering behaviors and a generic Use method, what else... Probably some kind of Attack, right? Unarmed Actors can attack, armed Actors can attack, weapon Actors can be attacked with... But what about Ranged attacks? Maybe when an Actor is commanded to Attack, it checks if it's holding something, and compares their stats, then uses the best attack available. If that's the item, it runs the attack command of that item instead of its own? Or do item and weapon Actors never get the Attack command used on them?

I think it should be something like, ranged_attack and melee_attack since they operate differently, and it'll be up to the AI which attack to use. Ahh, I thought of something. What if an Actor is holding a non-item, non-weapon actor? It should still get its turn and be able to attack independantly. So yeah, the attack methods of items and weapons will likely be blank.

Steering Behaviors, Use, Melee Attack, Ranged Attack.

Idle. That's a pretty important behavior too. Use time but do nothing.

Move. Yeah the steering behaviors are more for AI, telling you where to move to, so there should be a generic Move action.

3:20am - That can't be all of them but I'm having trouble thinking of more. o.o;;

Use is a real heavy lifter, especially since I don't intend anything in the game to have more than one functional purpose.

There are a couple other Actor types besides Player, NPC, Monster, Item and Weapon though. I wonder if Weapon is an Item? Anyways the others are Effect, Door and Container.

Effects are things like a wall of blazing fire or a teleporter or a magical spell in the course of operation. That sort of thing. They have a location and behaviors just like the other Actors.

Doors are artificial terrain. They switch between open and shut when used. But I'm not sure that's a "Use" case because they aren't in your inventory.

Containers are things like chests that contain items and are open or shut like a door, but that you can't put in your inventory.

Some items are 'containers' in that other actors can be put inside them. Probably all Actors will have a 'contains' or 'inventory' array that has all of the actors inside of it, but not all of them will be able to contain other Actors. You might find a Bone-in Ham in a Chest but you wouldn't put a sword in your Bone-in Ham. Well, not in game anyways.

So, there's also of course things you can't put into a container because it's too big or it just violates the game rules. Like, you can't pick up a chest and you can't put it in your inventory and you can't carry it with you and keep stuff in it. You can pick up a monster but you can't put it in your inventory. I think the player will have a seperate 'hold' inventory for things in their hands that they can pick up but not put in their pocket or whatever. So will other Actors. Or maybe Hold and Wield are synonymous? Anyways that's for later. Right now I'm trying to come up with generic actions.

Maybe you CAN use items that aren't in your inventory, that would work for doors and chests. But what about locks? I could easily make it so that if you have the key, you unlock the door, but what about closing and relocking it? Maybe that's not allowed in gameplay but it doesn't make a lot of sense. :P

At least you can close it again. Maybe it WILL automatically lock if you close it while holding the key? Hmm. I digress again.

So Use saves the day again, but this talk has revealed other things.

Move, Idle, Use, Melee Attack, Ranged Attack

Pick Up, Drop, Wield, Contain, Remove

We've suddenly doubled our actions.

3:40am - I can scarcely believe I've gone another Work Post doing nothing but research and planning, but here we are. I think I need to go to bed now, I have work tomorrow. I'll keep trying to think of other Actions that Actors can take while I rest.

Feel free to suggest some!

Work Post

Jun. 26th, 2021 06:09 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
6:13pm - Well I missed work again today, feel awful about that. But what's done is done, and I have time to do other things. I was going to do another other thing, but Reddit seems to be having troubles, so I'm here instead.

Right now the way my Roguelike Game works, each actor takes a turn based on it's action_points and speed values. When the current actor's action points are greater than zero, they reduce their action points by the cost returned by their on_turn() method. In the case of GreenEnemy it uses the Astar map to find the player and move closer, or attack if it's next to the player. It does that all by code in the on_turn function.

Instead I want to have GreenEnemy (for example) have an AI module which is run to determine its actions, and this AI module will pump out chains of Commands that the Actor will follow.

Let's walk through an example.

GreenEnemy's Turn!

GreenEnemy's AI runs, and looks at the portion of the map in it's senses. Using that sensemap, it sees Player_1 is three squares west!

GreenEnemy's AI returns an Array of Commands. It's a one command array!

Player_1's Turn! They move one square east, foolishly putting them into attack range of the GreenEnemy!

GreenEnemy's AI runs, and looks at the portion of the map in it's senses. Using that sensemap, it sees Player_1 is in attack range.

GreenEnemy's AI returns an Array of Commands. It's a one command array!

GreenEnemy attacks Player_1!


Hmm... There's a problem with this example though. The AI is a black box. We're not seeing what goes on in there. I wasn't expecting it to only give out one command at a time, but that makes sense since it runs every turn for the enemy, so the enemy can only do one thing!

So let's look at the AI.

It gathers a sensemap from the GameMap, which is something I havent't implemented yet. Then it analyzes that sensemap with an algorithm that simulates it's thought process. In this case it would be something like Find Enemy? Enemy Near? Attack Enemy! Enemy Far? Approach Enemy! Don't Find Enemy? Random Wander!

That's a very basic AI.

I was thinking I'd have to make "Commands" for the Actors to act on that would be composed into complex actions, but now I'm not so sure. The commands might all just be one simple thing. Let's look at something other than an enemy or the player. Actors includes Items.


Player_1 sees Bone-in Ham!

Bone-in Ham idles, emptying its action points.

Player_1 stands over Bone-in Ham and picks it up!

Bone-in Ham goes to Player_1's inventory, and idles, emptying its action points.

Player_1 uses Bone-in Ham, eating it!

Bone-in Ham uses Feed to increase Player_1's food level! Bone-in Ham also "dies" disappearing from Player_1's inventory!


That's a multi-action right there! The Bone-in Ham just Fed the player AND died in the same turn! So I will have to use arrays of commands sometimes. And what is "Feed" exactly? That's the sort of command I was thinking about before. Like Attack and Move, but less generic. Something unique to food items.

I need to think more about actions. Should they be hard coded or created outside in a file? I think they should probably be hard coded.

6:49pm - I'm time stamping here 'cause I've been thinkin' a while and it's hard to measure otherwise. Anyways I just realized that "Attack" is more complicated than just "Attack". Moves like Approach and Avoid seem simple enough but they might differ too. Let me explain.

When you "Attack" you might do it in different ways. IRL you might punch, kick, chop, bite, whatever. In the game it's probably divided by unarmed and armed attacks, and armed attacks use the values of an equipped Actor, right? So that differs based on what you've got equipped.

On the other hand, maybe it isn't so different, since you're just attacking with whatever you're equipped with, or your base attack, whichever is highest, right?

The Move commands like Approach and Avoid might differ by your means of locomotion, but as long as that's accounted for in the Approach and Avoid commands, that should still work.


6:55pm - So let's think about the AI again for a bit here. I'm thinking that I could compose several 'default' AI programs, like Enemy or NPC or Item, which behave differently, and in the text file you could pick which one your Actor would use, along with setting its stats and appearance.

I'd have to program any unique AIs in code but it would be a lot harder to make an interpreter to allow unique AI programming from a file.


7:00pm - Alright so I've got my idea for the AI and the Commands, now how to code it... I figure when the actor's on_turn method is used it will run its AI program to get the Command array, then run the function in each Command.

That brings me back to implementing the Command pattern in my game, but I think I can do that with no problems.

Now that I've been thinking so hard for almost an hour though, I want to take a break, so I will.



8:19pm - After my break I went to Reddit to find some Battlemaps maybe for my game, but there weren't any suitable ones.

Now I'm feeling upset and discouraged, and I'm not sure what to do. I don't feel like working right now, and really I feel like if I force myself to do work I'm going to do bad work right now. So, I'm going to relax and play a different game or something.

Work Post

Jun. 26th, 2021 02:46 am
relee: Picture of Relee Starbreeze, Wizard (Default)
2:47am - Well, it's past my bedtime, and I'm in bed, but I'm thinking, and I want to think here in my journal where it'll be recorded for later.

I know that in my Roguelike project I'm using Actors for the Player character/s, NPCs, Enemies, and even Items and Special Effects. I want them to have different abilities that interact with the environment and other actors, and I want them to know how and when to use those abilities.

Up until now, I had hard coded this in the Actor subclasses Player and GreenEnemy. But when I pivoted the Map system so hard, it collided with the Actor system in a way that the whole thing needs to be redone, and why not redo it right, you know?

Ideally the stats, abilities and AI of the Actors should all be in a seperate file. Something I can easily edit to add or remove or modify abilities. Probably some sort of text file, or json or xml maybe.

These would be loaded into the game at runtime. I'm not sure exactly how to do it though, and that's what I've been thinking about.

The most basic abilities that the actors in the game currently have/need are move and attack. How do I make it work without direct coding?

I'm thinking if I directly code a collection of 'commands' that the text file can reference, I can build features outside of the game.

It's sort of like building a mini language.

3:00am - Anyways it's really late and I need to sleep. I'll have to build on this more next time.

Work Post

Jun. 24th, 2021 09:16 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
9:16pm - Late start tonight, but that's okay. I got some good rest today.

First up on the agenda, moving the movement code from the actors into the map. The actors will tell the map to move them, instead of just modifying the map to move themselves.

9:19pm - On closer observation, the code that used to move actors on the map is missing. I must have deleted it without thinking ahead. Or maybe I'm just remembering poorly and the functionality wasn't so complex as to require copying?

Anyways what's past is past and I need to re-write the movement code anyways.

9:46pm - Okay I've moved the movement to the map class. Now the actor just calls a method on the map class to move itself.

The next step is the attack code. Previously, I had set it up so that an actor could attack in a direction, and hit whatever was there. This is a bit tricky now, since there could be many things in that direction, or nothing, or a wall, in addition to just one thing. So, I'm not sure what to do about that.

I'm going to have to halt and give this some thought.

11:50pm - I gave it some thought and I think I'm going to have to implement the Command Pattern to handle actor events, which is a lot more work to implement, but I'll get it done next time. It's too late now.

Work Post

Jun. 23rd, 2021 06:11 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
6:11pm - I should be at work today, but I couldn't do it again. My roomie said I should work on my programming projects instead, if I was going to miss work, and he's right, but I was in a funk for a while first.

Now that I'm out of that funk I'm going to take his advice and do some work of my own.

6:16pm - Phew, nobody said this was going to be easy... Just hit my first wave of flee response. It occurs to me that the flee response I get from this work isn't NEARLY as powerful as doing my job. Alas.

6:29pm - I still keep thinking 'Maybe this would be easier if I started from scratch with what I know now' and I'm pretty sure that's wrong, but the thought occurs to me over and over. ^.^;;

7:57pm - It's hard to believe I've been working almost two hours.

8:05pm - Break time!

9:36pm - Well that was a longish break, but I've had longer before and I'm back now.

I'm currently working on implementing the GameMap method stubs I put in before, so that when I overhaul everything else they have a working map to use.

9:51pm - I've been analyzing the code I've got so far and I'm starting to think that the actor_list should be in the map too, since it's a list of the actors on that map. Meanwhile the actor_timing_list would stay on the Level which manages the sequence of events in the game.

...

Yeah I'm gonna do that.

10:17pm - On closer analysis, this might be the best time to implement the Spatial List for the actors, since they are being contained by the map now.

*looks it up* Oh yeah that's how it's done. It's just a pair of dictionaries.

10:39pm - Okay that should do for the add_actor method. It adds an actor to the map by adding it to each of the actor_map and position_map, and sets up the Actor properties to match it's location and connection to the map, and move it to its position graphically.


11:13pm - Alright time to stop for the night, but I managed to get into The Zone and complete all the method stubs in the GameMap class. Next time, I have to migrate the movement code to the map, and integrate it.

Work Post

Jun. 16th, 2021 12:54 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
12:55pm - Well I didn't get to work more yesterday like I planned, the errands and dinner took longer than I expected, and the call started earlier too.

But I have an hour before work, so I'm going to try and get myself set up.

1:04pm - Alright first I want to take a look at the ActorFactory and see if I can decouple it from the Map. I want it to generate Actors without putting them on the map, so the Level script will have to handle passing them to the Map to be added.

1:08pm - Oh, I found a mistake in my design. The move_actor method in Actor should be in the GameMap instead. I have to pass a ton of map info to the actor, and the actor has to request info from the Map to do the wall detection. They're pretty well coupled, and they shouldn't be.

It's easy to understand though. I was thinking, "The Actor should do what the actor does, and the map should do what the map does" but really, moving things on the map should be done by the map, the Actor class should just tell the map to move it, and not worry about how.

1:24pm - Looking some more, I see that the die function on an actor doesn't remove it from the map, it only makes it invisible then deletes it. That'll have to change too.

1:40pm - I'm already low on time but there's so much to do. It's looking like a lot of my early assumptions were wrong and I'll have to redo a lot of code. But it'll be better for it! I think.

For now I'm going to get ready for work.

Work Post

Jun. 15th, 2021 05:22 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
5:23pm - My new job is pretty easy but I'm still having trouble with stress. I'm going to keep with it for now, and do my best, but the parts that are hard are all inside me.

Anyways it might help to do some work on my Roguelike Game to remind myself that I do other things.



5:39pm - I'm moving some of the code from my Level script to the GameMap script. Specifically the map code.

I think Level will still be responsible for the Actors in the level, while GameMap will handle tracking map details and updating the visual elements.

6:01pm - I moved the Map code from the Level Script to the GameMap script, but I haven't reintegrated things yet, so that'll come next.

I've put some TODO notes in where I need to redo some things, and it looks like I'll need to modify the ActorFactory to not directly apply actors to the map, but rather return them and let the Level script pass them to the GameMap script.

I'll also have a lot of functionality to implement in the new format in general, but that'll have to wait until later. My Roomie is done his stream so we want to go run a few errands and eat out, now that we can. I'm also almost done my drink.

So, I'll save this and leave it for later, hopefully later tonight. I'd just leave it open, but I'm probably going to have to turn off my computer between now and then.

Work Post

Jun. 7th, 2021 08:43 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
8:43pm - Well it's my 'weekend' at last, Monday and Tuesday, and that means I have time to work again. Precious little time, though. On my workdays I've found I can barely do anything but eat, work, and sleep, with maybe a half hour of gaming tacked on, as a treat. I'm not sure having a job is worth the trouble, especially long term, but maybe I can scale back my hours after I've got my debts paid off.

Anyways last time on Work Post, I was hemming and hawing about how to handle the FoV and Fog of War given the option for mutliple player controlled characters.

Generally what's revealed is revealed, so the 'discovery' map can remain on the map...

Yeah, that was what was getting me the most. Then the FoV is just a matter of display, compared to the discovery map. What's fogged or not, rather than the black areas.

So let's look at the GameMap class. It needs certain interfaces. So let's figure those out first, and put in stubs.

9:26pm - I added method stubs to the GameMap class.

9:30pm - Oh time's up. Gotta do Pathfinder now.

Work Post

May. 31st, 2021 03:43 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
3:47pm - Well I'm up, fed, and got some errands done. It's time to work on my projects. But which one?

I've got my Roguelike Project, my Story Trade, and my Farflung Campaign that I could be working on. I feel like I want to do the first more, but the other two feel more important? I'm not sure. They're all good projects, Bront.

Well how about I start working on my Roguelike Project and maybe change projects when I get tired of it or something else comes along?

Now that I've got it all Git'd up and up backed up on Github I can make changes without losing what I had before.

Now just what do I need to change?

I have the list of features that I wanted to implement after the last one, but I wanted to go back and change some things as well.

4:11pm - I'm going over my notes to see what I wanted to change. I'll make a list here and copy it to my TODO list.

Move all Map elements to a GameMap object under Level
Make the GameMap generate or load Maps instead of having them input from a seperate map maker
Modify Action Timer to only work on the player
Convert actor_list to a Spatial List design.
Create a 'View' system for maps, that can output heatmaps for pathfinding

I think that should do for now.

4:26pm - I've started creating the GameMap object but the stress is hitting now.

4:31pm - Yeah too much stress now. Gonna play a game for an hour, gonna set a timer, we'll see how it goes.

5:38pm - Alright that's about an hour of gameplay. Biomutant's pretty good, if a little rough.

5:50pm - I'm looking at the code to figure out what to shift to the new GameMap object, and how to do it, and I'm thinking about the Fog of War. To make it so that different player controlled entities can have different Fog of War views... hum... while I was having that thought a bigger one slipped in.

The idea I'm having is that maybe the actors should contain their own stored map with what they know and can see, instead of having the map hold that information for just one player actor?

Then when a player controlled actor is up, it displays their personal fov instead of a general one. That changes a lot of things though.

6:46pm - After some work I ended up getting distracted, while trying to figure out how to handle the FoV.

6:57pm - I've become completely distracted and lost my focus on the work, so I think I'm going to finish up here for now and focus on other things.

Work Post

May. 30th, 2021 07:19 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
7:19pm - So things got kind of slow when I started my new job two weeks ago. This is the first time I've had the time and energy and everything to work on my projects. It's been a while! Hopefully I'll be able to do a little on my days off, or when I'm not working. Since I'll be working from home my commute is 0 minutes long and that'll give me more me time.

So previously I said I would investigate GitHub and Git and try to put my project on there so that I could start modifying it without losing my changes. Well, that's what I'm doing today.

7:44pm - Ahh the stress just hit. My body's like, 'This looks hard' and I'm like 'Yeah but we're gonna do it'

8:57pm - Wow I spent almost two hours on that? Well anyways I've got the project in a local repo, I'll put it on Github later. I've got some other stuff come up in the mean time, so I'll be doing that.

Work Post

May. 16th, 2021 06:33 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
6:34pm - Well I've spent quite a bit of spare time the last few days trying to figure out a bit more of how the GoRogue library works 'under the hood' and I think I've figured out the key difference to it, as well as figuring out that it can actually modify terrain mid-game.

The key difference from what I've been doing and what GoRogue does is that I was keeping a list of entities like actors and items, while GoRogue uses something called a SpatialList.

7:05pm - Bleh. Got bigtime distracted in the middle of what I was writing.

So, a SpatialList is primarily based on two dictionaries, called _itemMapping and _positionMapping. _itemMapping is a dictionary where the item is the key, and the position of that item is the data. _positionMapping is a dictionary where the position is the key, and the item, or a list of items (depending on the type of spatialmap) is the data. So, you can find out what's at a location using the _positionMapping, or you can find out where an item is using the _itemMapping.

This seems like a good method to track the location of objects in the world, compared to a flat list.

Anyways I just wanted to get that recorded somewhere. I don't think I feel like working more tonight.

Work Post

May. 13th, 2021 09:20 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
6:31pm - Here I go again trying to figure out the code for the GoRogue library.

It's tricky to focus even still. I've been struggling to get myself to do this all afternoon.

6:53pm - Nope, just can't get into the zone. I need to do something else for a while I guess.

9:02pm - I spent an hour trying to play video games and not getting anywhere, then I laid down for an hour but I'm too restless to nap.

Too restless to nap and too tired to work or play, what a piece of work is man, geez.

My roomie suggested the game problem might be solved by writing about games instead of just playing them. I'm willing to try it, but I want to go all the way. Set up a new blog just for game reviews etc.

Unfortunately my Chromebook seems to be having troubles with the internet right now.

Ahh there it's fixed now. Took a bit of fiddling, or maybe the fiddling was pointless and all it took was time. Either way it's working now.

Now I'm going to DreamHost to set up a new blog on my website.

It looks like the connection's still not perfect. I wonder what's going on...

9:20pm - I had to restart my Chromebook but it seems to be okay now.

2:03am - I finished putting together the new blog but then I spent the next few hours with the guys and playing games, so now I'm going to bed. Tomorrow, maybe things will be better. ^.^

Work Post

May. 12th, 2021 06:07 pm
relee: Picture of Relee Starbreeze, Wizard (Default)
5:00pm - So, it's back to work again with me.

I've been thinking about the structure of the game and how I want to change it, but I haven't made any serious progress yet. So let's continue that now.

I've got a MapGenerator that generates an array of MapCell instances, and a MapCell is just a bunch of flags. The first two are simple, but the second two are probably going to have to be changed. They're "is_discovered" and "is_visible" which make the maptiles focused down to a singleplayer game, where only one player can discover or see tiles.

5:10pm - Actually, now that I'm looking at the code, why don't I take a walk through it and see how everything fits together?

It starts with the Level script running its restart_game() function, which is also used to restart the game if it needs to. It initializes everything to the starting point.

First it sets up the actor_list, which is a list of the actors in the scene, then it sets up the actor_timing_list which is an ordered list of the actors in turn.

It sets it to the player's turn, then zeroes out a bunch of game variables, then it makes the map, that should really be in the new GameMap class I want to make. The Level script should tell the map to create itself, rather than creating a map and setting it to the map's variable.

Then it sets up an AStar2D map, which is another thing that should be part of the GameMap class instead of in the Level class. I want the Level class to be a container for the GameMap and the various Actors who live on that GameMap.

After the AStar2D map is set up, the restart_game() function resumes, and creates the actors for the scene. I wonder if the Actors should be collected into some sort of 'Actor Stage' or left on the same level as the GameMap?

Then it initializes the field of view, again that should be in the GameMap class. These should all be set up as a single "GameMap.setup()" call or something.

Then it uses the player's location to determine a field of view, and modifies the cells based on that for the FogOfWarTileMap to update based on the regular terrain map.

Finally it starts the action timer, which is a timer that counts down between each actor's move. I remember I was going to modify this because it only makes sense for the actors on screen, and maybe not even then. It's important for the player though, to prevent them from moving super fast just by holding down the key too long.

That's the initialization phase of the game taken care of. After that, active play begins at the _process() function and the _input() function, two of Godot's builtin functions.

The process function runs every frame, and handles triggering the Actors' on_turn() methods. It's a game pump. The heartbeat of the whole thing.

The input function changes variables based on what keys are pressed, and if those variables are set true, the process function behaves differently.

The Actors do their thing. The tricky bit is how they interact with the Map.

Each Actor has a grid_position that says where on the map they are. There's no accordance for non-wall objects in the AStar2D map; if an Actor wants to move into a square where there's another Actor, it fails. This is a pretty big flaw in my current design, and something I need to change.

And I think that's everything I've got so far. That's it. That's the game.

6:04pm - So there's a lot of changes I'm going to want to make, but I have to figure out how it actually should be first. For that, and since I've been at this an hour now, I'm going to transfer over to my ChromeBook and work on there for a little while, and figure out what I want the game to look like while sitting somewhere else.

6:36pm - This is the sort of thing I want to use for my maps: http://www.roguelib.com/api/GoRogue.SpatialMaps.ISpatialMap-1.html

6:49pm - I'm looking at the GoRogue documentation in order to figure out how to bring what they did over to my project without using the library itself. But I'm losing steam pretty fast...

7:09pm - I realized there was something I wanted to do tonight, and it's happening at 9:30pm. So I want to play some games before then, and time is fleeting, so I'll finish this now.

Next time, I think I'll figure out how to set up an image of my current Roguelike Project on github, and start modifying it to look more like GoRogue's system.

Profile

relee: Picture of Relee Starbreeze, Wizard (Default)
Relee Squirrel

July 2023

S M T W T F S
      1
23456 78
9101112131415
16171819202122
23242526272829
3031     

Syndicate

RSS Atom

Most Popular Tags

Style Credit

Expand Cut Tags

No cut tags
Page generated May. 30th, 2025 01:21 pm
Powered by Dreamwidth Studios