30 Getting the multi player game working.
A day at the office
You may wonder what it was actually like to work at Graftgold developing games. The day for me started at 9 in the morning. We had a flexitime system but I tended to start at the same time. After the kids were delivered to school I had a short 10 minute drive to the office. My wife Julie used to take the car home until she started to work for me doing the accounts payroll. The office was usually already opened by the early starters. I would usually see who was in then go to my office. I had an office at first on my own and then shared with Julie. I would usually switch on my pc and get straight down to coding before any issues of the day interrupted me. In the days before we had a network the only pc connected to the WWW was in my office. That meant I could monitor its use and it also meant we were isolated from hackers and viruses.I nearly always spent part of the day coding. I had plenty of other things to do such as phoning publishers, sorting out any staff issues etc and generally having a walk round now and the to check progress. Generally the team were really productive once we got into a round of development. When things started to happen on screen both artists and programmers got a momentum going. The artist would be keen to see their new graphics in their game and the programmers keen to get the next bit done. If a programmer had a real tricky issue the may ask me or maybe Andrew for ideas. I would sometimes debug a piece of problematic code with a programmer explaining how I went about finding the problem step by step in order to pass on my skills.
I often ended up doing the hardest bits myself after Dominic Robinson left.. For example when we needed a 3d engine on the PC I rapidly put together a system based on code from a cd with a book on 3d programming and Dominic's 3d system for the Amiga and Atari ST. In the earlier years I was also coding complete games myself. It was a lot to do but that was my management style. I would pitch in where I could to get things moving. It was always a race against the clock. Get the monthly milestones done so I could invoice and get the money to pay the wages. I tried to keep money pressures off the staff, I thought it would block creative thought. I was the grease that kept all the wheels turning and got the wages paid on time. Well almost all of the time.
We had morning tea and afternoon coffee breaks together. Someone would make a round of drinks and we would gather in the largest office. This was a time where people would have a look at what each other was doing. We had a flexitime lunch period between 12 and 2. That could be problematic as staff would like to play games in their lunch period. People could be working while others were playing games and that was a distraction. It was important that staff saw all the latest games but I had to keep an eye on long gaming sessions.
Each member of staff had a flexitime sheet to fill in to show the hours they had worked and what they had done in that time. I held a weekly meeting to collect the sheets review progress and set the next weeks objectives. The system worked pretty well. All work hours on the sheets were fed into a project management system so I could see exactly how much time was being spent on each game. This allowed me to check progress against budget and also gave me a realistic start point for estimating the next game. I could calculate whether each staff member was earning their proportion of the budget for a game and this gave me a basis for determining wage levels.
Sometimes I spent ages on the phone or writing difficult letters to publishers. I tried not to have many meetings, it was better to keep everyone productive. Our weekly meeting acted as a project management meeting and also addressed any issues that had arisen. Staff could just come and see me any time if something needed my action, usually machines that broke down or sometimes relations between the staff. On the whole there was a good atmosphere in the office and Friday nights we used to go to the pub together and sometimes go back to the office to have a coffee and play games. I can remember after a frustrating week returning to the office and beating the life out of a stack of boxes.
I usually left shortly after 5.30. There were usually many people still at work especially those who tended to come in later. When we were up against a deadline I would have my dinner then drive into the office for the night shift. As we only had two Playstation development stations because of the huge licence cost I tried to keep them going round the clock. At times I was working into the early hours till the others went home. This all came to a head when I worked to 5.00am for a few weeks and still got in for 9.00 after a brief sleep. If we had a crisis staff would be there with me doing a night session. I never had to pressurise them they were just as keen as me to get the game finished.
I was very proud of the Graftgold team and hated it whenever someone left. I just wished I could afford to pay them the kind of sums that were offered to make them leave. I believe it was the competitive yet cooperative atmosphere that led to the quality of our games.
Deepest Blue Progress.
Last session I was getting the AI mechanics to work properly. I had left the most difficult actions till last but now it was time to get them working. Top of the difficulty list was getting AI ships to upgrade bases. The AI pilot had to navigate to a base that built base parts and dock to a base part. Then they had to travel to the base to be upgraded which might mean travelling down warp paths.They then had to calculate an approach path that ended up in the right place and the right orientation. Then they had to travel down that path and gently dock the part they were carrying to the correct docking point at the base. As I said before "It is only arithmetic". However the docking had to cater for the relative positions of the parts dock point from the carrying ship and the destination dock point relative to the base being upgraded. Also bear in mind the base is made of several mega sections each built of several parts stuck together . The ship itself has several parts stuck together and the base part is also made of several parts. That is a lot of adding up and transforming for each's parts orientation. Plenty of opportunity for an error or two or three or...
I was thrilled when I docked my first piece albeit nowhere near the intended base. At least I could then look at the calculations and see what had gone wrong. I lot of the positions and orientations were relative to another part. When I remembered the system I had devised I finally got it working. Some parts were relative to parent parts, some major parts were relative to the first part of a construction. I also found my new all singing and dancing control routine was miscalculating stopping distances causes some embarrassing crashes of AI ships into the base. Back to the physics. I had had forgotten to allow for increasing acceleration which I found gave more fine control. That made the speed increase not a straight line graph. When you approach something you need to know at what point to start slowing down. Instead of a neat little formula it was more complicated. It also meant my all singing and dancing routine needed to change into a singing routine and a dancing routine. So much for refactoring buts that is what programming is all about. One minute you are collecting like together to avoid repetition and long winded code, the next you are making one piece of code into two to avoid it getting too complicated.
In the heady rush of success I thought I would see what happened if I made a squad and sent them on a base upgrade mission. One ship should pick up the base part and the others protect it. The result was disaster, The squad could not even form up, the ships just flew off in random directions. Something I had done since I had last formed a squad had destroyed their AI. The new control routine was the main suspect and was not using the same target as the old one. I bit of tweaking to the squad fixed the problem. I decided to leave the squad missions for later when I had finished all the mission types. I needed to work out how to decide who does what on a mission, and how the squad behaves when some are doing the mission, others waiting. That needed a bit more thought. The player may be in control of a mission so would have to give orders to the squad.
Player ship leading a mall squad to a mission. |
I decided it was time to get the multiplayer system working. I had been careful to make all player decisions such as joining a mission or switching on/off autopilot occur via an event system that passed into a buffer with the control keys. This whole buffer is designed to fit in a communications packet to send to a server or peer.
I had programmed the machine to machine link via UDP so long ago I could not remember how far I had got or how it worked. I had the basics of the implementation handshakes in the game code and thought I had them talking to each other. When I tried a peer to peer connection the machines stopped talking after the first couple of messages. I spent about a week of really hard debugging getting it sorted out, reminding me of all night sessions at Graftgold trying to get Playstations talking to each other for Motox. You need to set breakpoints in two instances of the code and check each step of the handshake game protocol. My system is very complex as it collects game controls and events and buffers them in a cyclic buffer. The server collects the keysets and sends the set of them to all clients. The send contains the last 4 cycles key sets as UDP is not fail safe. This means 3 consecutive messages can be lost without breaking a game. The whole system has to be started in sync. The keys are read into one buffer while the game is waiting for a previous one to arrive to run a game cycle.
I kept finding both machines waiting for the other in the game cycle. To help find out why I put in some log messages to see who was sending what cycles data. This revealed many bugs including not putting the right cycle number in the message. It got close and closer to working until I was totally bored with the code. I had a few really nasty memory crashes when buffer ends were overwritten. every day it blew up in more wonderful ways. I finally found I had miscalculated where one of the buffers was located so the wrong data was sent. When this was sorted I finally got two screens running side by side. The only problem was each game was reading the same physical keys so each player ship responded when I pressed the controls. I need to test on separate machines, with many players and over the internet. I want to complete the faction AI first as it is the last component before the game will play. The factions have to decide what to ships and bases to build, where to explore, what sectors to defend/attack etc. I have done bits and pieces but it all needs pulling together.
It was a major milestone to get all this done so time for a commit and a backup of the whole code. I am always nervous of backups since the days I put the whole of Simulcra in the Atari ST non recoverable dustbin by accident. I have a hard disk from my first laptop dedicated to backups and copied the whole code after cleaning it to remove temporary files.
Programming Tips.
I use GIT for local code control and have tried to set it up so the hard disk is the master copy but have not managed to get it working so it pushes changes to the master repository. I once did establish a master repository on the remote disk using a standalone control panel. VS does not seem to support multiple repositories ,probably as they want you to use Team Studio. As I am the only one coding I don't need to worry about merging changes. That is a delight I remember from Eurobase. It is so easy for changes to conflict. Sometimes it is easier working alone.Although I have not got my head round all of the GIT commands I make use of it to track changes that I have made. I set up a local repository in VS. I use GIT to check the differences between my current code and the last checked in version. I check in whenever I have finished a piece or work and got everything working. If something stops working in my code it is usually because I have changed something which has had an unexpected effect. It means you can look at any past version of your code. It also means you can resurrect routines that you delete when you cant remember why they are their. It saves commenting out lines of code in case you want to refer to them later. That method is bad leading to messy code. It is all to easy to forget why a line is commented out. Then you wonder whether to leave it out or put it back in.
If you work with more than one person on a program good design and clear demarcation of responsibilities is essential. Although it is possible to merge changes into the same module I consider this extremely dangerous practice. Both changes would need low level testing repeated. It can lead to going round in circles for ages if the changes affect each other in unexpected ways. Source control leads to better programming. You can see who did what when and easily check each others changes for standards and readability. It makes programmers accountable for every line of code they change.
I work alone but like to read the changes I have done to check on myself. It is all too easy in VS on my laptop to change a bit of code inadvertently by accidentally touching the touch pad while I type. It also refreshes my mind on what I was up to.
"Don't Panic!"
5 minutes after writing the above I lost my whole shell code. I must say me heart rate increased when my full rebuild to reproduce all the temporary files after the backup failed all over the place. I thought "don't panic" they must be somewhere, checked the dustbin and had a look around. I used the search facility fro one of the files and found the directory with all its sub directories had moved to inside another directory. I probably had touched the pad by accident while moving the cursor to close the file explorer. Whoever invented that method of moving things without any user confirmation or notification should have to find all the things everyone has lost buy accident.
Great stuff!
ReplyDeleteOne way to avoid accidentally drag-and-dropping directories into each other is to close Windows Explorer windows whenever you aren't using them. On Linux Ubuntu, I can close all file-related windows with 'Quit (all) windows' on Files where (all) is the file window count. I think you can also Undo the action.
The missing game, however, having a name of Simulacra, did it ever exist except as an image?