Skip to content

Instantly share code, notes, and snippets.

@SeijiEmery
Last active August 29, 2015 14:09
Show Gist options
  • Save SeijiEmery/90e5ea87fc97aaa0c652 to your computer and use it in GitHub Desktop.
Save SeijiEmery/90e5ea87fc97aaa0c652 to your computer and use it in GitHub Desktop.
Generate vertices/edges for a n-dimensional cube
// Generate n-dimensional cube vertex/edges (opengl)
void genVerts (int dimensions, float scale = 1.0f) {
assert(dimensions > 1 && dimensions <= 4);
auto posVal = scale * 0.5f;
auto negVal = -posVal;
auto n = 1 << dimensions;
for (auto i = 0; i < n; ++i) {
for (auto bit_scan = 1; bit_scan & (n - 1); bit_scan <<= 1) {
emitVertexComponent( i & bit_scan ? posVal : negVal );
}
}
}
void genEdges (int dimensions) {
// Algorithm based (sort of) on graycode:
// If vertex (0, 0, 0) is at index 000, vertex (0, 1, 0) at index 010, etc., then generating
// edges between the vertices becomes a matter of connecting the vertices whose components differ
// by at most 1 (x-axis, y-axis, or z-axis). To prevent duplicates, we only connect verts *upwards*
// (eg 010 -> 110, 011, but not 110 -> 010 or 100, and do this via connecting an index i to each
// other i w/ one extra set bit (if it exists)). In three dimensions, this works as follows:
// 000 -> 100, 010, 001
// 100 -> 110, 101
// 010 -> 110, 011
// 110 -> 111
// ...
// 111 -> (nothing)
//
assert(dimensions > 1 && dimensions <= 4);
auto n = 1 << dimensions;
auto mask = n - 1;
for (auto i = 0; i < n; ++i) {
for (auto b = 1; b & mask; b <<= 1) {
if ((i & b) == 0) {
emitEdgeIndexPair(i, i | b);
}
}
}
}
@SeijiEmery
Copy link
Author

Shared credit w/ Michael Snowden (the genEdges algorithm and the bitwise optimizations are mine).
For a full graphical impl, see https://gist.github.com/MichaelSnowden/0d03155e3cbd20fcd04c.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment