Widgets are reusable elements of a graphical user interface that displays an information arrangement and provides standardized data manipulation.
We needed to implement many widgets to make a proper GUI for both players, in order to show them more information -got by the sensors data- that they could just get by the streaming video.
During the early stage of our game design, we needed to detect when the CTU had found and achieved access to the bomb. For this purpose we add the IR ball to the game (see 8.1). With the IR Ball available in the game it was quite obvious to include a sensor that could detect the presence if a ball. After a little research we found the IR Seeker V2 from Hitechnic.
This sensor could, detect the direction from where the IR light source is coming. This image below is from Hitechnic homepage gave us the inspiration for the IR Radar.
From the documentation it is stated that two sets of information is available.
There are 5 sensors in a horizontal row in the sensor. The sensor values can be read directly. The sensor itself derive 1 of 9 possible directions as shown in the image above, form the light intensity in these 5 sensors. This direction can also be read form the sensor. From this we sketched our IR Radar Widget.
Testing the new widget and the range of the IR Seeker
Coding the Radar Widget was fairly straight forward. Half way result can be seen above to the right. At this stage we actually thought we could read the intensity in the direction also, but this was a misunderstanding from the interpretation of the documentation and in the end result direction is only on or off, and only one at a time.
Demo of the IR Radar during a game
During the early stage of our game design stage it was quite clear that, while driving around in the city with this narrow camera view, we need to assist the player with more information to ease his navigation in the play field. We decided to build classical obstacle radar. Initially there were some, mechanical issues to overcome, e.g. classical radars rotate continuously in the same direction, but with a wire connected to the sensor, we need to switch direction every 360 degrees. For more mechanical info, see article 5.2.2.
We decided that we wanted to give the Obstacle Radar a classical look’n’feel. So a little research on Google, basically just confirmed what we already had in our minds.
Picture 29: A few inspirational examples from making an image search for a radar on Google
At the time of the OR widget development it was not decided yet what the final size would be. So it was a requirement that the widget should scale to any size. IT was also know from our lab experiment during our Lab session 2: Experimenting with the ultrasonic sensor , that the range is around ~2,5m and no matter what size the final size of the radar was, it should be available for the application creator to scale the range to make the highest resolution of the dots in the radar.
The interface to use the radar was quite simple.
Add the Radar to the GUI. It inherited from JPanel and can be treated as such. Setting up the radar requires only 2 settings from the application GUI:
· setCmToPixelRelation(double factor)
This factor is used to set a factor of how many pixels should represent the distance 1 cm on the size of the radar. This was a functional solution, but if we should spend more time in improving the radar widget, it would be more use full to set the range of the radar, and then this Cm to Pixel calculation can be calculated automatically.
· setObjectAge(int timeInMs)
As it can be seen in the video, the objects detected by the radar, fades as they get older. This setting sets the lifespan of the objects. Setting this to 5000 indicates that instantly an object is added it will appear at full brightness, and the it will laniary fade over the next 5000ms to have the same color as the background, when this occurs it will be removed from the array of objects known by the radar.
To put the radar in action only thing required is to call the function addObject(int Xcm, int Ycm) to indicate where there is a new obstacle detected. The rest is handled by the radar.
The final result can be seen below.
Picture 31 : Final result for the obstacle radar widget
The distance rings all indicate 1 meter. Hence this image if from before we achieved the correct scaling. The actual calculation of the radar dots is done on the brick. It is a simple SIN/COS calculation based on the distance measured by the sensor and the angle measured by the tacho in the LEGO motor. (see 7.2.1 for the calculation)
A last minute improvement on this widget was to overlay the compass direction of the unit. This can also be seen above. To use this function only two functions are required.
· setShowCompass(bool enable)
This function is used to enable the compass feature. It is disabled by default.
· setCompassDirection(int angleDeg)
This is used to set the last know direction sent from the unit.
We considered improvements for the Obstacle radar. In most common radars there is a sweep indication of where the scanner is currently searching for obstacles. We considered to add this feature, but were afraid to overload the BT bandwidth by adding another 200-400 mgs/second in order to achieve a fluent correct sweep, so this was omitted. But with more time we could implement a sweep that would simulate the sweep, and only require re sync at every time we switch direction, show should work good enough for a game concept.
The game was designed to include a bomb and our originally idea was just to present the button press sequence. For the user to remember similar to the image below
This would have worked perfectly for the game. But we keep thinking that normally (in movies) when you defuse a bomb you have to cut the right wires. So we decided to combine this idée with wire cutting. So instead of pressing a color sequence, you cutting a colored wire sequence. It is the exact same exercise and complexity, but more fun in the game context.
So we found an image of some pretty wires on the net.
From this image we just did a little make over using GIMP, to achieve the GFX we wanted. And we drew a se of uncut wires and a set of cut wires, in the color range we required. The result can be seen in the two images below.
With this graphics available it was quite simple to show the color sequence generated by the bomb.
The widget only requires a few functions to use it:
· setSequence(String sequence)
The string must consist of the letters g, b, r, y, each representing the next color in the sequence, Green, Blue, Red, and Yellow respectively. The string can be any length from 1 to 10 chars, the widget will adjust accordingly. And the color combination can be any possible combination.
· setShowColor(bool enabled)
This function will either allow the player to show the colors of the current wires or turn all the wires white. This is used in the game, when the player presses the first color. Then all the wires turn white, and the player is required to remember the rest.
· nextWireColorCut(char color)
This function will just allow the application designer just to forward the color press from the user and the widget will handle the rest. If the color is right, the widget will show the wire as cut.. if it is wrong it will clear the screen and just await a new sequence from the bomb.
One improvement for the architecture of the game should be revised here. Both this widget and the bomb independently do this evaluation of the wire cur, and this could potentially lead to an inconsistent state between the wire cut widget and the bomb. This should in an improved version of the game only be evaluated one place. In our model I would be most appropriate for the bomb to tell if it was a success or not.
The widget in action can be seen in the video below.