Reputation: 1756
I'm trying to code a simple DirectX11 engine but I keep getting this strange error and I can't find the problem: I define a Terrain class and a Mesh class and #include the Mesh class in the Terrain class:
the Terrain class definition:
// Terrain.h
#pragma once
#include "Noise.h"
#include "Mesh.h"
class Terrain
{
public:
Terrain(float width, float depth, int numVerticesW, int numVerticesD);
~Terrain();
float GetHeight(float x, float z);
void Draw();
private:
Mesh mMesh; // I get the error on this line
Noise mNoiseGenerator;
std::vector<float> mHeights;
void CreateTerrain(float width, float depth, int numVerticesW, int numVerticesD);
float ComputeHeight(float x, float z, float startFrequency, float startAmplitude, float persistence, int octaves);
};
and the Mesh class definition:
// Mesh.h
#pragma once
#include <d3d11.h>
#include <vector>
#include "Game.h"
class Mesh
{
public:
Mesh();
~Mesh();
template <typename T, unsigned int N>
void LoadVertexBuffer(T data[][N], unsigned int size, bool dynamic = false);
void LoadIndexBuffer(std::vector<unsigned int> indices);
void SetVertexCount(unsigned int vertexCount);
void Bind();
void Draw();
private:
std::vector<ID3D11Buffer*> mVertexBuffers;
std::vector<unsigned int> mStrides;
ID3D11Buffer *mIndexBuffer;
unsigned int mVertexCount;
};
template <typename T, unsigned int N>
void Mesh::LoadVertexBuffer(T data[][N], unsigned int size, bool dynamic)
{
D3D11_BUFFER_DESC bufferDesc = {};
bufferDesc.Usage = dynamic ? D3D11_USAGE_DYNAMIC : D3D11_USAGE_IMMUTABLE;
bufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
bufferDesc.ByteWidth = sizeof(T[N]) * size;
bufferDesc.CPUAccessFlags = dynamic ? D3D11_CPU_ACCESS_WRITE : 0;
bufferDesc.MiscFlags = 0;
bufferDesc.StructureByteStride = 0;
D3D11_SUBRESOURCE_DATA bufferData = {};
bufferData.pSysMem = data;
ID3D11Buffer *buffer;
Game::GetInstance()->GetDevice()->CreateBuffer(&bufferDesc, &bufferData, &buffer);
mVertexBuffers.push_back(buffer);
mStrides.push_back(sizeof(T[N]));
}
When I compile the code I get:
Severity Code Description Project File Line Suppression State
Error C3646 'mMesh': unknown override specifier DirectX11 engine 0.3 c:\users\luca\desktop\programming\code\c++\source\visual studio\directx11 engine 0.3\terrain.h 14
Severity Code Description Project File Line Suppression State
Error C4430 missing type specifier - int assumed. Note: C++ does not support default-int DirectX11 engine 0.3 c:\users\luca\desktop\programming\code\c++\source\visual studio\directx11 engine 0.3\terrain.h 14
I searched the web but most results show missing semicolons or circular inclusion issues but I can't find any.
EDIT I found the issue but I can't explain why my solution works: following the inclusion tree: Terrain.h --> Mesh.h --> Game.h --> Renderer.h --> Terrain.h
eliminating #include "Terrain.h" (since I just declare Terrain * pointers inside the class) and adding it to Terrain.cpp seems to solve the issue. So it must be a matter of circular inclusion, but shouldn't I be guarded against that by using header/include guards?
Upvotes: 15
Views: 43916
Reputation: 179779
Your problem is that #pragma once
only prevents against double inclusion. I.e. it makes the following safe (simplified to make it obvious) :
// Terrain.cpp
#include "Terrain.h"
#include "Terrain.h"
It does not solve circular inclusion, which is far harder to solve automatically. With double inclusion, it's clear which one is first. But a circle has no begin.
Upvotes: 24