我正在使用Glut在OpenGL中构建一个赛车游戏,我在细节上有点迷失。首先,任何建议或路线图都会非常棒。
到目前为止,我的想法是:
(*):我不确定这两个的顺序。
所以我开始使用没有树实现的模拟动态,结果对我来说是一个巨大的混乱。有什么办法可以让你想到一些可以帮助我建立这样一棵树以用于赛车游戏的东西吗?
我想到了类似的东西,但我不知道如何实现它。
红色是静态的,黄色是动态节点
答案 0 :(得分:10)
我建议与@bezad完全相反。
从单车和无限的道路开始。
将渲染和动态问题分解为两个完全不同的东西。常见的Car
更新和/或是CarRenderModel
和CarPhysicsModel
之间的链接。
Car
放入GL场景的形状取决于Car
。
除此之外,这意味着您可以在屏幕上显示一个非常简单的Car
,并为其添加一个非常简单的物理模型,并使Car
更漂亮或让它在物理上表现得更好更好,而不必将两者结合在一起。理想情况下,在每个阶段你都有可玩的。
所以,一辆长方形的车,5长3宽1高单位。一条宽13个单位的道路,永远持续下去。固定的相机。也许是一个视野。第一个物理模型是火箭飞船,每按一下箭头键,汽车就会在那个方向上获得x单位/秒的速度。请注意,此车不会旋转 - 它是轴对齐的。如果汽车离开道路,它会爆炸,“游戏”结束。
您现在屏幕上有一些响应用户输入的内容。你可以花时间制作一个更漂亮的汽车模型(车轮等),或者你可以改进汽车物理和控制模型(方向!角度!打破!=加速!),或者你可以使环境更有趣(添加黑色 - 白色条纹让你可以看到道路边缘的速度。道路附近的越野部分,也许树木会炸毁汽车),或者你可以让相机更有趣(比如,它留在汽车,看着它的肩膀。)
现在,对于动态,我会使用来自汽车互动的不同代码来对待宇宙车交互,只是为了保持我的理智不变。汽车无法改变环境。
这意味着你可以比汽车互动更容易地写出一堆汽车 - 宇宙互动。
...
在C ++中构建任意树很容易。
#include <vector>
#include <memory>
#include <string>
struct MyTree;
typedef std::unique_ptr<MyTree> upTree; // punt on memory management!
struct MyBaseNode;
typedef std::unique_ptr<MyBaseNode> upNode;
struct MyTree {
std::vector<upTree> children;
upNode node;
MyTree( upNode node_ ):node(std::move(node_)) {}
private:
// if C++11 compiler, use these:
MyTree( MyTree const& ) = delete;
MyTree& operator=( MyTree const& ) = delete;
// if C++03, use these:
// MyTree( MyTree const& ); // no implementation
// MyTree& operator=( MyTree const& ); // no implementation
};
upTree make_tree(upNode node) { return upTree( new MyTree(std::move(node)) ); }
enum EOrder{ eFirst, eMiddle, eLast };
template<typename Functor>
void walk_tree( upTree const& tree, Functor f, bool bFirst = true, bool bLast = true) {
if (!tree) return;
f( tree, bFirst, bLast );
for (auto it = tree->children.begin(); it != tree->children.end(); ++it) {
bool bChildFirst = (it == tree->children.begin());
bool bChildLast = ((it+1) == tree->children.end());
walk_tree( *it, f, bChildFirst, bChildLast );
}
}
struct MyBaseNode {
virtual ~MyBaseNode() {};
// put things that your tree nodes have to be able to do here
// as pure virtual functions...
virtual std::string MyName() const = 0;
};
struct CarsNode : MyBaseNode {
// cars node implementation!
virtual std::string MyName() const /*override*/ { return "I am a bunch of CARS!"; }
};
upNode make_cars() { return upNode( new CarsNode() ); }
struct CarNode : MyBaseNode {
// car node implementation!
virtual std::string MyName() const /*override*/ { return "I am a CAR!"; }
};
upNode make_car() { return upNode( new CarNode() ); }
struct RoadNode : MyBaseNode {
// car node implementation!
virtual std::string MyName() const /*override*/ { return "I am a ROAD!"; }
};
upNode make_road() { return upNode( new RoadNode() ); }
#include <iostream>
void tree_printer_func( upTree const& tree, bool bFirst, bool bLast ) {
if (bFirst) std::cout << "[ ";
if (tree->node) {
std::cout << tree->node->MyName().c_str();
} else {
std::cout << "nullNode";
}
if (bLast) {
std::cout << " ]\n";
} else {
std::cout << ", ";
}
}
int main() {
upTree root = make_tree(upNode());
upTree carsTree = make_tree(make_cars());
carsTree->children.push_back( make_tree( make_car() ) );
carsTree->children.push_back( make_tree( make_car() ) );
root->children.push_back( std::move(carsTree) );
upTree roadTree = make_tree(make_road());
root->children.push_back( std::move(roadTree) );
walk_tree( root, tree_printer_func );
}
以上是非常粗糙的(例如,我没有在打印机中完全正确地处理端节点处理),但它在C ++中演示了一种非同质的,非泄漏的,n-ary树结构。
答案 1 :(得分:2)
如果我理解你的话,你就会想到如何开发项目(你的游戏)。我会从较小的物体开始,比如轮胎,车身,其他汽车零件和汽车,然后是环境,地形和公路轨道等。最后是世界,将所有其他物体放在一起。希望它有所帮助。
答案 2 :(得分:2)
您可以考虑在gamdev.stackexchange上发布此内容;你可能会在那里得到更好的答案。
话虽如此,我同意评论中Michael IV的建议。你最好的选择是从一个免费的开源游戏引擎开始。即使你想制造自己的引擎,首先用现有引擎构建引擎,也会为你提供有关如何实现它的宝贵意见。
Here is a relevant answered question on gamedev regarding which engine to use.