As promised, Demo One of Rktcr is now available for download on the game's web page. Please enjoy to the full extent allowed by morality, good sense, and the laws of thermodynamics. (And then drop me an e-mail, IM, or comment.)
News
Thursday, May 30, 2013
Wednesday, May 29, 2013
Rktcr: Preparing for Demo1
This week, I've been preparing the next demo release of Rktcr. I expect to have the build up tomorrow. For now, all I have for you are screenshots and descriptions of a few of the refinements I've added to the game in demo1.
Tree-Style Path Select
Path selection got a major overhaul for demo1. Now it is easier to see what paths exist for a zone (and their relative lengths). Clicking on a portal will immediately select the fastest path to that portal.
Also, the opacity animation in the displayed path is really quite pretty. If I make an announcement video for demo1, I will probably dwell on it longer than necessary.
End Markers
The win markers now show whether you've beaten the par time (and your personal best). Also, there is now a distinguished lose marker for running out of time budget in a zone.
Colorful Text
Character names (and their pronouns) are now colorful. This can make dialog a bit more sensible if you pick weird/pathological names.
Time Control
I've changed the way time control works -- 'a' and 'd' still move backward and forward, but 'w' and 's' have been removed and 'ctrl' now slows time (just like 'shift' speeds it up). This change was based on feedback from Taus and Mike, and on my desire to free up 'w' and 's' for path selection.
Copy/Paste
You can now copy paths out of rktcr using Ctrl-C
and paste them in with Ctrl-V
.
This allows for sharing of paths without having to actually find the .path file.
By way of example, the path shown above is:
1 af169 f2 cf38 f3 af65 f53 af41 f41 af13 f19 af22 f21 af17 f11 af24 f13 af47 f15 af28 f17 af100 f8 af2 f70 af3 f4 af66 f14 cf96
Sunday, May 26, 2013
Why, cl.exe, Why?
When compiling C++ projects (e.g. Rktcr), I use different compilers on different platforms:
Microsoft's cl.exe
from Visual Studio Express Edition on Windows,
Apple's clang++
from XCode on OSX,
and g++
from the GCC on Linux.
(These also use different versions of the C++ Standard Library, for added variability.)
This is great for catching errors in my code, as I get three different sets of static checks and three sets of design decisions (for those memory bugs that "just happen to work" on one system or another). But it also means I get exposed to a fair amount of compiler (and system library) quirkiness.
Today, I'm going to talk about one of the odder bits of behavior I've seen out of cl.exe
(Version 17.00.60315.1 for x86 from Visual Studio 2012 Update 2).
I ran across this a few months back, but have been lax in posting because I didn't have any sort of CSS styling set up for posting code in news.tchow.com ; a situation which I have partially rectified (no syntax highlighting or fancy line numbers; sorry).
The Code
Apologies about the spacing in this code. Blogger apparently converts tabs to single spaces. For reference, using spaces to indent code is wrong.
#include <iostream>
template< int N >
struct TrivialTemplate {
int val;
typedef TrivialTemplate< N > type;
};
struct NoTemplate {
int val;
};
//Consider different types of Coord:
#if COORD==1
typedef NoTemplate Coord; //<-- (1)
#elif COORD==2
typedef TrivialTemplate< 27 > Coord; //<-- (2)
#elif COORD==3
typedef TrivialTemplate< 27 >::type Coord; //<-- (3)
#endif
struct Pt {
union {
Coord arr[2];
struct {
Coord x;
Coord y;
};
};
};
int main(int, char **) {
Pt pt;
pt.x.val = 12;
std::cout << pt.arr[0].val << std::endl;
return 0;
}
This C++ code defines type Pt
, which makes use of a struct wrapped in a union to allow individual coordinate access as pt.x
and pt.y
, and easy coordinate indexing with pt.arr[i]
.
(This method can be extended to allow synonyms like pt.x
and pt.r
and subvectors like pt.xy
or pt.yz
.
I use it in my Vector.hpp.)
The Problem
Notice that the lines marked (1)
, (2)
, and (3)
all define Coord
to be the same type -- a struct
with a single int
as a member -- but in slightly different ways.
So, with the line marked (1)
, things compile fine:
c:\Users\ix\Code\rktcr>cl /nologo /EHsc /W3 /WX /DCOORD=1 weird_template.cpp weird_template.cpp c:\Users\ix\Code\rktcr>weird_template.exe 12 c:\Users\ix\Code\rktcr>
If I use line (2)
, I get some weirdness:
c:\Users\ix\Code\rktcr>cl /nologo /EHsc /W3 /WX /DCOORD=2 weird_template.cpp weird_template.cpp weird_template.cpp(20) : error C2621: member 'Pt::arr' of union 'Pt::<unnamed-tag>' has copy constructor weird_template.cpp(31) : error C2039: 'arr' : is not a member of 'Pt' weird_template.cpp(18) : see declaration of 'Pt' weird_template.cpp(31) : error C2228: left of '.val' must have class/struct/union
So, what happened?
Well, cl.exe
has (presumably) synthesized a copy constructor for Pt::arr
-- which, after some typedef
expansion -- is an array of TrivialTemplate< 27 >
.
Now, having non-trivial constructors and destructors for data in a union is problematic, because the whole point of a union
is that its members overlap in memory.
However, it's also odd that a copy constructor would be synthesized -- after all, TrivialTemplate< 27 >
is functionally identical to NoTemplate
, and no constructor was synthesized there.
Indeed, neither g++
or clang++
have any problems compiling this code.
But here's where it gets really weird.
If I compile with the line marked (3)
active -- that is, if we talk about TrivialTemplate< 27 >
using a typedef
it contains for itself,
one would expect the same error.
Instead, it just works fine:
c:\Users\ix\Code\rktcr>cl /nologo /EHsc /W3 /WX /DCOORD=3 weird_template.cpp weird_template.cpp c:\Users\ix\Code\rktcr>weird_template.exe 12 c:\Users\ix\Code\rktcr>
So, where does that leave me?
Spending time writing workarounds -- in this case, my planar map code (which uses templated classes wrapping integers to make sure it isn't going to overflow) now has a fair number of uses of the somewhat odd-looking BitsInt< N >::self
.
This is certainly a lot nicer than the llvm-gcc
bug that incorrectly passed unions to functions (effectively reordering function parameters).
That bug led to me abandoning Apple-supplied compilers on OSX until clang
was mature enough.
Saturday, May 25, 2013
Rktcr: Stylish Tree Path Select
Today, I continue to progress on Rktcr's tree select. Actually riffling through the paths feels much more natural and usable than before, with a small magnified region around the current tick and markers to indicate important path events.
The styling of the tree is also improved, with different thicknesses for different control signals. I like how this works, and something like it is likely to appear in the next demo release.
Friday, May 24, 2013
Rktcr Path Select Tree
Today, I decided to dive back into revising path select mode in Rktcr. As I mentioned before, this has been a process without a clear design answer.
However, I think I'm getting closer. Today, I worked on a tree-like view and path selection therein. This prototype doesn't yet have flashy graphics on the tree, any sort of magnification for dealing with longer paths, or the ability to do any editing of paths. However, it does give a clear impression of the relation of paths (especially their relative times).
With some markers for important events (gems, finishing), and a fair amount more graphical polish (using lines is... well, not optimal, for sure) I think this has the potential to be the new path select.
Thursday, May 23, 2013
Enlightening Work
After a slow day and a half, the C++ port of Rainbow now has enlightenment working.
The next thing to do is probably to revisit how control works, and build effects to reflect the current state of each frequency band (unclaimed, claiming, following, crashed). These will be different than the mouse-control effects, because with touches one does not know where an inactive control point lies.
Tuesday, May 21, 2013
Utilitarian Level Select
Today, I completed the last pieces of the editing levels puzzle for my C++ port of Rainbow.
The first of these was level loading and saving (which doesn't really have a screenshot representation). The second was level selection:
This is a utilitarian screen designed for use when editing levels. Tapping any level edits it, tapping a '+' spot edits a new blank level.
One final thing I might add add to the editor is some sort of zoom capability (or I could forgo editing large levels on iPhone). The downside of this is it might encourage the creation of levels with detail too small to play on one screen; and I'd rather avoid having to have zoom during play, given that the rainbow's trail is accumulated into a framebuffer.
Monday, May 20, 2013
A More Finished Editor
Today, I continued work on the level editor component of my C++ port of Rainbow. While it isn't as pretty as it could be, it now is entirely functional, and ready to build levels with.
Here's what a little test level looks like in the editor and in the game. Note that the grey box in the lower right of the game view is a button that brings up a "restart/quit" menu -- useful to have so you can get back to the editor.
All that remains is to get peon placement and load/save looped in, and then I should be able to realize my goal of being able to build Rainbow levels "on the go". (Hmm, I wonder how I can get the files back off my phone? I should make sure there's a section for that in the XCode organizer. I think there is.)
Rainbow's Mobile Editor
I've been working on a C++/OpenGL port of Rainbow for a number of reasons. The first is that I like Rainbow, and I thought it might be fun to play on iOS. The second is that there were things I wanted to add to the gameplay that would have complicated the javascript code terribly. The third is that I'd like to be able to be productive on my iPhone.
This is the beginnings of a level editor for Rainbow, running on my iPhone.
I really don't do tile-based games very often, and when I do, the levels are often specified in ASCII. (Indeed, this is what the javascript version of rainbow uses, as you can see.) So this is my first time writing a tile grid editor. So far, it seems to feel pretty good.
Saturday, May 18, 2013
Another Rainbow Drawing Interation
Last night, after some profiling under iOS, it became clear that the method of drawing rainbows that I discussed in my previous post was going to be too heavy. Basically, the nice curve-y geometry of Rainbow's rainbows just contain too many vertices for my iPhone4 to want to render every frame at 60fps.
So, this morning, I revised the drawing code again, this time to accumulate into a framebuffer. This means that the actual amount of bow geometry rendered each frame is quite small, in exchange for the (large) fixed overhead of a full-screen blend. As an added bonus, when two active fronts overlap, the resulting bow is nicely blended (something that no other method I've come up with can achieve).
Unfortunately, this method limits (somewhat) the kind of graphical effects the game can perform. E.g., it can't fade out an entire band that hits a wall, or animate bands along their length. Rather, it could do these things, but I'd have to change the drawing method again, and sacrifice transparent bands and smooth mixing, or pay for another full-screen blend which -- it seems like -- the game can't really afford.
Friday, May 17, 2013
Stylish [Rain]bows
Today's hacking on Rainbow proceeded under Linux with OpenGL3 for output. I've built a helper class that should (fingers crossed) mean that everything transitions cleanly to OpenGL ES (at least as far as streaming vertex attributes).
Today, I worked on making the rainbow draw more nicely. The first step was to start using a special purpose shader.
The shader takes the position of each vertex and three info values -- the index of the frequency band, the position within the frequency band (shown above), and an alpha value which modulates the band's transparency.
A 1D profile texture (with mipmap) provides "fake" antialiasing, while a 1D color texture tints each band.
The above screenshot also shows off, to some extent, decent bow overlapping. In the Javascript version of Rainbow, overlapping is depth-buffer based (basically, bands are ordered based on the amount of time they've been controlled). This wasn't really satisfying, because it could result in hard edges where band orders switched.
This shows my first attempt at resolving the overlap problem by adding smooth fades. Unfortunately, without some sort of matching fade out, there are slight edges induced (especially in the infrared and ultraviolet). Solving this is going to involve slinging a fair number more dynamic vertices around, so I'm going to jump back to iPhone and see how my performance is faring before getting too far into things.
Thursday, May 16, 2013
Rainbow Port Progress: Steering
Today, I continued working on my port of Rainbow from Javascript/WebGL to C++/OpenGL. I got steering in, and tested out collision detection -- [nearly] working first time.
As you can see in the screenshot above, I haven't yet turned on depth testing (to make the stripes render in the proper stacking order). Also, if you are an astute counter of pixels, you will notice that this shot is exactly the size of an iPhone4 display.
Yep, instead of graphical effects, I decided to find out how similar the OpenGL 3.2 and OpenGL ES 2.0 APIs were, and got an iPhone compile working. Turns out: really really similar; though the GLSL flavors are unfortunately somewhat different. Also, using GL_STREAM_DRAW vertex buffer objects instead of just pointing to data in memory seems to be a bad idea on iOS (versus the only game in town in GL3).
So it looks like my mobile version is going to probably have some unfortunate #ifdef magic in place in the graphics code. On the other hand, steering (multiple) rainbow fronts around with multiple fingers is already working (and fun!), and there's a fair amount of room on an iPhone screen to do it in.
Wednesday, May 15, 2013
Porting Rainbow
Today, I took some time away from fiddling with Rktcr's path select mode to work on the OpenGL/C++ port of my WebGL/Javascript game Rainbow. I'm using this port as an opportunity to re-write a lot of my basic infrastructure code, and to add some features to the game.
After one afternoon of work, I have basic drawing working nicely. I'm hoping that tomorrow I can get gameplay going again, test the collision detection routines I wrote today, and maybe even start playing with some of my graphics enhancement ideas.
It would be odd, though not entirely unexpected, if it turns out that the C++ port takes longer than the original javascript version to write.
Tuesday, May 14, 2013
Rktcr: Path Select
Rktcr, as text, is pretty much free association. I know what I want to happen in the game, and it flows relatively freely into the code. This isn't to say that things work properly on the first try -- many of the systems in Rktcr have undergone (and are undergoing) refinement.
Of course, you can motivate this refinement by downloading the demo and providing feedback.
One of the systems in the game that I've been having a fair amount of trouble getting right is path selection. In the current demo, path selection looks like the above shot -- a simple way of picking any completed trajectory through the zone.
This path select doesn't really give one a good idea of the content of paths, or how they vary -- e.g. two paths that are the same except for the last five ticks are displayed entirely separately. It also strikes me that path select mode, with its holistic view of trajectories, is a good place for timeline-based editing.
The (work-in-progress) screenshot above shows my current progress in playing with these ideas. I'm generally liking the two-level timeline (detailed view and overall view) for showing the controls applied along a trajectory, though I dislike the redundancy. Perhaps I will test a magnification-in-context style as well. I also like the faded-wheel trajectory visualization (n.b. this is animated in game, though I'm still trying to find the right sort of curve to use to animate it -- right now it's a sine wave, and feels a bit too smooth).
However, I'm struggling to figure out how to show different paths in this context and how to select between them. In broad outline, I know I want to use a tree structure, which should make common segments of paths clear. Indeed, I have a fair number of sketches of potential display and control options. Unfortunately, no option is clearly the correct one yet.
Thursday, May 2, 2013
Rktcr Demo Zero Video
I believe I recently mentioned that Rktcr Demo Zero is out.
As a further enticement to just go download it, already, I've created the following compelling piece of documentary cinematography.
I'm sure you will agree that it is a great success, though perhaps overburdened with symbols in -- I would say -- the surrealist tradition.
Wednesday, May 1, 2013
Rktcr Demo Zero is out!
The title says it all. Rktcr demo zero has been unleashed upon the world.
Download it now, while you read the rest of this post. (Zip file contains versions for Windows [32-bit], OSX [10.7+; 64-bit], and Linux [32-bit]. You'll need a decent video card to play.)
This is the first public release of the game, and -- thus -- a great opportunity to provide feedback. I'm very interested in what you, the players, enjoy about the game and what you not-so-enjoy. You can let me know by contacting me directly through e-mail or instant message, by commenting on the game over at Steam Greenlight, or simply by commenting on this news post.
I look forward to hearing about your experiences with Rktcr. Have fun!