mirror of
https://github.com/MaSzyna-EU07/maszyna.git
synced 2026-07-22 06:59:18 +02:00
build 170511. crossroad generation for vbo render path. partial unification of generation and render functions for tracks and ground nodes
This commit is contained in:
@@ -230,9 +230,7 @@ bool TSpeedPos::Update(vector3 *p, vector3 *dir, double &len)
|
|||||||
if( fDist < 50.0 ) {
|
if( fDist < 50.0 ) {
|
||||||
// old sceneries use trick of placing 'helper' semaphores underground, which can lead to vehicles running over them instead of stopping in front of them
|
// old sceneries use trick of placing 'helper' semaphores underground, which can lead to vehicles running over them instead of stopping in front of them
|
||||||
// to account for it at short distances we redo distance calculation on 2d plane
|
// to account for it at short distances we redo distance calculation on 2d plane
|
||||||
fDist = glm::dot(
|
fDist = glm::length( glm::vec3( v.x, 0.0, v.z ) );
|
||||||
glm::vec3( v.x, 0.0, v.z ),
|
|
||||||
glm::vec3( dir->x, 0.0, dir->z ) );
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
205
Ground.cpp
205
Ground.cpp
@@ -290,16 +290,13 @@ void TGroundNode::RaRenderVBO()
|
|||||||
glDrawArrays(iType, iVboPtr, iNumVerts); // Narysuj naraz wszystkie trójkąty
|
glDrawArrays(iType, iVboPtr, iNumVerts); // Narysuj naraz wszystkie trójkąty
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef EU07_USE_OLD_RENDERCODE
|
||||||
void TGroundNode::RenderVBO() { // renderowanie obiektu z VBO - faza nieprzezroczystych
|
void TGroundNode::RenderVBO() { // renderowanie obiektu z VBO - faza nieprzezroczystych
|
||||||
|
|
||||||
switch( iType ) { // obiekty renderowane niezależnie od odległości
|
switch( iType ) { // obiekty renderowane niezależnie od odległości
|
||||||
case TP_SUBMODEL:
|
case TP_SUBMODEL:
|
||||||
TSubModel::fSquareDist = 0;
|
TSubModel::fSquareDist = 0;
|
||||||
#ifdef EU07_USE_OLD_RENDERCODE
|
|
||||||
return smTerrain->RenderDL();
|
|
||||||
#else
|
|
||||||
GfxRenderer.Render( smTerrain );
|
GfxRenderer.Render( smTerrain );
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
double distancesquared = SquareMagnitude( pCenter - Global::pCameraPosition ) / Global::ZoomFactor;
|
double distancesquared = SquareMagnitude( pCenter - Global::pCameraPosition ) / Global::ZoomFactor;
|
||||||
@@ -334,15 +331,9 @@ void TGroundNode::RenderVBO() { // renderowanie obiektu z VBO - faza nieprzezroc
|
|||||||
if( linealpha > 255 )
|
if( linealpha > 255 )
|
||||||
linealpha = 255;
|
linealpha = 255;
|
||||||
float r, g, b;
|
float r, g, b;
|
||||||
#ifdef EU07_USE_OLD_LIGHTING_MODEL
|
|
||||||
r = floor( Diffuse[ 0 ] * Global::ambientDayLight[ 0 ] ); // w zaleznosci od koloru swiatla
|
|
||||||
g = floor( Diffuse[ 1 ] * Global::ambientDayLight[ 1 ] );
|
|
||||||
b = floor( Diffuse[ 2 ] * Global::ambientDayLight[ 2 ] );
|
|
||||||
#else
|
|
||||||
r = floor( Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ] ); // w zaleznosci od koloru swiatla
|
r = floor( Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ] ); // w zaleznosci od koloru swiatla
|
||||||
g = floor( Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ] );
|
g = floor( Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ] );
|
||||||
b = floor( Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ] );
|
b = floor( Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ] );
|
||||||
#endif
|
|
||||||
glColor4ub( r, g, b, linealpha ); // przezroczystosc dalekiej linii
|
glColor4ub( r, g, b, linealpha ); // przezroczystosc dalekiej linii
|
||||||
GfxRenderer.Bind( 0 );
|
GfxRenderer.Bind( 0 );
|
||||||
|
|
||||||
@@ -436,6 +427,8 @@ void TGroundNode::RenderAlphaVBO()
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
void TGroundNode::Compile(bool many)
|
void TGroundNode::Compile(bool many)
|
||||||
{ // tworzenie skompilowanej listy w wyświetlaniu DL
|
{ // tworzenie skompilowanej listy w wyświetlaniu DL
|
||||||
if (!many)
|
if (!many)
|
||||||
@@ -451,49 +444,28 @@ void TGroundNode::Compile(bool many)
|
|||||||
}
|
}
|
||||||
if ((iType == GL_LINES) || (iType == GL_LINE_STRIP) || (iType == GL_LINE_LOOP))
|
if ((iType == GL_LINES) || (iType == GL_LINE_STRIP) || (iType == GL_LINE_LOOP))
|
||||||
{
|
{
|
||||||
#ifdef USE_VERTEX_ARRAYS
|
|
||||||
glVertexPointer(3, GL_DOUBLE, sizeof(vector3), &Points[0].x);
|
|
||||||
glDrawArrays(iType, 0, iNumPts);
|
|
||||||
#else
|
|
||||||
glBegin(iType);
|
glBegin(iType);
|
||||||
for (int i = 0; i < iNumPts; i++)
|
for (int i = 0; i < iNumPts; i++)
|
||||||
glVertex3dv(&Points[i].x);
|
glVertex3dv(&Points[i].x);
|
||||||
glEnd();
|
glEnd();
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
else if (iType == GL_TRIANGLE_STRIP || iType == GL_TRIANGLE_FAN || iType == GL_TRIANGLES)
|
else if (iType == GL_TRIANGLE_STRIP || iType == GL_TRIANGLE_FAN || iType == GL_TRIANGLES)
|
||||||
{ // jak nie linie, to trójkąty
|
{ // jak nie linie, to trójkąty
|
||||||
TGroundNode *tri = this;
|
TGroundNode *tri = this;
|
||||||
do
|
do
|
||||||
{ // pętla po obiektach w grupie w celu połączenia siatek
|
{ // pętla po obiektach w grupie w celu połączenia siatek
|
||||||
#ifdef USE_VERTEX_ARRAYS
|
// TODO: eliminate these calls, they're duplicated by setup part in the unified render function
|
||||||
glVertexPointer(3, GL_DOUBLE, sizeof(TGroundVertex), &tri->Vertices[0].Point.x);
|
|
||||||
glNormalPointer(GL_DOUBLE, sizeof(TGroundVertex), &tri->Vertices[0].Normal.x);
|
|
||||||
glTexCoordPointer(2, GL_FLOAT, sizeof(TGroundVertex), &tri->Vertices[0].tu);
|
|
||||||
#endif
|
|
||||||
glColor3ub(tri->Diffuse[0], tri->Diffuse[1], tri->Diffuse[2]);
|
glColor3ub(tri->Diffuse[0], tri->Diffuse[1], tri->Diffuse[2]);
|
||||||
GfxRenderer.Bind(Global::bWireFrame ? 0 : tri->TextureID);
|
GfxRenderer.Bind(Global::bWireFrame ? 0 : tri->TextureID);
|
||||||
#ifdef USE_VERTEX_ARRAYS
|
|
||||||
glDrawArrays(Global::bWireFrame ? GL_LINE_LOOP : tri->iType, 0, tri->iNumVerts);
|
|
||||||
#else
|
|
||||||
glBegin(Global::bWireFrame ? GL_LINE_LOOP : tri->iType);
|
glBegin(Global::bWireFrame ? GL_LINE_LOOP : tri->iType);
|
||||||
for (int i = 0; i < tri->iNumVerts; i++)
|
for (int i = 0; i < tri->iNumVerts; i++)
|
||||||
{
|
{
|
||||||
glNormal3d(tri->Vertices[i].Normal.x, tri->Vertices[i].Normal.y,
|
glNormal3dv(&tri->Vertices[i].Normal.x);
|
||||||
tri->Vertices[i].Normal.z);
|
|
||||||
glTexCoord2f(tri->Vertices[i].tu, tri->Vertices[i].tv);
|
glTexCoord2f(tri->Vertices[i].tu, tri->Vertices[i].tv);
|
||||||
glVertex3dv(&tri->Vertices[i].Point.x);
|
glVertex3dv(&tri->Vertices[i].Point.x);
|
||||||
};
|
};
|
||||||
glEnd();
|
glEnd();
|
||||||
#endif
|
|
||||||
/*
|
|
||||||
if (tri->pTriGroup) //jeśli z grupy
|
|
||||||
{tri=tri->pNext2; //następny w sektorze
|
|
||||||
while (tri?!tri->pTriGroup:false) tri=tri->pNext2; //szukamy kolejnego należącego do
|
|
||||||
grupy
|
|
||||||
}
|
|
||||||
else
|
|
||||||
*/
|
|
||||||
tri = NULL; // a jak nie, to koniec
|
tri = NULL; // a jak nie, to koniec
|
||||||
} while (tri);
|
} while (tri);
|
||||||
}
|
}
|
||||||
@@ -552,17 +524,14 @@ void TGroundNode::RenderHidden()
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifdef EU07_USE_OLD_RENDERCODE
|
||||||
void TGroundNode::RenderDL()
|
void TGroundNode::RenderDL()
|
||||||
{ // wyświetlanie obiektu przez Display List
|
{ // wyświetlanie obiektu przez Display List
|
||||||
switch (iType)
|
switch (iType)
|
||||||
{ // obiekty renderowane niezależnie od odległości
|
{ // obiekty renderowane niezależnie od odległości
|
||||||
case TP_SUBMODEL:
|
case TP_SUBMODEL:
|
||||||
TSubModel::fSquareDist = 0;
|
TSubModel::fSquareDist = 0;
|
||||||
#ifdef EU07_USE_OLD_RENDERCODE
|
|
||||||
return smTerrain->RenderDL();
|
|
||||||
#else
|
|
||||||
GfxRenderer.Render( smTerrain );
|
GfxRenderer.Render( smTerrain );
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
double distancesquared = SquareMagnitude(pCenter - Global::pCameraPosition) / Global::ZoomFactor;
|
double distancesquared = SquareMagnitude(pCenter - Global::pCameraPosition) / Global::ZoomFactor;
|
||||||
@@ -605,15 +574,9 @@ void TGroundNode::RenderDL()
|
|||||||
if( linealpha > 255 )
|
if( linealpha > 255 )
|
||||||
linealpha = 255;
|
linealpha = 255;
|
||||||
float r, g, b;
|
float r, g, b;
|
||||||
#ifdef EU07_USE_OLD_LIGHTING_MODEL
|
|
||||||
r = floor( Diffuse[ 0 ] * Global::ambientDayLight[ 0 ] ); // w zaleznosci od koloru swiatla
|
|
||||||
g = floor( Diffuse[ 1 ] * Global::ambientDayLight[ 1 ] );
|
|
||||||
b = floor( Diffuse[ 2 ] * Global::ambientDayLight[ 2 ] );
|
|
||||||
#else
|
|
||||||
r = floor( Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ] ); // w zaleznosci od koloru swiatla
|
r = floor( Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ] ); // w zaleznosci od koloru swiatla
|
||||||
g = floor( Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ] );
|
g = floor( Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ] );
|
||||||
b = floor( Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ] );
|
b = floor( Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ] );
|
||||||
#endif
|
|
||||||
glColor4ub( r, g, b, linealpha ); // przezroczystosc dalekiej linii
|
glColor4ub( r, g, b, linealpha ); // przezroczystosc dalekiej linii
|
||||||
GfxRenderer.Bind( 0 );
|
GfxRenderer.Bind( 0 );
|
||||||
|
|
||||||
@@ -689,15 +652,9 @@ void TGroundNode::RenderAlphaDL()
|
|||||||
float linealpha = 255000 * fLineThickness / ( distancesquared + 1.0 );
|
float linealpha = 255000 * fLineThickness / ( distancesquared + 1.0 );
|
||||||
if (linealpha > 255)
|
if (linealpha > 255)
|
||||||
linealpha = 255;
|
linealpha = 255;
|
||||||
#ifdef EU07_USE_OLD_LIGHTING_MODEL
|
|
||||||
r = Diffuse[ 0 ] * Global::ambientDayLight[ 0 ]; // w zaleznosci od koloru swiatla
|
|
||||||
g = Diffuse[ 1 ] * Global::ambientDayLight[ 1 ];
|
|
||||||
b = Diffuse[ 2 ] * Global::ambientDayLight[ 2 ];
|
|
||||||
#else
|
|
||||||
float r = Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ]; // w zaleznosci od koloru swiatla
|
float r = Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ]; // w zaleznosci od koloru swiatla
|
||||||
float g = Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ];
|
float g = Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ];
|
||||||
float b = Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ];
|
float b = Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ];
|
||||||
#endif
|
|
||||||
glColor4ub( r, g, b, linealpha ); // przezroczystosc dalekiej linii
|
glColor4ub( r, g, b, linealpha ); // przezroczystosc dalekiej linii
|
||||||
GfxRenderer.Bind( 0 );
|
GfxRenderer.Bind( 0 );
|
||||||
|
|
||||||
@@ -720,6 +677,7 @@ void TGroundNode::RenderAlphaDL()
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
//------------------ Podstawowy pojemnik terenu - sektor -----------------------
|
//------------------ Podstawowy pojemnik terenu - sektor -----------------------
|
||||||
@@ -1093,8 +1051,7 @@ void TSubRect::LoadNodes()
|
|||||||
case GL_LINE_STRIP:
|
case GL_LINE_STRIP:
|
||||||
case GL_LINE_LOOP:
|
case GL_LINE_LOOP:
|
||||||
n->iVboPtr = m_nVertexCount; // nowy początek
|
n->iVboPtr = m_nVertexCount; // nowy początek
|
||||||
m_nVertexCount +=
|
m_nVertexCount += n->iNumPts; // miejsce w tablicach normalnych i teksturowania się zmarnuje...
|
||||||
n->iNumPts; // miejsce w tablicach normalnych i teksturowania się zmarnuje...
|
|
||||||
break;
|
break;
|
||||||
case TP_TRACK:
|
case TP_TRACK:
|
||||||
n->iVboPtr = m_nVertexCount; // nowy początek
|
n->iVboPtr = m_nVertexCount; // nowy początek
|
||||||
@@ -1180,10 +1137,10 @@ void TSubRect::RenderDL()
|
|||||||
{ // renderowanie nieprzezroczystych (DL)
|
{ // renderowanie nieprzezroczystych (DL)
|
||||||
TGroundNode *node;
|
TGroundNode *node;
|
||||||
RaAnimate(); // przeliczenia animacji torów w sektorze
|
RaAnimate(); // przeliczenia animacji torów w sektorze
|
||||||
for (node = nRender; node; node = node->nNext3)
|
for( node = nRender; node; node = node->nNext3 )
|
||||||
node->RenderDL(); // nieprzezroczyste obiekty (oprócz pojazdów)
|
GfxRenderer.Render( node ); // nieprzezroczyste obiekty (oprócz pojazdów)
|
||||||
for (node = nRenderMixed; node; node = node->nNext3)
|
for (node = nRenderMixed; node; node = node->nNext3)
|
||||||
node->RenderDL(); // nieprzezroczyste z mieszanych modeli
|
GfxRenderer.Render( node ); // nieprzezroczyste z mieszanych modeli
|
||||||
for (int j = 0; j < iTracks; ++j)
|
for (int j = 0; j < iTracks; ++j)
|
||||||
tTracks[j]->RenderDyn(); // nieprzezroczyste fragmenty pojazdów na torach
|
tTracks[j]->RenderDyn(); // nieprzezroczyste fragmenty pojazdów na torach
|
||||||
#ifdef EU07_SCENERY_EDITOR
|
#ifdef EU07_SCENERY_EDITOR
|
||||||
@@ -1237,13 +1194,10 @@ void TSubRect::RenderDL()
|
|||||||
void TSubRect::RenderAlphaDL()
|
void TSubRect::RenderAlphaDL()
|
||||||
{ // renderowanie przezroczystych modeli oraz pojazdów (DL)
|
{ // renderowanie przezroczystych modeli oraz pojazdów (DL)
|
||||||
TGroundNode *node;
|
TGroundNode *node;
|
||||||
for (node = nRenderMixed; node; node = node->nNext3)
|
for( node = nRenderMixed; node; node = node->nNext3 )
|
||||||
node->RenderAlphaDL(); // przezroczyste z mieszanych modeli
|
GfxRenderer.Render_Alpha( node ); // przezroczyste z mieszanych modeli
|
||||||
for (node = nRenderAlpha; node; node = node->nNext3)
|
for( node = nRenderAlpha; node; node = node->nNext3 )
|
||||||
node->RenderAlphaDL(); // przezroczyste modele
|
GfxRenderer.Render_Alpha( node ); // przezroczyste modele
|
||||||
// for (node=tmp->nRender;node;node=node->nNext3)
|
|
||||||
// if (node->iType==TP_TRACK)
|
|
||||||
// node->pTrack->RenderAlpha(); //przezroczyste fragmenty pojazdów na torach
|
|
||||||
for (int j = 0; j < iTracks; ++j)
|
for (int j = 0; j < iTracks; ++j)
|
||||||
tTracks[j]->RenderDynAlpha(); // przezroczyste fragmenty pojazdów na torach
|
tTracks[j]->RenderDynAlpha(); // przezroczyste fragmenty pojazdów na torach
|
||||||
};
|
};
|
||||||
@@ -1255,15 +1209,15 @@ void TSubRect::RenderVBO()
|
|||||||
LoadNodes(); // czemu tutaj?
|
LoadNodes(); // czemu tutaj?
|
||||||
if (StartVBO())
|
if (StartVBO())
|
||||||
{
|
{
|
||||||
for (node = nRenderRect; node; node = node->nNext3)
|
for( node = nRenderRect; node; node = node->nNext3 )
|
||||||
if (node->iVboPtr >= 0)
|
if( node->iVboPtr >= 0 )
|
||||||
node->RenderVBO(); // nieprzezroczyste obiekty terenu
|
GfxRenderer.Render( node ); // nieprzezroczyste obiekty terenu
|
||||||
EndVBO();
|
EndVBO();
|
||||||
}
|
}
|
||||||
for (node = nRender; node; node = node->nNext3)
|
for( node = nRender; node; node = node->nNext3 )
|
||||||
node->RenderVBO(); // nieprzezroczyste obiekty (oprócz pojazdów)
|
GfxRenderer.Render( node ); // nieprzezroczyste obiekty (oprócz pojazdów)
|
||||||
for (node = nRenderMixed; node; node = node->nNext3)
|
for (node = nRenderMixed; node; node = node->nNext3)
|
||||||
node->RenderVBO(); // nieprzezroczyste z mieszanych modeli
|
GfxRenderer.Render( node ); // nieprzezroczyste z mieszanych modeli
|
||||||
for (int j = 0; j < iTracks; ++j)
|
for (int j = 0; j < iTracks; ++j)
|
||||||
tTracks[j]->RenderDyn(); // nieprzezroczyste fragmenty pojazdów na torach
|
tTracks[j]->RenderDyn(); // nieprzezroczyste fragmenty pojazdów na torach
|
||||||
#ifdef EU07_SCENERY_EDITOR
|
#ifdef EU07_SCENERY_EDITOR
|
||||||
@@ -1279,13 +1233,10 @@ void TSubRect::RenderVBO()
|
|||||||
void TSubRect::RenderAlphaVBO()
|
void TSubRect::RenderAlphaVBO()
|
||||||
{ // renderowanie przezroczystych modeli oraz pojazdów (VBO)
|
{ // renderowanie przezroczystych modeli oraz pojazdów (VBO)
|
||||||
TGroundNode *node;
|
TGroundNode *node;
|
||||||
for (node = nRenderMixed; node; node = node->nNext3)
|
for( node = nRenderMixed; node; node = node->nNext3 )
|
||||||
node->RenderAlphaVBO(); // przezroczyste z mieszanych modeli
|
GfxRenderer.Render_Alpha( node ); // przezroczyste z mieszanych modeli
|
||||||
for (node = nRenderAlpha; node; node = node->nNext3)
|
for( node = nRenderAlpha; node; node = node->nNext3 )
|
||||||
node->RenderAlphaVBO(); // przezroczyste modele
|
GfxRenderer.Render_Alpha( node ); // przezroczyste modele
|
||||||
// for (node=tmp->nRender;node;node=node->nNext3)
|
|
||||||
// if (node->iType==TP_TRACK)
|
|
||||||
// node->pTrack->RenderAlpha(); //przezroczyste fragmenty pojazdów na torach
|
|
||||||
for (int j = 0; j < iTracks; ++j)
|
for (int j = 0; j < iTracks; ++j)
|
||||||
tTracks[j]->RenderDynAlpha(); // przezroczyste fragmenty pojazdów na torach
|
tTracks[j]->RenderDynAlpha(); // przezroczyste fragmenty pojazdów na torach
|
||||||
};
|
};
|
||||||
@@ -1300,8 +1251,6 @@ void TSubRect::RenderSounds()
|
|||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
int TGroundRect::iFrameNumber = 0; // licznik wyświetlanych klatek
|
int TGroundRect::iFrameNumber = 0; // licznik wyświetlanych klatek
|
||||||
|
|
||||||
//TGroundRect::TGroundRect( float3 const &Position, float const Radius = 1000.0f * M_SQRT2 ) :
|
|
||||||
|
|
||||||
TGroundRect::~TGroundRect()
|
TGroundRect::~TGroundRect()
|
||||||
{
|
{
|
||||||
SafeDeleteArray(pSubRects);
|
SafeDeleteArray(pSubRects);
|
||||||
@@ -1343,50 +1292,12 @@ void TGroundRect::RenderDL()
|
|||||||
node->Compile(true);
|
node->Compile(true);
|
||||||
glEndList();
|
glEndList();
|
||||||
}
|
}
|
||||||
nRender->RenderDL(); // nieprzezroczyste trójkąty kwadratu kilometrowego
|
GfxRenderer.Render( nRender ); // nieprzezroczyste trójkąty kwadratu kilometrowego
|
||||||
}
|
}
|
||||||
if (nRootMesh)
|
if( nRootMesh )
|
||||||
nRootMesh->RenderDL();
|
GfxRenderer.Render( nRootMesh );
|
||||||
iLastDisplay = iFrameNumber; // drugi raz nie potrzeba
|
iLastDisplay = iFrameNumber; // drugi raz nie potrzeba
|
||||||
}
|
}
|
||||||
/*
|
|
||||||
float width = 500.0f;
|
|
||||||
float height = 50.0f;
|
|
||||||
float3 vTopLeftFront( m_area.center.x - width, m_area.center.y + height, m_area.center.z + width );
|
|
||||||
float3 vTopLeftBack( m_area.center.x - width, m_area.center.y + height, m_area.center.z - width );
|
|
||||||
float3 vTopRightBack( m_area.center.x + width, m_area.center.y + height, m_area.center.z - width );
|
|
||||||
float3 vTopRightFront( m_area.center.x + width, m_area.center.y + height, m_area.center.z + width );
|
|
||||||
|
|
||||||
float3 vBottom_LeftFront( m_area.center.x - width, m_area.center.y - height, m_area.center.z + width );
|
|
||||||
float3 vBottom_LeftBack( m_area.center.x - width, m_area.center.y - height, m_area.center.z - width );
|
|
||||||
float3 vBottomRightBack( m_area.center.x + width, m_area.center.y - height, m_area.center.z - width );
|
|
||||||
float3 vBottomRightFront( m_area.center.x + width, m_area.center.y - height, m_area.center.z + width );
|
|
||||||
|
|
||||||
glDisable( GL_LIGHTING );
|
|
||||||
glDisable( GL_TEXTURE_2D );
|
|
||||||
glColor3ub( 0, 255, 255 );
|
|
||||||
glBegin( GL_LINE_LOOP );
|
|
||||||
glVertex3fv( &vTopLeftFront.x );
|
|
||||||
glVertex3fv( &vTopLeftBack.x );
|
|
||||||
glVertex3fv( &vTopRightBack.x );
|
|
||||||
glVertex3fv( &vTopRightFront.x );
|
|
||||||
glEnd();
|
|
||||||
glBegin( GL_LINE_LOOP );
|
|
||||||
glVertex3fv( &vBottom_LeftFront.x );
|
|
||||||
glVertex3fv( &vBottom_LeftBack.x );
|
|
||||||
glVertex3fv( &vBottomRightBack.x );
|
|
||||||
glVertex3fv( &vBottomRightFront.x );
|
|
||||||
glEnd();
|
|
||||||
glBegin( GL_LINES );
|
|
||||||
glVertex3fv( &vTopLeftFront.x ); glVertex3fv( &vBottom_LeftFront.x );
|
|
||||||
glVertex3fv( &vTopLeftBack.x ); glVertex3fv( &vBottom_LeftBack.x );
|
|
||||||
glVertex3fv( &vTopRightBack.x ); glVertex3fv( &vBottomRightBack.x );
|
|
||||||
glVertex3fv( &vTopRightFront.x ); glVertex3fv( &vBottomRightFront.x );
|
|
||||||
glEnd();
|
|
||||||
glColor3ub( 255, 255, 255 );
|
|
||||||
glEnable( GL_TEXTURE_2D );
|
|
||||||
glEnable( GL_LIGHTING );
|
|
||||||
*/
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void TGroundRect::RenderVBO()
|
void TGroundRect::RenderVBO()
|
||||||
@@ -1410,46 +1321,8 @@ void TGroundRect::RenderVBO()
|
|||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|
||||||
void TGround::MoveGroundNode(vector3 pPosition)
|
|
||||||
{ // Ra: to wymaga gruntownej reformy
|
|
||||||
/*
|
|
||||||
TGroundNode *Current;
|
|
||||||
for (Current=RootNode;Current!=NULL;Current=Current->Next)
|
|
||||||
Current->MoveMe(pPosition);
|
|
||||||
|
|
||||||
TGroundRect *Rectx=new TGroundRect; //kwadrat kilometrowy
|
|
||||||
for(int i=0;i<iNumRects;i++)
|
|
||||||
for(int j=0;j<iNumRects;j++)
|
|
||||||
Rects[i][j]=*Rectx; //kopiowanie zawartości do każdego kwadratu
|
|
||||||
delete Rectx;
|
|
||||||
for (Current=RootNode;Current!=NULL;Current=Current->Next)
|
|
||||||
{//rozłożenie obiektów na mapie
|
|
||||||
if (Current->iType!=TP_DYNAMIC)
|
|
||||||
{//pojazdów to w ogóle nie dotyczy
|
|
||||||
if ((Current->iType!=GL_TRIANGLES)&&(Current->iType!=GL_TRIANGLE_STRIP)?true //~czy trójkąt?
|
|
||||||
:(Current->iFlags&0x20)?true //~czy teksturę ma nieprzezroczystą?
|
|
||||||
//:(Current->iNumVerts!=3)?true //~czy tylko jeden trójkąt?
|
|
||||||
:(Current->fSquareMinRadius!=0.0)?true //~czy widoczny z bliska?
|
|
||||||
:(Current->fSquareRadius<=90000.0)) //~czy widoczny z daleka?
|
|
||||||
GetSubRect(Current->pCenter.x,Current->pCenter.z)->AddNode(Current);
|
|
||||||
else //dodajemy do kwadratu kilometrowego
|
|
||||||
GetRect(Current->pCenter.x,Current->pCenter.z)->AddNode(Current);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
for (Current=RootDynamic;Current!=NULL;Current=Current->Next)
|
|
||||||
{
|
|
||||||
Current->pCenter+=pPosition;
|
|
||||||
Current->DynamicObject->UpdatePos();
|
|
||||||
}
|
|
||||||
for (Current=RootDynamic;Current!=NULL;Current=Current->Next)
|
|
||||||
Current->DynamicObject->MoverParameters->Physic_ReActivation();
|
|
||||||
*/
|
|
||||||
}
|
|
||||||
|
|
||||||
std::vector<TGroundVertex> TempVerts;
|
std::vector<TGroundVertex> TempVerts;
|
||||||
/*
|
|
||||||
TGroundVertex TempVerts[ 10000 ]; // tu wczytywane s¹ trójk¹ty
|
|
||||||
*/
|
|
||||||
BYTE TempConnectionType[ 200 ]; // Ra: sprzêgi w sk³adzie; ujemne, gdy odwrotnie
|
BYTE TempConnectionType[ 200 ]; // Ra: sprzêgi w sk³adzie; ujemne, gdy odwrotnie
|
||||||
|
|
||||||
TGround::TGround()
|
TGround::TGround()
|
||||||
@@ -4856,8 +4729,8 @@ bool TGround::RenderAlphaDL(vector3 pPosition)
|
|||||||
for (i = iRendered - 1; i >= 0; --i) // od najdalszych
|
for (i = iRendered - 1; i >= 0; --i) // od najdalszych
|
||||||
{ // przezroczyste trójkąty w oddzielnym cyklu przed modelami
|
{ // przezroczyste trójkąty w oddzielnym cyklu przed modelami
|
||||||
tmp = pRendered[i];
|
tmp = pRendered[i];
|
||||||
for (node = tmp->nRenderRectAlpha; node; node = node->nNext3)
|
for( node = tmp->nRenderRectAlpha; node; node = node->nNext3 )
|
||||||
node->RenderAlphaDL(); // przezroczyste modele
|
GfxRenderer.Render_Alpha( node ); // przezroczyste modele
|
||||||
}
|
}
|
||||||
for (i = iRendered - 1; i >= 0; --i) // od najdalszych
|
for (i = iRendered - 1; i >= 0; --i) // od najdalszych
|
||||||
{ // renderowanie przezroczystych modeli oraz pojazdów
|
{ // renderowanie przezroczystych modeli oraz pojazdów
|
||||||
@@ -4867,8 +4740,8 @@ bool TGround::RenderAlphaDL(vector3 pPosition)
|
|||||||
for (i = iRendered - 1; i >= 0; --i) // od najdalszych
|
for (i = iRendered - 1; i >= 0; --i) // od najdalszych
|
||||||
{ // druty na końcu, żeby się nie robiły białe plamy na tle lasu
|
{ // druty na końcu, żeby się nie robiły białe plamy na tle lasu
|
||||||
tmp = pRendered[i];
|
tmp = pRendered[i];
|
||||||
for (node = tmp->nRenderWires; node; node = node->nNext3)
|
for( node = tmp->nRenderWires; node; node = node->nNext3 )
|
||||||
node->RenderAlphaDL(); // druty
|
GfxRenderer.Render_Alpha( node ); // druty
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -4954,9 +4827,9 @@ bool TGround::RenderAlphaVBO(vector3 pPosition)
|
|||||||
tmp->LoadNodes(); // ewentualne tworzenie siatek
|
tmp->LoadNodes(); // ewentualne tworzenie siatek
|
||||||
if (tmp->StartVBO())
|
if (tmp->StartVBO())
|
||||||
{
|
{
|
||||||
for (node = tmp->nRenderRectAlpha; node; node = node->nNext3)
|
for( node = tmp->nRenderRectAlpha; node; node = node->nNext3 )
|
||||||
if (node->iVboPtr >= 0)
|
if( node->iVboPtr >= 0 )
|
||||||
node->RenderAlphaVBO(); // nieprzezroczyste obiekty terenu
|
GfxRenderer.Render_Alpha( node ); // nieprzezroczyste obiekty terenu
|
||||||
tmp->EndVBO();
|
tmp->EndVBO();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4968,8 +4841,8 @@ bool TGround::RenderAlphaVBO(vector3 pPosition)
|
|||||||
tmp = pRendered[i];
|
tmp = pRendered[i];
|
||||||
if (tmp->StartVBO())
|
if (tmp->StartVBO())
|
||||||
{
|
{
|
||||||
for (node = tmp->nRenderWires; node; node = node->nNext3)
|
for( node = tmp->nRenderWires; node; node = node->nNext3 )
|
||||||
node->RenderAlphaVBO(); // przezroczyste modele
|
GfxRenderer.Render_Alpha( node ); // przezroczyste modele
|
||||||
tmp->EndVBO();
|
tmp->EndVBO();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
45
Ground.h
45
Ground.h
@@ -101,8 +101,11 @@ class TSubRect; // sektor (aktualnie 200m×200m, ale może być zmieniony)
|
|||||||
|
|
||||||
class TGroundNode : public Resource
|
class TGroundNode : public Resource
|
||||||
{ // obiekt scenerii
|
{ // obiekt scenerii
|
||||||
private:
|
|
||||||
public:
|
friend class opengl_renderer;
|
||||||
|
|
||||||
|
private:
|
||||||
|
public:
|
||||||
TGroundNodeType iType; // typ obiektu
|
TGroundNodeType iType; // typ obiektu
|
||||||
union
|
union
|
||||||
{ // Ra: wskażniki zależne od typu - zrobić klasy dziedziczone zamiast
|
{ // Ra: wskażniki zależne od typu - zrobić klasy dziedziczone zamiast
|
||||||
@@ -130,12 +133,7 @@ class TGroundNode : public Resource
|
|||||||
};
|
};
|
||||||
vector3 pCenter; // współrzędne środka do przydzielenia sektora
|
vector3 pCenter; // współrzędne środka do przydzielenia sektora
|
||||||
|
|
||||||
union
|
double fLineThickness; // McZapkie-120702: grubosc linii
|
||||||
{
|
|
||||||
// double fAngle; //kąt obrotu dla modelu
|
|
||||||
double fLineThickness; // McZapkie-120702: grubosc linii
|
|
||||||
// int Status; //McZapkie-170303: status dzwieku
|
|
||||||
};
|
|
||||||
double fSquareRadius; // kwadrat widoczności do
|
double fSquareRadius; // kwadrat widoczności do
|
||||||
double fSquareMinRadius; // kwadrat widoczności od
|
double fSquareMinRadius; // kwadrat widoczności od
|
||||||
// TGroundNode *nMeshGroup; //Ra: obiekt grupujący trójkąty w TSubRect dla tekstury
|
// TGroundNode *nMeshGroup; //Ra: obiekt grupujący trójkąty w TSubRect dla tekstury
|
||||||
@@ -174,12 +172,8 @@ class TGroundNode : public Resource
|
|||||||
void Release();
|
void Release();
|
||||||
|
|
||||||
void RenderHidden(); // obsługa dźwięków i wyzwalaczy zdarzeń
|
void RenderHidden(); // obsługa dźwięków i wyzwalaczy zdarzeń
|
||||||
void RenderDL(); // renderowanie nieprzezroczystych w Display Lists
|
|
||||||
void RenderAlphaDL(); // renderowanie przezroczystych w Display Lists
|
|
||||||
// (McZapkie-131202)
|
// (McZapkie-131202)
|
||||||
void RaRenderVBO(); // renderowanie (nieprzezroczystych) ze wspólnego VBO
|
void RaRenderVBO(); // renderowanie (nieprzezroczystych) ze wspólnego VBO
|
||||||
void RenderVBO(); // renderowanie nieprzezroczystych z własnego VBO
|
|
||||||
void RenderAlphaVBO(); // renderowanie przezroczystych z (własnego) VBO
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -313,9 +307,6 @@ class TGround
|
|||||||
public:
|
public:
|
||||||
bool bDynamicRemove = false; // czy uruchomić procedurę usuwania pojazdów
|
bool bDynamicRemove = false; // czy uruchomić procedurę usuwania pojazdów
|
||||||
TDynamicObject *LastDyn = nullptr; // ABu: paskudnie, ale na bardzo szybko moze jakos przejdzie...
|
TDynamicObject *LastDyn = nullptr; // ABu: paskudnie, ale na bardzo szybko moze jakos przejdzie...
|
||||||
// TTrain *pTrain;
|
|
||||||
// double fVDozwolona;
|
|
||||||
// bool bTrabil;
|
|
||||||
|
|
||||||
TGround();
|
TGround();
|
||||||
~TGround();
|
~TGround();
|
||||||
@@ -329,7 +320,6 @@ class TGround
|
|||||||
TTrack * FindTrack(vector3 Point, int &iConnection, TGroundNode *Exclude);
|
TTrack * FindTrack(vector3 Point, int &iConnection, TGroundNode *Exclude);
|
||||||
TTraction * FindTraction(vector3 *Point, int &iConnection, TGroundNode *Exclude);
|
TTraction * FindTraction(vector3 *Point, int &iConnection, TGroundNode *Exclude);
|
||||||
TTraction * TractionNearestFind(vector3 &p, int dir, TGroundNode *n);
|
TTraction * TractionNearestFind(vector3 &p, int dir, TGroundNode *n);
|
||||||
// TGroundNode* CreateGroundNode();
|
|
||||||
TGroundNode * AddGroundNode(cParser *parser);
|
TGroundNode * AddGroundNode(cParser *parser);
|
||||||
bool AddGroundNode(double x, double z, TGroundNode *Node)
|
bool AddGroundNode(double x, double z, TGroundNode *Node)
|
||||||
{
|
{
|
||||||
@@ -342,11 +332,6 @@ class TGround
|
|||||||
else
|
else
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
// bool Include(TQueryParserComp *Parser);
|
|
||||||
// TGroundNode* GetVisible(AnsiString asName);
|
|
||||||
TGroundNode * GetNode(std::string asName);
|
|
||||||
bool AddDynamic(TGroundNode *Node);
|
|
||||||
void MoveGroundNode(vector3 pPosition);
|
|
||||||
void UpdatePhys(double dt, int iter); // aktualizacja fizyki stałym krokiem
|
void UpdatePhys(double dt, int iter); // aktualizacja fizyki stałym krokiem
|
||||||
bool Update(double dt, int iter); // aktualizacja przesunięć zgodna z FPS
|
bool Update(double dt, int iter); // aktualizacja przesunięć zgodna z FPS
|
||||||
void Update_Lights(); // updates scene lights array
|
void Update_Lights(); // updates scene lights array
|
||||||
@@ -358,23 +343,6 @@ class TGround
|
|||||||
bool RenderVBO(vector3 pPosition);
|
bool RenderVBO(vector3 pPosition);
|
||||||
bool RenderAlphaVBO(vector3 pPosition);
|
bool RenderAlphaVBO(vector3 pPosition);
|
||||||
bool CheckQuery();
|
bool CheckQuery();
|
||||||
// GetRect(double x, double z) { return
|
|
||||||
// &(Rects[int(x/fSubRectSize+fHalfNumRects)][int(z/fSubRectSize+fHalfNumRects)]); };
|
|
||||||
/*
|
|
||||||
int GetRowFromZ(double z) { return (z/fRectSize+fHalfNumRects); };
|
|
||||||
int GetColFromX(double x) { return (x/fRectSize+fHalfNumRects); };
|
|
||||||
int GetSubRowFromZ(double z) { return (z/fSubRectSize+fHalfNumSubRects); };
|
|
||||||
int GetSubColFromX(double x) { return (x/fSubRectSize+fHalfNumSubRects); };
|
|
||||||
*/
|
|
||||||
/*
|
|
||||||
inline TGroundNode* FindGroundNode(const AnsiString &asNameToFind )
|
|
||||||
{
|
|
||||||
if (RootNode)
|
|
||||||
return (RootNode->Find( asNameToFind ));
|
|
||||||
else
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
TGroundNode * DynamicFindAny(std::string asNameToFind);
|
TGroundNode * DynamicFindAny(std::string asNameToFind);
|
||||||
TGroundNode * DynamicFind(std::string asNameToFind);
|
TGroundNode * DynamicFind(std::string asNameToFind);
|
||||||
void DynamicList(bool all = false);
|
void DynamicList(bool all = false);
|
||||||
@@ -419,7 +387,6 @@ class TGround
|
|||||||
void WyslijNamiary(TGroundNode *t);
|
void WyslijNamiary(TGroundNode *t);
|
||||||
void WyslijParam(int nr, int fl);
|
void WyslijParam(int nr, int fl);
|
||||||
void WyslijUszkodzenia(const std::string &t, char fl);
|
void WyslijUszkodzenia(const std::string &t, char fl);
|
||||||
void WyslijPojazdy(int nr); // -> skladanie wielu pojazdow
|
|
||||||
void WyslijObsadzone(); // -> skladanie wielu pojazdow
|
void WyslijObsadzone(); // -> skladanie wielu pojazdow
|
||||||
void RadioStop(vector3 pPosition);
|
void RadioStop(vector3 pPosition);
|
||||||
TDynamicObject * DynamicNearest(vector3 pPosition, double distance = 20.0,
|
TDynamicObject * DynamicNearest(vector3 pPosition, double distance = 20.0,
|
||||||
|
|||||||
887
Segment.cpp
887
Segment.cpp
@@ -19,12 +19,6 @@ http://mozilla.org/MPL/2.0/.
|
|||||||
|
|
||||||
// 101206 Ra: trapezoidalne drogi
|
// 101206 Ra: trapezoidalne drogi
|
||||||
// 110806 Ra: odwrócone mapowanie wzdłuż - Point1 == 1.0
|
// 110806 Ra: odwrócone mapowanie wzdłuż - Point1 == 1.0
|
||||||
|
|
||||||
float Interpolate( float const First, float const Second, float const Factor ) {
|
|
||||||
|
|
||||||
return ( First * ( 1.0f - Factor ) ) + ( Second * Factor );
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string Where(vector3 p)
|
std::string Where(vector3 p)
|
||||||
{ // zamiana współrzędnych na tekst, używana w błędach
|
{ // zamiana współrzędnych na tekst, używana w błędach
|
||||||
return std::to_string(p.x) + " " + std::to_string(p.y) + " " + std::to_string(p.z);
|
return std::to_string(p.x) + " " + std::to_string(p.y) + " " + std::to_string(p.z);
|
||||||
@@ -122,15 +116,14 @@ bool TSegment::Init(vector3 &NewPoint1, vector3 NewCPointOut, vector3 NewCPointI
|
|||||||
// MessageBox(0,"Length<=0","TSegment::Init",MB_OK);
|
// MessageBox(0,"Length<=0","TSegment::Init",MB_OK);
|
||||||
return false; // zerowe nie mogą być
|
return false; // zerowe nie mogą być
|
||||||
}
|
}
|
||||||
fStoop = atan2((Point2.y - Point1.y),
|
fStoop = std::atan2((Point2.y - Point1.y), fLength); // pochylenie toru prostego, żeby nie liczyć wielokrotnie
|
||||||
fLength); // pochylenie toru prostego, żeby nie liczyć wielokrotnie
|
|
||||||
SafeDeleteArray(fTsBuffer);
|
SafeDeleteArray(fTsBuffer);
|
||||||
|
|
||||||
if( ( bCurve ) && ( fStep > 0 ) ) {
|
if( ( bCurve ) && ( fStep > 0 ) ) {
|
||||||
if( fStep > 0 ) { // Ra: prosty dostanie podział, jak ma różną przechyłkę na końcach
|
if( fStep > 0 ) { // Ra: prosty dostanie podział, jak ma różną przechyłkę na końcach
|
||||||
double s = 0;
|
double s = 0;
|
||||||
int i = 0;
|
int i = 0;
|
||||||
iSegCount = ceil( fLength / fStep ); // potrzebne do VBO
|
iSegCount = static_cast<int>( std::ceil( fLength / fStep )); // potrzebne do VBO
|
||||||
// fStep=fLength/(double)(iSegCount-1); //wyrównanie podziału
|
// fStep=fLength/(double)(iSegCount-1); //wyrównanie podziału
|
||||||
fTsBuffer = new double[ iSegCount + 1 ];
|
fTsBuffer = new double[ iSegCount + 1 ];
|
||||||
fTsBuffer[ 0 ] = 0; /* TODO : fix fTsBuffer */
|
fTsBuffer[ 0 ] = 0; /* TODO : fix fTsBuffer */
|
||||||
@@ -324,408 +317,213 @@ vector3 TSegment::FastGetPoint(double t)
|
|||||||
return (bCurve ? RaInterpolate(t) : ((1.0 - t) * Point1 + (t)*Point2));
|
return (bCurve ? RaInterpolate(t) : ((1.0 - t) * Point1 + (t)*Point2));
|
||||||
}
|
}
|
||||||
|
|
||||||
void TSegment::RenderLoft(const vector6 *ShapePoints, int iNumShapePoints, double fTextureLength,
|
void TSegment::RenderLoft( CVertNormTex* &Output, const vector6 *ShapePoints, int iNumShapePoints, double fTextureLength, double Texturescale, int iSkip, int iEnd, double fOffsetX, bool Onlypositions, vector3 **p, bool bRender)
|
||||||
int iSkip, int iQualityFactor, vector3 **p, bool bRender)
|
|
||||||
{ // generowanie trójkątów dla odcinka trajektorii ruchu
|
{ // generowanie trójkątów dla odcinka trajektorii ruchu
|
||||||
// standardowo tworzy triangle_strip dla prostego albo ich zestaw dla łuku
|
// standardowo tworzy triangle_strip dla prostego albo ich zestaw dla łuku
|
||||||
// po modyfikacji - dla ujemnego (iNumShapePoints) w dodatkowych polach tabeli
|
// po modyfikacji - dla ujemnego (iNumShapePoints) w dodatkowych polach tabeli
|
||||||
// podany jest przekrój końcowy
|
// podany jest przekrój końcowy
|
||||||
// podsypka toru jest robiona za pomocą 6 punktów, szyna 12, drogi i rzeki na 3+2+3
|
// podsypka toru jest robiona za pomocą 6 punktów, szyna 12, drogi i rzeki na 3+2+3
|
||||||
if (iQualityFactor < 1)
|
if( !fTsBuffer )
|
||||||
iQualityFactor = 1; // co który segment ma być uwzględniony
|
return; // prowizoryczne zabezpieczenie przed wysypem - ustalić faktyczną przyczynę
|
||||||
|
|
||||||
vector3 pos1, pos2, dir, parallel1, parallel2, pt, norm;
|
vector3 pos1, pos2, dir, parallel1, parallel2, pt, norm;
|
||||||
double s, step, fOffset, tv1, tv2, t;
|
double s, step, fOffset, tv1, tv2, t, fEnd;
|
||||||
int i, j;
|
bool const trapez = iNumShapePoints < 0; // sygnalizacja trapezowatości
|
||||||
bool trapez = iNumShapePoints < 0; // sygnalizacja trapezowatości
|
iNumShapePoints = std::abs( iNumShapePoints );
|
||||||
iNumShapePoints = abs(iNumShapePoints);
|
fTextureLength *= Texturescale;
|
||||||
if (bCurve)
|
|
||||||
{
|
double m1, jmm1, m2, jmm2; // pozycje względne na odcinku 0...1 (ale nie parametr Beziera)
|
||||||
double m1, jmm1, m2, jmm2; // pozycje względne na odcinku 0...1 (ale nie parametr Beziera)
|
step = fStep;
|
||||||
tv1 = 1.0; // Ra: to by można było wyliczać dla odcinka, wyglądało by lepiej
|
tv1 = 1.0; // Ra: to by można było wyliczać dla odcinka, wyglądało by lepiej
|
||||||
step = fStep * iQualityFactor;
|
s = fStep * iSkip; // iSkip - ile odcinków z początku pominąć
|
||||||
s = fStep * iSkip; // iSkip - ile odcinków z początku pominąć
|
int i = iSkip; // domyślnie 0
|
||||||
i = iSkip; // domyślnie 0
|
t = fTsBuffer[ i ]; // tabela wattości t dla segmentów
|
||||||
if (!fTsBuffer)
|
// BUG: length of spline can be 0, we should skip geometry generation for such cases
|
||||||
return; // prowizoryczne zabezpieczenie przed wysypem - ustalić faktyczną przyczynę
|
fOffset = 0.1 / fLength; // pierwsze 10cm
|
||||||
if (i > iSegCount)
|
pos1 = FastGetPoint( t ); // wektor początku segmentu
|
||||||
return; // prowizoryczne zabezpieczenie przed wysypem - ustalić faktyczną przyczynę
|
dir = FastGetDirection( t, fOffset ); // wektor kierunku
|
||||||
t = fTsBuffer[i]; // tabela watości t dla segmentów
|
parallel1 = Normalize( vector3( -dir.z, 0.0, dir.x ) ); // wektor poprzeczny
|
||||||
fOffset = 0.1 / fLength; // pierwsze 10cm
|
if( iEnd == 0 )
|
||||||
pos1 = FastGetPoint(t); // wektor początku segmentu
|
iEnd = iSegCount;
|
||||||
dir = FastGetDirection(t, fOffset); // wektor kierunku
|
fEnd = fLength * double( iEnd ) / double( iSegCount );
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0))); //wektor poprzeczny
|
m2 = s / fEnd;
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
jmm2 = 1.0 - m2;
|
||||||
m2 = s / fLength;
|
while( i < iEnd ) {
|
||||||
jmm2 = 1.0 - m2;
|
|
||||||
while (s < fLength)
|
++i; // kolejny punkt łamanej
|
||||||
{
|
s += step; // końcowa pozycja segmentu [m]
|
||||||
// step=SquareMagnitude(Global::GetCameraPosition()+pos);
|
m1 = m2;
|
||||||
i += iQualityFactor; // kolejny punkt łamanej
|
jmm1 = jmm2; // stara pozycja
|
||||||
s += step; // końcowa pozycja segmentu [m]
|
m2 = s / fEnd;
|
||||||
m1 = m2;
|
jmm2 = 1.0 - m2; // nowa pozycja
|
||||||
jmm1 = jmm2; // stara pozycja
|
if( i == iEnd ) { // gdy przekroczyliśmy koniec - stąd dziury w torach...
|
||||||
m2 = s / fLength;
|
step -= ( s - fEnd ); // jeszcze do wyliczenia mapowania potrzebny
|
||||||
jmm2 = 1.0 - m2; // nowa pozycja
|
s = fEnd;
|
||||||
if (s > fLength - 0.5) // Ra: -0.5 żeby nie robiło cieniasa na końcu
|
m2 = 1.0;
|
||||||
{ // gdy przekroczyliśmy koniec - stąd dziury w torach...
|
jmm2 = 0.0;
|
||||||
step -= (s - fLength); // jeszcze do wyliczenia mapowania potrzebny
|
|
||||||
s = fLength;
|
|
||||||
i = iSegCount; // 20/5 ma dawać 4
|
|
||||||
m2 = 1.0;
|
|
||||||
jmm2 = 0.0;
|
|
||||||
}
|
|
||||||
while (tv1 < 0.0)
|
|
||||||
tv1 += 1.0; // przestawienie mapowania
|
|
||||||
tv2 = tv1 - step / fTextureLength; // mapowanie na końcu segmentu
|
|
||||||
t = fTsBuffer[i]; // szybsze od GetTFromS(s);
|
|
||||||
pos2 = FastGetPoint(t);
|
|
||||||
dir = FastGetDirection(t, fOffset); // nowy wektor kierunku
|
|
||||||
// parallel2=CrossProduct(dir,vector3(0,1,0)); //wektor poprzeczny
|
|
||||||
parallel2 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
glBegin(GL_TRIANGLE_STRIP);
|
|
||||||
if (trapez)
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{
|
|
||||||
norm = (jmm1 * ShapePoints[j].n.x + m1 * ShapePoints[j + iNumShapePoints].n.x) *
|
|
||||||
parallel1;
|
|
||||||
norm.y += jmm1 * ShapePoints[j].n.y + m1 * ShapePoints[j + iNumShapePoints].n.y;
|
|
||||||
pt = parallel1 *
|
|
||||||
(jmm1 * ShapePoints[j].x + m1 * ShapePoints[j + iNumShapePoints].x) +
|
|
||||||
pos1;
|
|
||||||
pt.y += jmm1 * ShapePoints[j].y + m1 * ShapePoints[j + iNumShapePoints].y;
|
|
||||||
if (bRender)
|
|
||||||
{ // skrzyżowania podczas łączenia siatek mogą nie renderować poboczy, ale
|
|
||||||
// potrzebować punktów
|
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(
|
|
||||||
jmm1 * ShapePoints[j].z + m1 * ShapePoints[j + iNumShapePoints].z, tv1);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z); // pt nie mamy gdzie zapamiętać?
|
|
||||||
}
|
|
||||||
// BUG: things blow up badly in the following part in 64bit version on baltyk.scn
|
|
||||||
// TODO: sort this mess out when the time comes to reorganize spline generation
|
|
||||||
if( p ) // jeśli jest wskaźnik do tablicy
|
|
||||||
if (*p)
|
|
||||||
if (!j) // to dla pierwszego punktu
|
|
||||||
{
|
|
||||||
*(*p) = pt;
|
|
||||||
(*p)++;
|
|
||||||
} // zapamiętanie brzegu jezdni
|
|
||||||
// dla trapezu drugi koniec ma inne współrzędne
|
|
||||||
norm = (jmm1 * ShapePoints[j].n.x + m1 * ShapePoints[j + iNumShapePoints].n.x) *
|
|
||||||
parallel2;
|
|
||||||
norm.y += jmm1 * ShapePoints[j].n.y + m1 * ShapePoints[j + iNumShapePoints].n.y;
|
|
||||||
pt = parallel2 *
|
|
||||||
(jmm2 * ShapePoints[j].x + m2 * ShapePoints[j + iNumShapePoints].x) +
|
|
||||||
pos2;
|
|
||||||
pt.y += jmm2 * ShapePoints[j].y + m2 * ShapePoints[j + iNumShapePoints].y;
|
|
||||||
if (bRender)
|
|
||||||
{ // skrzyżowania podczas łączenia siatek mogą nie renderować poboczy, ale
|
|
||||||
// potrzebować punktów
|
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(
|
|
||||||
jmm2 * ShapePoints[j].z + m2 * ShapePoints[j + iNumShapePoints].z, tv2);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
}
|
|
||||||
if (p) // jeśli jest wskaźnik do tablicy
|
|
||||||
if (*p)
|
|
||||||
if (!j) // to dla pierwszego punktu
|
|
||||||
if (i == iSegCount)
|
|
||||||
{
|
|
||||||
*(*p) = pt;
|
|
||||||
(*p)++;
|
|
||||||
} // zapamiętanie brzegu jezdni
|
|
||||||
}
|
|
||||||
else
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{ //łuk z jednym profilem
|
|
||||||
norm = ShapePoints[j].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel1 * ShapePoints[j].x + pos1;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(ShapePoints[j].z, tv1);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z); // punkt na początku odcinka
|
|
||||||
norm = ShapePoints[j].n.x * parallel2;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel2 * ShapePoints[j].x + pos2;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(ShapePoints[j].z, tv2);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z); // punkt na końcu odcinka
|
|
||||||
}
|
|
||||||
glEnd();
|
|
||||||
pos1 = pos2;
|
|
||||||
parallel1 = parallel2;
|
|
||||||
tv1 = tv2;
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
else
|
if( false == Onlypositions ) {
|
||||||
#ifdef EU07_USE_OLD_LIGHTING_MODEL
|
while( tv1 < 0.0 ) {
|
||||||
{ // gdy prosty, nie modyfikujemy wektora kierunkowego i poprzecznego
|
tv1 += 1.0;
|
||||||
pos1 = FastGetPoint((fStep * iSkip) / fLength);
|
|
||||||
pos2 = FastGetPoint_1();
|
|
||||||
dir = GetDirection();
|
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0)));
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
glBegin(GL_TRIANGLE_STRIP);
|
|
||||||
if (trapez)
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{
|
|
||||||
norm = ShapePoints[j].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel1 * ShapePoints[j].x + pos1;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(ShapePoints[j].z, 0);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
// dla trapezu drugi koniec ma inne współrzędne względne
|
|
||||||
norm = ShapePoints[j + iNumShapePoints].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j + iNumShapePoints].n.y;
|
|
||||||
pt = parallel1 * ShapePoints[j + iNumShapePoints].x + pos2; // odsunięcie
|
|
||||||
pt.y += ShapePoints[j + iNumShapePoints].y; // wysokość
|
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(ShapePoints[j + iNumShapePoints].z, fLength / fTextureLength);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
}
|
}
|
||||||
else
|
tv2 = tv1 - step / fTextureLength; // mapowanie na końcu segmentu
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
}
|
||||||
{
|
|
||||||
norm = ShapePoints[j].n.x * parallel1;
|
t = fTsBuffer[ i ]; // szybsze od GetTFromS(s);
|
||||||
norm.y += ShapePoints[j].n.y;
|
pos2 = FastGetPoint( t );
|
||||||
pt = parallel1 * ShapePoints[j].x + pos1;
|
dir = FastGetDirection( t, fOffset ); // nowy wektor kierunku
|
||||||
pt.y += ShapePoints[j].y;
|
parallel2 = Normalize( vector3( -dir.z, 0.0, dir.x ) ); // wektor poprzeczny
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(ShapePoints[j].z, 0);
|
if( Output == nullptr ) {
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
// immediate mode
|
||||||
pt = parallel1 * ShapePoints[j].x + pos2;
|
::glBegin( GL_TRIANGLE_STRIP );
|
||||||
pt.y += ShapePoints[j].y;
|
}
|
||||||
glNormal3f(norm.x, norm.y, norm.z);
|
|
||||||
glTexCoord2f(ShapePoints[j].z, fLength / fTextureLength);
|
if( trapez ) {
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
for( int j = 0; j < iNumShapePoints; ++j ) {
|
||||||
|
pt = parallel1 * ( jmm1 * ( ShapePoints[ j ].x - fOffsetX ) + m1 * ShapePoints[ j + iNumShapePoints ].x ) + pos1;
|
||||||
|
pt.y += jmm1 * ShapePoints[ j ].y + m1 * ShapePoints[ j + iNumShapePoints ].y;
|
||||||
|
if( false == Onlypositions ) {
|
||||||
|
norm = ( jmm1 * ShapePoints[ j ].n.x + m1 * ShapePoints[ j + iNumShapePoints ].n.x ) * parallel1;
|
||||||
|
norm.y += jmm1 * ShapePoints[ j ].n.y + m1 * ShapePoints[ j + iNumShapePoints ].n.y;
|
||||||
|
}
|
||||||
|
if( bRender ) { // skrzyżowania podczas łączenia siatek mogą nie renderować poboczy, ale potrzebować punktów
|
||||||
|
if( Output == nullptr ) {
|
||||||
|
// immediate mode
|
||||||
|
if( false == Onlypositions ) {
|
||||||
|
::glNormal3f( norm.x, norm.y, norm.z );
|
||||||
|
::glTexCoord2f( (jmm1 * ShapePoints[ j ].z + m1 * ShapePoints[ j + iNumShapePoints ].z) / Texturescale, tv1 );
|
||||||
|
}
|
||||||
|
::glVertex3f( pt.x, pt.y, pt.z ); // pt nie mamy gdzie zapamiętać?
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
Output->x = pt.x;
|
||||||
|
Output->y = pt.y;
|
||||||
|
Output->z = pt.z;
|
||||||
|
if( false == Onlypositions ) {
|
||||||
|
Output->nx = norm.x;
|
||||||
|
Output->ny = norm.y;
|
||||||
|
Output->nz = norm.z;
|
||||||
|
Output->u = (jmm1 * ShapePoints[ j ].z + m1 * ShapePoints[ j + iNumShapePoints ].z) / Texturescale;
|
||||||
|
Output->v = tv1;
|
||||||
|
}
|
||||||
|
++Output;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if( p ) // jeśli jest wskaźnik do tablicy
|
||||||
|
if( *p )
|
||||||
|
if( !j ) // to dla pierwszego punktu
|
||||||
|
{
|
||||||
|
*( *p ) = pt;
|
||||||
|
( *p )++;
|
||||||
|
} // zapamiętanie brzegu jezdni
|
||||||
|
// dla trapezu drugi koniec ma inne współrzędne
|
||||||
|
pt = parallel2 * ( jmm2 * ( ShapePoints[ j ].x - fOffsetX ) + m2 * ShapePoints[ j + iNumShapePoints ].x ) + pos2;
|
||||||
|
pt.y += jmm2 * ShapePoints[ j ].y + m2 * ShapePoints[ j + iNumShapePoints ].y;
|
||||||
|
if( false == Onlypositions ) {
|
||||||
|
norm = ( jmm1 * ShapePoints[ j ].n.x + m1 * ShapePoints[ j + iNumShapePoints ].n.x ) * parallel2;
|
||||||
|
norm.y += jmm1 * ShapePoints[ j ].n.y + m1 * ShapePoints[ j + iNumShapePoints ].n.y;
|
||||||
|
}
|
||||||
|
if( bRender ) { // skrzyżowania podczas łączenia siatek mogą nie renderować poboczy, ale potrzebować punktów
|
||||||
|
if( Output == nullptr ) {
|
||||||
|
// immediate mode
|
||||||
|
if( false == Onlypositions ) {
|
||||||
|
::glNormal3f( norm.x, norm.y, norm.z );
|
||||||
|
::glTexCoord2f( (jmm2 * ShapePoints[ j ].z + m2 * ShapePoints[ j + iNumShapePoints ].z) / Texturescale, tv2 );
|
||||||
|
}
|
||||||
|
::glVertex3f( pt.x, pt.y, pt.z );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
Output->x = pt.x;
|
||||||
|
Output->y = pt.y;
|
||||||
|
Output->z = pt.z;
|
||||||
|
if( false == Onlypositions ) {
|
||||||
|
Output->nx = norm.x;
|
||||||
|
Output->ny = norm.y;
|
||||||
|
Output->nz = norm.z;
|
||||||
|
Output->u = (jmm2 * ShapePoints[ j ].z + m2 * ShapePoints[ j + iNumShapePoints ].z) / Texturescale;
|
||||||
|
Output->v = tv2;
|
||||||
|
}
|
||||||
|
++Output;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if( p ) // jeśli jest wskaźnik do tablicy
|
||||||
|
if( *p )
|
||||||
|
if( !j ) // to dla pierwszego punktu
|
||||||
|
if( i == iSegCount ) {
|
||||||
|
*( *p ) = pt;
|
||||||
|
( *p )++;
|
||||||
|
} // zapamiętanie brzegu jezdni
|
||||||
}
|
}
|
||||||
glEnd();
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
{
|
|
||||||
Math3D::vector3 const pos0 = FastGetPoint( ( fStep * iSkip ) / fLength );
|
|
||||||
Math3D::vector3 const pos1 = FastGetPoint_1();
|
|
||||||
dir = GetDirection();
|
|
||||||
Math3D::vector3 const parallel = Normalize( vector3( -dir.z, 0.0, dir.x ) ); // wektor poprzeczny
|
|
||||||
|
|
||||||
Math3D::vector3 startnormal0, startnormal1, endnormal0, endnormal1;
|
|
||||||
Math3D::vector3 startvertex0, startvertex1, endvertex0, endvertex1;
|
|
||||||
float startuv0, startuv1, enduv0, enduv1;
|
|
||||||
|
|
||||||
for( j = 0; j < iNumShapePoints - 1; ++j ) {
|
|
||||||
|
|
||||||
startnormal0 = ShapePoints[ j ].n.x * parallel;
|
|
||||||
startnormal0.y += ShapePoints[ j ].n.y;
|
|
||||||
startvertex0 = parallel * ShapePoints[ j ].x + pos0;
|
|
||||||
startvertex0.y += ShapePoints[ j ].y;
|
|
||||||
startuv0 = ShapePoints[ j ].z;
|
|
||||||
startnormal1 = ShapePoints[ j + 1 ].n.x * parallel;
|
|
||||||
startnormal1.y += ShapePoints[ j + 1 ].n.y;
|
|
||||||
startvertex1 = parallel * ShapePoints[ j + 1 ].x + pos0;
|
|
||||||
startvertex1.y += ShapePoints[ j + 1 ].y;
|
|
||||||
startuv1 = ShapePoints[ j + 1 ].z;
|
|
||||||
|
|
||||||
if( trapez == false ) {
|
|
||||||
// single profile throughout
|
|
||||||
endnormal0 = startnormal0;
|
|
||||||
endvertex0 = startvertex0 + ( pos1 - pos0 );
|
|
||||||
enduv0 = startuv0;
|
|
||||||
endnormal1 = startnormal1;
|
|
||||||
endvertex1 = startvertex1 + ( pos1 - pos0 );
|
|
||||||
enduv1 = startuv1;
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// end profile is different
|
for( int j = 0; j < iNumShapePoints; ++j ) {
|
||||||
endnormal0 = ShapePoints[ j + iNumShapePoints ].n.x * parallel;
|
//łuk z jednym profilem
|
||||||
endnormal0.y += ShapePoints[ j + iNumShapePoints ].n.y;
|
pt = parallel1 * ( ShapePoints[ j ].x - fOffsetX ) + pos1;
|
||||||
endvertex0 = parallel * ShapePoints[ j + iNumShapePoints ].x + pos1; // odsunięcie
|
pt.y += ShapePoints[ j ].y;
|
||||||
endvertex0.y += ShapePoints[ j + iNumShapePoints ].y; // wysokość
|
if( false == Onlypositions ) {
|
||||||
enduv0 = ShapePoints[ j + iNumShapePoints ].z;
|
norm = ShapePoints[ j ].n.x * parallel1;
|
||||||
endnormal1 = ShapePoints[ j + iNumShapePoints + 1 ].n.x * parallel;
|
norm.y += ShapePoints[ j ].n.y;
|
||||||
endnormal1.y += ShapePoints[ j + iNumShapePoints + 1 ].n.y;
|
}
|
||||||
endvertex1 = parallel * ShapePoints[ j + iNumShapePoints + 1 ].x + pos1; // odsunięcie
|
if( Output == nullptr ) {
|
||||||
endvertex1.y += ShapePoints[ j + iNumShapePoints + 1 ].y; // wysokość
|
// immediate mode
|
||||||
enduv1 = ShapePoints[ j + iNumShapePoints + 1 ].z;
|
if( false == Onlypositions ) {
|
||||||
}
|
::glNormal3f( norm.x, norm.y, norm.z );
|
||||||
// now build strips, lerping from start to endpoint
|
::glTexCoord2f( ShapePoints[ j ].z / Texturescale, tv1 );
|
||||||
step = 10.0; // arbitrary segment size for straights
|
}
|
||||||
float s = 0.0,
|
::glVertex3f( pt.x, pt.y, pt.z ); // punkt na początku odcinka
|
||||||
t = 0.0,
|
}
|
||||||
uv = 0.0;
|
else {
|
||||||
glBegin( GL_TRIANGLE_STRIP );
|
Output->x = pt.x;
|
||||||
while( s < fLength ) {
|
Output->y = pt.y;
|
||||||
|
Output->z = pt.z;
|
||||||
t = s / fLength;
|
if( false == Onlypositions ) {
|
||||||
uv = s / fTextureLength;
|
Output->nx = norm.x;
|
||||||
|
Output->ny = norm.y;
|
||||||
auto const normal1lerp = Interpolate( startnormal1, endnormal1, t );
|
Output->nz = norm.z;
|
||||||
glNormal3dv( &normal1lerp.x );
|
Output->u = ShapePoints[ j ].z / Texturescale;
|
||||||
auto const uv1lerp = Interpolate( startuv1, enduv1, t );
|
Output->v = tv1;
|
||||||
glTexCoord2f( uv1lerp, uv );
|
}
|
||||||
auto const vertex1lerp = Interpolate( startvertex1, endvertex1, t );
|
++Output;
|
||||||
glVertex3dv( &vertex1lerp.x );
|
}
|
||||||
|
pt = parallel2 * ShapePoints[ j ].x + pos2;
|
||||||
auto const normal0lerp = Interpolate( startnormal0, endnormal0, t );
|
pt.y += ShapePoints[ j ].y;
|
||||||
glNormal3dv( &normal0lerp.x );
|
if( false == Onlypositions ) {
|
||||||
auto const uv0lerp = Interpolate( startuv0, enduv0, t );
|
norm = ShapePoints[ j ].n.x * parallel2;
|
||||||
glTexCoord2f( uv0lerp, uv );
|
norm.y += ShapePoints[ j ].n.y;
|
||||||
auto const vertex0lerp = Interpolate( startvertex0, endvertex0, t );
|
}
|
||||||
glVertex3dv( &vertex0lerp.x );
|
if( Output == nullptr ) {
|
||||||
|
// immediate mode
|
||||||
s += step;
|
if( false == Onlypositions ) {
|
||||||
}
|
::glNormal3f( norm.x, norm.y, norm.z );
|
||||||
// add ending vertex pair if needed
|
::glTexCoord2f( ShapePoints[ j ].z / Texturescale, tv2 );
|
||||||
glNormal3dv( &endnormal1.x );
|
}
|
||||||
glTexCoord2f( enduv1, fLength / fTextureLength );
|
::glVertex3f( pt.x, pt.y, pt.z ); // punkt na końcu odcinka
|
||||||
glVertex3dv( &endvertex1.x );
|
}
|
||||||
glNormal3dv( &endnormal0.x );
|
else {
|
||||||
glTexCoord2f( enduv0, fLength / fTextureLength );
|
Output->x = pt.x;
|
||||||
glVertex3dv( &endvertex0.x );
|
Output->y = pt.y;
|
||||||
|
Output->z = pt.z;
|
||||||
glEnd();
|
if( false == Onlypositions ) {
|
||||||
}
|
Output->nx = norm.x;
|
||||||
}
|
Output->ny = norm.y;
|
||||||
#endif
|
Output->nz = norm.z;
|
||||||
};
|
Output->u = ShapePoints[ j ].z / Texturescale;
|
||||||
|
Output->v = tv2;
|
||||||
void TSegment::RenderSwitchRail(const vector6 *ShapePoints1, const vector6 *ShapePoints2,
|
}
|
||||||
int iNumShapePoints, double fTextureLength, int iSkip,
|
++Output;
|
||||||
double fOffsetX)
|
}
|
||||||
{ // tworzenie siatki trójkątów dla iglicy
|
|
||||||
vector3 pos1, pos2, dir, parallel1, parallel2, pt;
|
|
||||||
double a1, a2, s, step, offset, tv1, tv2, t, t2step, oldt2;
|
|
||||||
int i, j;
|
|
||||||
if (bCurve)
|
|
||||||
{ // dla toru odchylonego
|
|
||||||
// t2= 0;
|
|
||||||
t2step = 1 / double(iSkip); // przesunięcie tekstury?
|
|
||||||
oldt2 = 1;
|
|
||||||
tv1 = 1.0;
|
|
||||||
step = fStep; // długść segmentu
|
|
||||||
s = 0;
|
|
||||||
i = 0;
|
|
||||||
t = fTsBuffer[i]; // wartość t krzywej Beziera dla początku
|
|
||||||
a1 = 0;
|
|
||||||
// step= fStep/fLength;
|
|
||||||
offset = 0.1 / fLength; // około 10cm w sensie parametru t
|
|
||||||
pos1 = FastGetPoint(t); // współrzędne dla parmatru t
|
|
||||||
// dir= GetDirection1();
|
|
||||||
dir = FastGetDirection(t, offset); // wektor wzdłużny
|
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0))); //poprzeczny?
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
|
|
||||||
while (s < fLength && i < iSkip)
|
|
||||||
{
|
|
||||||
// step= SquareMagnitude(Global::GetCameraPosition()+pos);
|
|
||||||
// t2= oldt2+t2step;
|
|
||||||
i++;
|
|
||||||
s += step;
|
|
||||||
|
|
||||||
if (s > fLength)
|
|
||||||
{
|
|
||||||
step -= (s - fLength);
|
|
||||||
s = fLength;
|
|
||||||
}
|
|
||||||
|
|
||||||
while (tv1 < 0.0)
|
|
||||||
tv1 += 1.0;
|
|
||||||
tv2 = tv1 - step / fTextureLength;
|
|
||||||
|
|
||||||
t = fTsBuffer[i];
|
|
||||||
pos2 = FastGetPoint(t);
|
|
||||||
dir = FastGetDirection(t, offset);
|
|
||||||
// parallel2=Normalize(CrossProduct(dir,vector3(0,1,0)));
|
|
||||||
parallel2 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
|
|
||||||
a2 = double(i) / (iSkip);
|
|
||||||
glBegin(GL_TRIANGLE_STRIP);
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{ // po dwa punkty trapezu
|
|
||||||
pt = parallel1 *
|
|
||||||
(ShapePoints1[j].x * a1 + (ShapePoints2[j].x - fOffsetX) * (1.0 - a1)) +
|
|
||||||
pos1;
|
|
||||||
pt.y += ShapePoints1[j].y * a1 + ShapePoints2[j].y * (1.0 - a1);
|
|
||||||
glNormal3f(0.0f, 1.0f, 0.0f);
|
|
||||||
glTexCoord2f(ShapePoints1[j].z * a1 + ShapePoints2[j].z * (1.0 - a1), tv1);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
|
|
||||||
pt = parallel2 *
|
|
||||||
(ShapePoints1[j].x * a2 + (ShapePoints2[j].x - fOffsetX) * (1.0 - a2)) +
|
|
||||||
pos2;
|
|
||||||
pt.y += ShapePoints1[j].y * a2 + ShapePoints2[j].y * (1.0 - a2);
|
|
||||||
glNormal3f(0.0f, 1.0f, 0.0f);
|
|
||||||
glTexCoord2f(ShapePoints1[j].z * a2 + ShapePoints2[j].z * (1.0 - a2), tv2);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
if( Output == nullptr ) {
|
||||||
|
// immediate mode
|
||||||
glEnd();
|
glEnd();
|
||||||
pos1 = pos2;
|
|
||||||
parallel1 = parallel2;
|
|
||||||
tv1 = tv2;
|
|
||||||
a1 = a2;
|
|
||||||
}
|
}
|
||||||
}
|
pos1 = pos2;
|
||||||
else
|
parallel1 = parallel2;
|
||||||
{ // dla toru prostego
|
if( false == Onlypositions ) {
|
||||||
tv1 = 1.0;
|
|
||||||
s = 0;
|
|
||||||
i = 0;
|
|
||||||
// pos1= FastGetPoint( (5*iSkip)/fLength );
|
|
||||||
pos1 = FastGetPoint_0();
|
|
||||||
dir = GetDirection();
|
|
||||||
// parallel1=CrossProduct(dir,vector3(0,1,0));
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
|
|
||||||
step = 5;
|
|
||||||
a1 = 0;
|
|
||||||
|
|
||||||
while (i < iSkip)
|
|
||||||
{
|
|
||||||
// step= SquareMagnitude(Global::GetCameraPosition()+pos);
|
|
||||||
i++;
|
|
||||||
s += step;
|
|
||||||
|
|
||||||
if (s > fLength)
|
|
||||||
{
|
|
||||||
step -= (s - fLength);
|
|
||||||
s = fLength;
|
|
||||||
}
|
|
||||||
|
|
||||||
while (tv1 < 0.0)
|
|
||||||
tv1 += 1.0;
|
|
||||||
|
|
||||||
tv2 = tv1 - step / fTextureLength;
|
|
||||||
|
|
||||||
t = s / fLength;
|
|
||||||
pos2 = FastGetPoint(t);
|
|
||||||
|
|
||||||
a2 = double(i) / (iSkip);
|
|
||||||
glBegin(GL_TRIANGLE_STRIP);
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{
|
|
||||||
pt = parallel1 *
|
|
||||||
(ShapePoints1[j].x * a1 + (ShapePoints2[j].x - fOffsetX) * (1.0 - a1)) +
|
|
||||||
pos1;
|
|
||||||
pt.y += ShapePoints1[j].y * a1 + ShapePoints2[j].y * (1.0 - a1);
|
|
||||||
glNormal3f(0.0f, 1.0f, 0.0f);
|
|
||||||
glTexCoord2f((ShapePoints1[j].z), tv1);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
|
|
||||||
pt = parallel1 *
|
|
||||||
(ShapePoints1[j].x * a2 + (ShapePoints2[j].x - fOffsetX) * (1.0 - a2)) +
|
|
||||||
pos2;
|
|
||||||
pt.y += ShapePoints1[j].y * a2 + ShapePoints2[j].y * (1.0 - a2);
|
|
||||||
glNormal3f(0.0f, 1.0f, 0.0f);
|
|
||||||
glTexCoord2f(ShapePoints2[j].z, tv2);
|
|
||||||
glVertex3f(pt.x, pt.y, pt.z);
|
|
||||||
}
|
|
||||||
glEnd();
|
|
||||||
pos1 = pos2;
|
|
||||||
tv1 = tv2;
|
tv1 = tv2;
|
||||||
a1 = a2;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -778,301 +576,4 @@ void TSegment::Render()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void TSegment::RaRenderLoft(CVertNormTex *&Vert, const vector6 *ShapePoints, int iNumShapePoints,
|
|
||||||
double fTextureLength, int iSkip, int iEnd, double fOffsetX)
|
|
||||||
{ // generowanie trójkątów dla odcinka trajektorii ruchu
|
|
||||||
// standardowo tworzy triangle_strip dla prostego albo ich zestaw dla łuku
|
|
||||||
// po modyfikacji - dla ujemnego (iNumShapePoints) w dodatkowych polach tabeli
|
|
||||||
// podany jest przekrój końcowy
|
|
||||||
// podsypka toru jest robiona za pomocą 6 punktów, szyna 12, drogi i rzeki na 3+2+3
|
|
||||||
// na użytek VBO strip dla łuków jest tworzony wzdłuż
|
|
||||||
// dla skróconego odcinka (iEnd<iSegCount), ShapePoints dotyczy
|
|
||||||
// końców skróconych, a nie całości (to pod kątem iglic jest)
|
|
||||||
vector3 pos1, pos2, dir, parallel1, parallel2, pt, norm;
|
|
||||||
double s, step, fOffset, tv1, tv2, t, fEnd;
|
|
||||||
int i, j;
|
|
||||||
bool trapez = iNumShapePoints < 0; // sygnalizacja trapezowatości
|
|
||||||
iNumShapePoints = abs(iNumShapePoints);
|
|
||||||
if (bCurve)
|
|
||||||
{
|
|
||||||
double m1, jmm1, m2, jmm2; // pozycje względne na odcinku 0...1 (ale nie parametr Beziera)
|
|
||||||
step = fStep;
|
|
||||||
tv1 = 1.0; // Ra: to by można było wyliczać dla odcinka, wyglądało by lepiej
|
|
||||||
s = fStep * iSkip; // iSkip - ile odcinków z początku pominąć
|
|
||||||
i = iSkip; // domyślnie 0
|
|
||||||
t = fTsBuffer[i]; // tabela wattości t dla segmentów
|
|
||||||
// BUG: length of spline can be 0, we should skip geometry generation for such cases
|
|
||||||
fOffset = 0.1 / fLength; // pierwsze 10cm
|
|
||||||
pos1 = FastGetPoint(t); // wektor początku segmentu
|
|
||||||
dir = FastGetDirection(t, fOffset); // wektor kierunku
|
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0))); //wektor prostopadły
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
if (iEnd == 0)
|
|
||||||
iEnd = iSegCount;
|
|
||||||
fEnd = fLength * double(iEnd) / double(iSegCount);
|
|
||||||
m2 = s / fEnd;
|
|
||||||
jmm2 = 1.0 - m2;
|
|
||||||
while (i < iEnd)
|
|
||||||
{
|
|
||||||
++i; // kolejny punkt łamanej
|
|
||||||
s += step; // końcowa pozycja segmentu [m]
|
|
||||||
m1 = m2;
|
|
||||||
jmm1 = jmm2; // stara pozycja
|
|
||||||
m2 = s / fEnd;
|
|
||||||
jmm2 = 1.0 - m2; // nowa pozycja
|
|
||||||
if (i == iEnd)
|
|
||||||
{ // gdy przekroczyliśmy koniec - stąd dziury w torach...
|
|
||||||
step -= (s - fEnd); // jeszcze do wyliczenia mapowania potrzebny
|
|
||||||
s = fEnd;
|
|
||||||
// i=iEnd; //20/5 ma dawać 4
|
|
||||||
m2 = 1.0;
|
|
||||||
jmm2 = 0.0;
|
|
||||||
}
|
|
||||||
while (tv1 < 0.0)
|
|
||||||
tv1 += 1.0;
|
|
||||||
tv2 = tv1 - step / fTextureLength; // mapowanie na końcu segmentu
|
|
||||||
t = fTsBuffer[i]; // szybsze od GetTFromS(s);
|
|
||||||
pos2 = FastGetPoint(t);
|
|
||||||
dir = FastGetDirection(t, fOffset); // nowy wektor kierunku
|
|
||||||
// parallel2=Normalize(CrossProduct(dir,vector3(0,1,0)));
|
|
||||||
parallel2 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
if (trapez)
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{ // współrzędne początku
|
|
||||||
norm = (jmm1 * ShapePoints[j].n.x + m1 * ShapePoints[j + iNumShapePoints].n.x) *
|
|
||||||
parallel1;
|
|
||||||
norm.y += jmm1 * ShapePoints[j].n.y + m1 * ShapePoints[j + iNumShapePoints].n.y;
|
|
||||||
pt = parallel1 * (jmm1 * (ShapePoints[j].x - fOffsetX) +
|
|
||||||
m1 * ShapePoints[j + iNumShapePoints].x) +
|
|
||||||
pos1;
|
|
||||||
pt.y += jmm1 * ShapePoints[j].y + m1 * ShapePoints[j + iNumShapePoints].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = jmm1 * ShapePoints[j].z + m1 * ShapePoints[j + iNumShapePoints].z;
|
|
||||||
Vert->v = tv1;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na początku odcinka
|
|
||||||
Vert++;
|
|
||||||
// dla trapezu drugi koniec ma inne współrzędne względne
|
|
||||||
norm = (jmm1 * ShapePoints[j].n.x + m1 * ShapePoints[j + iNumShapePoints].n.x) *
|
|
||||||
parallel2;
|
|
||||||
norm.y += jmm1 * ShapePoints[j].n.y + m1 * ShapePoints[j + iNumShapePoints].n.y;
|
|
||||||
pt = parallel2 * (jmm2 * (ShapePoints[j].x - fOffsetX) +
|
|
||||||
m2 * ShapePoints[j + iNumShapePoints].x) +
|
|
||||||
pos2;
|
|
||||||
pt.y += jmm2 * ShapePoints[j].y + m2 * ShapePoints[j + iNumShapePoints].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = jmm2 * ShapePoints[j].z + m2 * ShapePoints[j + iNumShapePoints].z;
|
|
||||||
Vert->v = tv2;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na końcu odcinka
|
|
||||||
Vert++;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{ // współrzędne początku
|
|
||||||
norm = ShapePoints[j].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel1 * (ShapePoints[j].x - fOffsetX) + pos1;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = ShapePoints[j].z;
|
|
||||||
Vert->v = tv1;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na początku odcinka
|
|
||||||
Vert++;
|
|
||||||
norm = ShapePoints[j].n.x * parallel2;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel2 * ShapePoints[j].x + pos2;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = ShapePoints[j].z;
|
|
||||||
Vert->v = tv2;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na końcu odcinka
|
|
||||||
Vert++;
|
|
||||||
}
|
|
||||||
pos1 = pos2;
|
|
||||||
parallel1 = parallel2;
|
|
||||||
tv1 = tv2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{ // gdy prosty
|
|
||||||
pos1 = FastGetPoint((fStep * iSkip) / fLength);
|
|
||||||
pos2 = FastGetPoint_1();
|
|
||||||
dir = GetDirection();
|
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0)));
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
if (trapez)
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{
|
|
||||||
norm = ShapePoints[j].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel1 * (ShapePoints[j].x - fOffsetX) + pos1;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = ShapePoints[j].z;
|
|
||||||
Vert->v = 0;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na początku odcinka
|
|
||||||
Vert++;
|
|
||||||
// dla trapezu drugi koniec ma inne współrzędne
|
|
||||||
norm = ShapePoints[j + iNumShapePoints].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j + iNumShapePoints].n.y;
|
|
||||||
pt = parallel1 * (ShapePoints[j + iNumShapePoints].x - fOffsetX) +
|
|
||||||
pos2; // odsunięcie
|
|
||||||
pt.y += ShapePoints[j + iNumShapePoints].y; // wysokość
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = ShapePoints[j + iNumShapePoints].z;
|
|
||||||
Vert->v = fLength / fTextureLength;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na końcu odcinka
|
|
||||||
Vert++;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{
|
|
||||||
norm = ShapePoints[j].n.x * parallel1;
|
|
||||||
norm.y += ShapePoints[j].n.y;
|
|
||||||
pt = parallel1 * (ShapePoints[j].x - fOffsetX) + pos1;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = ShapePoints[j].z;
|
|
||||||
Vert->v = 0;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na początku odcinka
|
|
||||||
Vert++;
|
|
||||||
pt = parallel1 * (ShapePoints[j].x - fOffsetX) + pos2;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
Vert->nx = norm.x; // niekoniecznie tak
|
|
||||||
Vert->ny = norm.y;
|
|
||||||
Vert->nz = norm.z;
|
|
||||||
Vert->u = ShapePoints[j].z;
|
|
||||||
Vert->v = fLength / fTextureLength;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na końcu odcinka
|
|
||||||
Vert++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
void TSegment::RaAnimate(CVertNormTex *&Vert, const vector6 *ShapePoints, int iNumShapePoints,
|
|
||||||
double fTextureLength, int iSkip, int iEnd, double fOffsetX)
|
|
||||||
{ // jak wyżej, tylko z pominięciem mapowania i braku trapezowania
|
|
||||||
vector3 pos1, pos2, dir, parallel1, parallel2, pt;
|
|
||||||
double s, step, fOffset, t, fEnd;
|
|
||||||
int i, j;
|
|
||||||
bool trapez = iNumShapePoints < 0; // sygnalizacja trapezowatości
|
|
||||||
iNumShapePoints = abs(iNumShapePoints);
|
|
||||||
if (bCurve)
|
|
||||||
{
|
|
||||||
double m1, jmm1, m2, jmm2; // pozycje względne na odcinku 0...1 (ale nie parametr Beziera)
|
|
||||||
step = fStep;
|
|
||||||
s = fStep * iSkip; // iSkip - ile odcinków z początku pominąć
|
|
||||||
i = iSkip; // domyślnie 0
|
|
||||||
t = fTsBuffer[i]; // tabela wattości t dla segmentów
|
|
||||||
fOffset = 0.1 / fLength; // pierwsze 10cm
|
|
||||||
pos1 = FastGetPoint(t); // wektor początku segmentu
|
|
||||||
dir = FastGetDirection(t, fOffset); // wektor kierunku
|
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0))); //wektor prostopadły
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
if (iEnd == 0)
|
|
||||||
iEnd = iSegCount;
|
|
||||||
fEnd = fLength * double(iEnd) / double(iSegCount);
|
|
||||||
m2 = s / fEnd;
|
|
||||||
jmm2 = 1.0 - m2;
|
|
||||||
while (i < iEnd)
|
|
||||||
{
|
|
||||||
++i; // kolejny punkt łamanej
|
|
||||||
s += step; // końcowa pozycja segmentu [m]
|
|
||||||
m1 = m2;
|
|
||||||
jmm1 = jmm2; // stara pozycja
|
|
||||||
m2 = s / fEnd;
|
|
||||||
jmm2 = 1.0 - m2; // nowa pozycja
|
|
||||||
if (i == iEnd)
|
|
||||||
{ // gdy przekroczyliśmy koniec - stąd dziury w torach...
|
|
||||||
step -= (s - fEnd); // jeszcze do wyliczenia mapowania potrzebny
|
|
||||||
s = fEnd;
|
|
||||||
// i=iEnd; //20/5 ma dawać 4
|
|
||||||
m2 = 1.0;
|
|
||||||
jmm2 = 0.0;
|
|
||||||
}
|
|
||||||
t = fTsBuffer[i]; // szybsze od GetTFromS(s);
|
|
||||||
pos2 = FastGetPoint(t);
|
|
||||||
dir = FastGetDirection(t, fOffset); // nowy wektor kierunku
|
|
||||||
// parallel2=Normalize(CrossProduct(dir,vector3(0,1,0)));
|
|
||||||
parallel2 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
if (trapez)
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{ // współrzędne początku
|
|
||||||
pt = parallel1 * (jmm1 * (ShapePoints[j].x - fOffsetX) +
|
|
||||||
m1 * ShapePoints[j + iNumShapePoints].x) +
|
|
||||||
pos1;
|
|
||||||
pt.y += jmm1 * ShapePoints[j].y + m1 * ShapePoints[j + iNumShapePoints].y;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na początku odcinka
|
|
||||||
Vert++;
|
|
||||||
// dla trapezu drugi koniec ma inne współrzędne
|
|
||||||
pt = parallel2 * (jmm2 * (ShapePoints[j].x - fOffsetX) +
|
|
||||||
m2 * ShapePoints[j + iNumShapePoints].x) +
|
|
||||||
pos2;
|
|
||||||
pt.y += jmm2 * ShapePoints[j].y + m2 * ShapePoints[j + iNumShapePoints].y;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na końcu odcinka
|
|
||||||
Vert++;
|
|
||||||
}
|
|
||||||
pos1 = pos2;
|
|
||||||
parallel1 = parallel2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{ // gdy prosty
|
|
||||||
pos1 = FastGetPoint((fStep * iSkip) / fLength);
|
|
||||||
pos2 = FastGetPoint_1();
|
|
||||||
dir = GetDirection();
|
|
||||||
// parallel1=Normalize(CrossProduct(dir,vector3(0,1,0)));
|
|
||||||
parallel1 = Normalize(vector3(-dir.z, 0.0, dir.x)); // wektor poprzeczny
|
|
||||||
if (trapez)
|
|
||||||
for (j = 0; j < iNumShapePoints; j++)
|
|
||||||
{
|
|
||||||
pt = parallel1 * (ShapePoints[j].x - fOffsetX) + pos1;
|
|
||||||
pt.y += ShapePoints[j].y;
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na początku odcinka
|
|
||||||
Vert++;
|
|
||||||
pt = parallel1 * (ShapePoints[j + iNumShapePoints].x - fOffsetX) +
|
|
||||||
pos2; // odsunięcie
|
|
||||||
pt.y += ShapePoints[j + iNumShapePoints].y; // wysokość
|
|
||||||
Vert->x = pt.x;
|
|
||||||
Vert->y = pt.y;
|
|
||||||
Vert->z = pt.z; // punkt na końcu odcinka
|
|
||||||
Vert++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|||||||
23
Segment.h
23
Segment.h
@@ -13,6 +13,7 @@ http://mozilla.org/MPL/2.0/.
|
|||||||
#include "VBO.h"
|
#include "VBO.h"
|
||||||
#include "dumb3d.h"
|
#include "dumb3d.h"
|
||||||
#include "Classes.h"
|
#include "Classes.h"
|
||||||
|
#include "usefull.h"
|
||||||
|
|
||||||
using namespace Math3D;
|
using namespace Math3D;
|
||||||
|
|
||||||
@@ -61,8 +62,6 @@ class TSegment
|
|||||||
double fDirection = 0.0; // Ra: kąt prostego w planie; dla łuku kąt od Point1
|
double fDirection = 0.0; // Ra: kąt prostego w planie; dla łuku kąt od Point1
|
||||||
double fStoop = 0.0; // Ra: kąt wzniesienia; dla łuku od Point1
|
double fStoop = 0.0; // Ra: kąt wzniesienia; dla łuku od Point1
|
||||||
vector3 vA, vB, vC; // współczynniki wielomianów trzeciego stopnia vD==Point1
|
vector3 vA, vB, vC; // współczynniki wielomianów trzeciego stopnia vD==Point1
|
||||||
// TSegment *pPrev; //odcinek od strony punktu 1 - w segmencie, żeby nie skakać na zwrotnicach
|
|
||||||
// TSegment *pNext; //odcinek od strony punktu 2
|
|
||||||
TTrack *pOwner = nullptr; // wskaźnik na właściciela
|
TTrack *pOwner = nullptr; // wskaźnik na właściciela
|
||||||
double fAngle[2]; // kąty zakończenia drogi na przejazdach
|
double fAngle[2]; // kąty zakończenia drogi na przejazdach
|
||||||
|
|
||||||
@@ -71,12 +70,8 @@ class TSegment
|
|||||||
double GetTFromS(double s);
|
double GetTFromS(double s);
|
||||||
vector3 RaInterpolate(double t);
|
vector3 RaInterpolate(double t);
|
||||||
vector3 RaInterpolate0(double t);
|
vector3 RaInterpolate0(double t);
|
||||||
// TSegment *segNeightbour[2]; //sąsiednie odcinki - musi być przeniesione z Track
|
|
||||||
// int iNeightbour[2]; //do którego końca doczepiony
|
|
||||||
public:
|
public:
|
||||||
bool bCurve = false;
|
bool bCurve = false;
|
||||||
// int iShape; //Ra: flagi kształtu dadzą więcej możliwości optymalizacji
|
|
||||||
// (0-Bezier,1-prosty,2/3-łuk w lewo/prawo,6/7-przejściowa w lewo/prawo)
|
|
||||||
TSegment(TTrack *owner);
|
TSegment(TTrack *owner);
|
||||||
~TSegment();
|
~TSegment();
|
||||||
bool Init(vector3 NewPoint1, vector3 NewPoint2, double fNewStep, double fNewRoll1 = 0,
|
bool Init(vector3 NewPoint1, vector3 NewPoint2, double fNewStep, double fNewRoll1 = 0,
|
||||||
@@ -109,21 +104,16 @@ class TSegment
|
|||||||
{
|
{
|
||||||
return Point2;
|
return Point2;
|
||||||
};
|
};
|
||||||
inline double GetRoll(double s)
|
inline double GetRoll(double const Distance)
|
||||||
{
|
{
|
||||||
s /= fLength;
|
return interpolate( fRoll1, fRoll2, Distance / fLength );
|
||||||
return ((1.0 - s) * fRoll1 + s * fRoll2);
|
|
||||||
}
|
}
|
||||||
void GetRolls(double &r1, double &r2)
|
void GetRolls(double &r1, double &r2)
|
||||||
{ // pobranie przechyłek (do generowania trójkątów)
|
{ // pobranie przechyłek (do generowania trójkątów)
|
||||||
r1 = fRoll1;
|
r1 = fRoll1;
|
||||||
r2 = fRoll2;
|
r2 = fRoll2;
|
||||||
}
|
}
|
||||||
void RenderLoft(const vector6 *ShapePoints, int iNumShapePoints, double fTextureLength,
|
void RenderLoft( CVertNormTex* &Output, const vector6 *ShapePoints, int iNumShapePoints, double fTextureLength, double Texturescale = 1.0, int iSkip = 0, int iEnd = 0, double fOffsetX = 0.0, bool Onlypositions = false, vector3 **p = nullptr, bool bRender = true);
|
||||||
int iSkip = 0, int iQualityFactor = 1, vector3 **p = NULL, bool bRender = true);
|
|
||||||
void RenderSwitchRail(const vector6 *ShapePoints1, const vector6 *ShapePoints2,
|
|
||||||
int iNumShapePoints, double fTextureLength, int iSkip = 0,
|
|
||||||
double fOffsetX = 0.0f);
|
|
||||||
void Render();
|
void Render();
|
||||||
inline double GetLength()
|
inline double GetLength()
|
||||||
{
|
{
|
||||||
@@ -143,15 +133,10 @@ class TSegment
|
|||||||
{
|
{
|
||||||
return fTsBuffer ? iSegCount : 1;
|
return fTsBuffer ? iSegCount : 1;
|
||||||
};
|
};
|
||||||
void RaRenderLoft(CVertNormTex *&Vert, const vector6 *ShapePoints, int iNumShapePoints,
|
|
||||||
double fTextureLength, int iSkip = 0, int iEnd = 0, double fOffsetX = 0.0);
|
|
||||||
void RaAnimate(CVertNormTex *&Vert, const vector6 *ShapePoints, int iNumShapePoints,
|
|
||||||
double fTextureLength, int iSkip = 0, int iEnd = 0, double fOffsetX = 0.0);
|
|
||||||
void AngleSet(int i, double a)
|
void AngleSet(int i, double a)
|
||||||
{
|
{
|
||||||
fAngle[i] = a;
|
fAngle[i] = a;
|
||||||
};
|
};
|
||||||
void Rollment(double w1, double w2); // poprawianie przechyłki
|
|
||||||
};
|
};
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
|||||||
8
dumb3d.h
8
dumb3d.h
@@ -104,14 +104,8 @@ class vector3
|
|||||||
return &x;
|
return &x;
|
||||||
}
|
}
|
||||||
|
|
||||||
// union
|
|
||||||
// {
|
|
||||||
// struct
|
|
||||||
// {
|
|
||||||
double x, y, z;
|
double x, y, z;
|
||||||
// };
|
|
||||||
// scalar_t e[3];
|
|
||||||
// };
|
|
||||||
bool inline Equal(vector3 *v)
|
bool inline Equal(vector3 *v)
|
||||||
{ // sprawdzenie odległości punktów
|
{ // sprawdzenie odległości punktów
|
||||||
if (std::fabs(x - v->x) > 0.02)
|
if (std::fabs(x - v->x) > 0.02)
|
||||||
|
|||||||
305
renderer.cpp
305
renderer.cpp
@@ -11,8 +11,11 @@ http://mozilla.org/MPL/2.0/.
|
|||||||
|
|
||||||
#include "renderer.h"
|
#include "renderer.h"
|
||||||
#include "globals.h"
|
#include "globals.h"
|
||||||
|
#include "timer.h"
|
||||||
#include "world.h"
|
#include "world.h"
|
||||||
#include "dynobj.h"
|
#include "dynobj.h"
|
||||||
|
#include "animmodel.h"
|
||||||
|
#include "traction.h"
|
||||||
#include "uilayer.h"
|
#include "uilayer.h"
|
||||||
#include "logs.h"
|
#include "logs.h"
|
||||||
#include "usefull.h"
|
#include "usefull.h"
|
||||||
@@ -31,11 +34,11 @@ bool
|
|||||||
opengl_camera::visible( TDynamicObject const *Dynamic ) const {
|
opengl_camera::visible( TDynamicObject const *Dynamic ) const {
|
||||||
|
|
||||||
// sphere test is faster than AABB, so we'll use it here
|
// sphere test is faster than AABB, so we'll use it here
|
||||||
float3 diagonal(
|
glm::vec3 diagonal(
|
||||||
Dynamic->MoverParameters->Dim.L,
|
static_cast<float>( Dynamic->MoverParameters->Dim.L ),
|
||||||
Dynamic->MoverParameters->Dim.H,
|
static_cast<float>( Dynamic->MoverParameters->Dim.H ),
|
||||||
Dynamic->MoverParameters->Dim.W );
|
static_cast<float>( Dynamic->MoverParameters->Dim.W ) );
|
||||||
float const radius = diagonal.Length() * 0.5f;
|
float const radius = glm::length( diagonal ) * 0.5f;
|
||||||
|
|
||||||
return ( m_frustum.sphere_inside( Dynamic->GetPosition(), radius ) > 0.0f );
|
return ( m_frustum.sphere_inside( Dynamic->GetPosition(), radius ) > 0.0f );
|
||||||
}
|
}
|
||||||
@@ -183,7 +186,7 @@ opengl_renderer::Render( world_environment *Environment ) {
|
|||||||
if( Global::fFogEnd > 0 ) {
|
if( Global::fFogEnd > 0 ) {
|
||||||
// fog setup
|
// fog setup
|
||||||
::glFogfv( GL_FOG_COLOR, Global::FogColor );
|
::glFogfv( GL_FOG_COLOR, Global::FogColor );
|
||||||
::glFogf( GL_FOG_DENSITY, 1.0f / Global::fFogEnd );
|
::glFogf( GL_FOG_DENSITY, static_cast<GLfloat>( 1.0 / Global::fFogEnd ) );
|
||||||
::glEnable( GL_FOG );
|
::glEnable( GL_FOG );
|
||||||
}
|
}
|
||||||
else { ::glDisable( GL_FOG ); }
|
else { ::glDisable( GL_FOG ); }
|
||||||
@@ -236,7 +239,7 @@ opengl_renderer::Render( world_environment *Environment ) {
|
|||||||
{
|
{
|
||||||
Bind( m_moontextureid );
|
Bind( m_moontextureid );
|
||||||
float3 mooncolor( 255.0f / 255.0f, 242.0f / 255.0f, 231.0f / 255.0f );
|
float3 mooncolor( 255.0f / 255.0f, 242.0f / 255.0f, 231.0f / 255.0f );
|
||||||
::glColor4f( mooncolor.x, mooncolor.y, mooncolor.z, 1.0f - Global::fLuminance * 0.5f );
|
::glColor4f( mooncolor.x, mooncolor.y, mooncolor.z, static_cast<GLfloat>( 1.0 - Global::fLuminance * 0.5 ) );
|
||||||
|
|
||||||
auto const moonvector = Environment->m_moon.getDirection();
|
auto const moonvector = Environment->m_moon.getDirection();
|
||||||
auto const moonposition = modelview * glm::vec4( moonvector.x, moonvector.y, moonvector.z, 1.0f );
|
auto const moonposition = modelview * glm::vec4( moonvector.x, moonvector.y, moonvector.z, 1.0f );
|
||||||
@@ -296,9 +299,9 @@ opengl_renderer::Render( TGround *Ground ) {
|
|||||||
glEnable( GL_LIGHTING );
|
glEnable( GL_LIGHTING );
|
||||||
glColor3f( 1.0f, 1.0f, 1.0f );
|
glColor3f( 1.0f, 1.0f, 1.0f );
|
||||||
|
|
||||||
float3 const cameraposition = float3( Global::pCameraPosition.x, Global::pCameraPosition.y, Global::pCameraPosition.z );
|
glm::vec3 const cameraposition( Global::pCameraPosition.x, Global::pCameraPosition.y, Global::pCameraPosition.z );
|
||||||
int const camerax = std::floor( cameraposition.x / 1000.0f ) + iNumRects / 2;
|
int const camerax = static_cast<int>( std::floor( cameraposition.x / 1000.0f ) + iNumRects / 2 );
|
||||||
int const cameraz = std::floor( cameraposition.z / 1000.0f ) + iNumRects / 2;
|
int const cameraz = static_cast<int>( std::floor( cameraposition.z / 1000.0f ) + iNumRects / 2 );
|
||||||
int const segmentcount = 2 * static_cast<int>(std::ceil( m_drawrange * Global::fDistanceFactor / 1000.0f ));
|
int const segmentcount = 2 * static_cast<int>(std::ceil( m_drawrange * Global::fDistanceFactor / 1000.0f ));
|
||||||
int const originx = std::max( 0, camerax - segmentcount / 2 );
|
int const originx = std::max( 0, camerax - segmentcount / 2 );
|
||||||
int const originz = std::max( 0, cameraz - segmentcount / 2 );
|
int const originz = std::max( 0, cameraz - segmentcount / 2 );
|
||||||
@@ -317,15 +320,133 @@ opengl_renderer::Render( TGround *Ground ) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
opengl_renderer::Render( TDynamicObject *Dynamic ) {
|
opengl_renderer::Render( TGroundNode *Node ) {
|
||||||
|
|
||||||
if( false == m_camera.visible( Dynamic ) ) {
|
Node->SetLastUsage( Timer::GetSimulationTime() );
|
||||||
|
|
||||||
Dynamic->renderme = false;
|
switch (Node->iType)
|
||||||
|
{ // obiekty renderowane niezależnie od odległości
|
||||||
|
case TP_SUBMODEL:
|
||||||
|
TSubModel::fSquareDist = 0;
|
||||||
|
Render( Node->smTerrain );
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
double const distancesquared = SquareMagnitude( ( Node->pCenter - Global::pCameraPosition ) / Global::ZoomFactor );
|
||||||
|
if( ( distancesquared > ( Node->fSquareRadius * Global::fDistanceFactor ) )
|
||||||
|
|| ( distancesquared < ( Node->fSquareMinRadius / Global::fDistanceFactor ) ) ) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Dynamic->renderme = true;
|
switch (Node->iType)
|
||||||
|
{
|
||||||
|
case TP_TRACK: {
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( Global::bUseVBO ) {
|
||||||
|
if( Node->iNumVerts ) {
|
||||||
|
Node->pTrack->RaRenderVBO( Node->iVboPtr );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
Node->pTrack->Render();
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
case TP_MODEL: {
|
||||||
|
Node->Model->Render( &Node->pCenter );
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
case TP_MEMCELL: {
|
||||||
|
GfxRenderer.Render( Node->MemCell );
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: sprawdzic czy jest potrzebny warunek fLineThickness < 0
|
||||||
|
if( ( Node->iFlags & 0x10 )
|
||||||
|
|| ( Node->fLineThickness < 0 ) ) {
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( false == Global::bUseVBO ) {
|
||||||
|
// additional setup for display lists
|
||||||
|
if( ( Node->DisplayListID == 0 )
|
||||||
|
|| ( Node->iVersion != Global::iReCompile ) ) { // Ra: wymuszenie rekompilacji
|
||||||
|
Node->Compile();
|
||||||
|
if( Global::bManageNodes )
|
||||||
|
ResourceManager::Register( Node );
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
if( ( Node->iType == GL_LINES )
|
||||||
|
|| ( Node->iType == GL_LINE_STRIP )
|
||||||
|
|| ( Node->iType == GL_LINE_LOOP ) ) {
|
||||||
|
// wszelkie linie są rysowane na samym końcu
|
||||||
|
if( Node->iNumPts ) {
|
||||||
|
// setup
|
||||||
|
// w zaleznosci od koloru swiatla
|
||||||
|
::glColor4ub(
|
||||||
|
static_cast<GLubyte>( std::floor( Node->Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ] ) ),
|
||||||
|
static_cast<GLubyte>( std::floor( Node->Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ] ) ),
|
||||||
|
static_cast<GLubyte>( std::floor( Node->Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ] ) ),
|
||||||
|
static_cast<GLubyte>( std::min( 255.0, 255000 * Node->fLineThickness / ( distancesquared + 1.0 ) ) ) );
|
||||||
|
|
||||||
|
GfxRenderer.Bind( 0 );
|
||||||
|
|
||||||
|
// render
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( Global::bUseVBO ) {
|
||||||
|
::glDrawArrays( Node->iType, Node->iVboPtr, Node->iNumPts );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
::glCallList( Node->DisplayListID );
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// GL_TRIANGLE etc
|
||||||
|
// setup
|
||||||
|
::glColor3ub(
|
||||||
|
static_cast<GLubyte>( Node->Diffuse[ 0 ] ),
|
||||||
|
static_cast<GLubyte>( Node->Diffuse[ 1 ] ),
|
||||||
|
static_cast<GLubyte>( Node->Diffuse[ 2 ] ) );
|
||||||
|
|
||||||
|
Bind( Node->TextureID );
|
||||||
|
|
||||||
|
// render
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( Global::bUseVBO ) {
|
||||||
|
// vbo render path
|
||||||
|
if( Node->iVboPtr >= 0 ) {
|
||||||
|
::glDrawArrays( Node->iType, Node->iVboPtr, Node->iNumVerts );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// display list render path
|
||||||
|
::glCallList( Node->DisplayListID );
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// in theory we shouldn't ever get here but, eh
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
opengl_renderer::Render( TDynamicObject *Dynamic ) {
|
||||||
|
|
||||||
|
Dynamic->renderme = m_camera.visible( Dynamic );
|
||||||
|
if( false == Dynamic->renderme ) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
// setup
|
// setup
|
||||||
TSubModel::iInstance = ( size_t )this; //żeby nie robić cudzych animacji
|
TSubModel::iInstance = ( size_t )this; //żeby nie robić cudzych animacji
|
||||||
@@ -517,7 +638,7 @@ opengl_renderer::Render( TSubModel *Submodel ) {
|
|||||||
float const anglefactor = ( Submodel->fCosViewAngle - Submodel->fCosFalloffAngle ) / ( 1.0f - Submodel->fCosFalloffAngle );
|
float const anglefactor = ( Submodel->fCosViewAngle - Submodel->fCosFalloffAngle ) / ( 1.0f - Submodel->fCosFalloffAngle );
|
||||||
// distance attenuation. NOTE: since it's fixed pipeline with built-in gamma correction we're using linear attenuation
|
// distance attenuation. NOTE: since it's fixed pipeline with built-in gamma correction we're using linear attenuation
|
||||||
// we're capping how much effect the distance attenuation can have, otherwise the lights get too tiny at regular distances
|
// we're capping how much effect the distance attenuation can have, otherwise the lights get too tiny at regular distances
|
||||||
float const distancefactor = std::max( 0.5, ( Submodel->fSquareMaxDist - TSubModel::fSquareDist ) / ( Submodel->fSquareMaxDist * Global::fDistanceFactor ) );
|
float const distancefactor = static_cast<float>( std::max( 0.5, ( Submodel->fSquareMaxDist - TSubModel::fSquareDist ) / ( Submodel->fSquareMaxDist * Global::fDistanceFactor ) ) );
|
||||||
|
|
||||||
if( lightlevel > 0.0f ) {
|
if( lightlevel > 0.0f ) {
|
||||||
// material configuration:
|
// material configuration:
|
||||||
@@ -609,6 +730,146 @@ opengl_renderer::Render( TMemCell *Memcell ) {
|
|||||||
::glPopAttrib();
|
::glPopAttrib();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// NOTE: legacy render system switch
|
||||||
|
#define _PROBLEND
|
||||||
|
|
||||||
|
bool
|
||||||
|
opengl_renderer::Render_Alpha( TGroundNode *Node ) {
|
||||||
|
|
||||||
|
// SPOSOB NA POZBYCIE SIE RAMKI DOOKOLA TEXTURY ALPHA DLA OBIEKTOW ZAGNIEZDZONYCH W SCN JAKO
|
||||||
|
// NODE
|
||||||
|
|
||||||
|
// W GROUND.H dajemy do klasy TGroundNode zmienna bool PROBLEND to samo robimy w klasie TGround
|
||||||
|
// nastepnie podczas wczytywania textury dla TRIANGLES w TGround::AddGroundNode
|
||||||
|
// sprawdzamy czy w nazwie jest @ i wg tego
|
||||||
|
// ustawiamy PROBLEND na true dla wlasnie wczytywanego trojkata (kazdy trojkat jest osobnym
|
||||||
|
// nodem)
|
||||||
|
// nastepnie podczas renderowania w bool TGroundNode::RenderAlpha()
|
||||||
|
// na poczatku ustawiamy standardowe GL_GREATER = 0.04
|
||||||
|
// pozniej sprawdzamy czy jest wlaczony PROBLEND dla aktualnie renderowanego noda TRIANGLE,
|
||||||
|
// wlasciwie dla kazdego node'a
|
||||||
|
// i jezeli tak to odpowiedni GL_GREATER w przeciwnym wypadku standardowy 0.04
|
||||||
|
|
||||||
|
Node->SetLastUsage( Timer::GetSimulationTime() );
|
||||||
|
|
||||||
|
double const distancesquared = SquareMagnitude( ( Node->pCenter - Global::pCameraPosition ) / Global::ZoomFactor );
|
||||||
|
if( ( distancesquared > ( Node->fSquareRadius * Global::fDistanceFactor ) )
|
||||||
|
|| ( distancesquared < ( Node->fSquareMinRadius / Global::fDistanceFactor ) ) ) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (Node->iType)
|
||||||
|
{
|
||||||
|
case TP_TRACTION: {
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( Node->bVisible ) {
|
||||||
|
if( Global::bUseVBO ) {
|
||||||
|
Node->hvTraction->RenderVBO( distancesquared, Node->iVboPtr );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
Node->hvTraction->RenderDL( distancesquared );
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case TP_MODEL: {
|
||||||
|
Node->Model->RenderAlpha( &Node->pCenter );
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: sprawdzic czy jest potrzebny warunek fLineThickness < 0
|
||||||
|
if( ( Node->iNumVerts && ( Node->iFlags & 0x20 ) )
|
||||||
|
|| ( Node->iNumPts && ( Node->fLineThickness > 0 ) ) ) {
|
||||||
|
|
||||||
|
#ifdef _PROBLEND
|
||||||
|
if( ( Node->PROBLEND ) ) // sprawdza, czy w nazwie nie ma @ //Q: 13122011 - Szociu: 27012012
|
||||||
|
{
|
||||||
|
::glDisable( GL_BLEND );
|
||||||
|
::glAlphaFunc( GL_GREATER, 0.50f ); // im mniejsza wartość, tym większa ramka, domyślnie 0.1f
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( false == Global::bUseVBO ) {
|
||||||
|
// additional setup for display lists
|
||||||
|
if( ( Node->DisplayListID == 0 )
|
||||||
|
|| ( Node->iVersion != Global::iReCompile ) ) { // Ra: wymuszenie rekompilacji
|
||||||
|
Node->Compile();
|
||||||
|
if( Global::bManageNodes )
|
||||||
|
ResourceManager::Register( Node );
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
bool result( false );
|
||||||
|
|
||||||
|
if( ( Node->iType == GL_LINES )
|
||||||
|
|| ( Node->iType == GL_LINE_STRIP )
|
||||||
|
|| ( Node->iType == GL_LINE_LOOP ) ) {
|
||||||
|
// wszelkie linie są rysowane na samym końcu
|
||||||
|
if( Node->iNumPts ) {
|
||||||
|
// setup
|
||||||
|
// w zaleznosci od koloru swiatla
|
||||||
|
::glColor4ub(
|
||||||
|
static_cast<GLubyte>( std::floor( Node->Diffuse[ 0 ] * Global::DayLight.ambient[ 0 ] ) ),
|
||||||
|
static_cast<GLubyte>( std::floor( Node->Diffuse[ 1 ] * Global::DayLight.ambient[ 1 ] ) ),
|
||||||
|
static_cast<GLubyte>( std::floor( Node->Diffuse[ 2 ] * Global::DayLight.ambient[ 2 ] ) ),
|
||||||
|
static_cast<GLubyte>( std::min( 255.0, 255000 * Node->fLineThickness / ( distancesquared + 1.0 ) ) ) );
|
||||||
|
|
||||||
|
GfxRenderer.Bind( 0 );
|
||||||
|
|
||||||
|
// render
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( Global::bUseVBO ) {
|
||||||
|
::glDrawArrays( Node->iType, Node->iVboPtr, Node->iNumPts );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
::glCallList( Node->DisplayListID );
|
||||||
|
}
|
||||||
|
result = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// GL_TRIANGLE etc
|
||||||
|
// setup
|
||||||
|
::glColor3ub(
|
||||||
|
static_cast<GLubyte>( Node->Diffuse[ 0 ] ),
|
||||||
|
static_cast<GLubyte>( Node->Diffuse[ 1 ] ),
|
||||||
|
static_cast<GLubyte>( Node->Diffuse[ 2 ] ) );
|
||||||
|
|
||||||
|
Bind( Node->TextureID );
|
||||||
|
|
||||||
|
// render
|
||||||
|
// TODO: unify the render code after generic buffers are in place
|
||||||
|
if( Global::bUseVBO ) {
|
||||||
|
// vbo render path
|
||||||
|
if( Node->iVboPtr >= 0 ) {
|
||||||
|
::glDrawArrays( Node->iType, Node->iVboPtr, Node->iNumVerts );
|
||||||
|
result = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// display list render path
|
||||||
|
::glCallList( Node->DisplayListID );
|
||||||
|
result = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// post-render cleanup
|
||||||
|
#ifdef _PROBLEND
|
||||||
|
if( ( Node->PROBLEND ) ) // sprawdza, czy w nazwie nie ma @ //Q: 13122011 - Szociu: 27012012
|
||||||
|
{
|
||||||
|
::glEnable( GL_BLEND );
|
||||||
|
::glAlphaFunc( GL_GREATER, 0.04f );
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
// in theory we shouldn't ever get here but, eh
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
opengl_renderer::Render_Alpha( TDynamicObject *Dynamic ) {
|
opengl_renderer::Render_Alpha( TDynamicObject *Dynamic ) {
|
||||||
|
|
||||||
@@ -978,12 +1239,12 @@ opengl_renderer::Update_Lights( light_array const &Lights ) {
|
|||||||
if( environment > 0.0f ) {
|
if( environment > 0.0f ) {
|
||||||
luminance *= environment;
|
luminance *= environment;
|
||||||
}
|
}
|
||||||
renderlight->diffuse[ 0 ] = std::max( 0.0, scenelight.color.x - luminance );
|
renderlight->diffuse[ 0 ] = static_cast<GLfloat>( std::max( 0.0, scenelight.color.x - luminance ) );
|
||||||
renderlight->diffuse[ 1 ] = std::max( 0.0, scenelight.color.y - luminance );
|
renderlight->diffuse[ 1 ] = static_cast<GLfloat>( std::max( 0.0, scenelight.color.y - luminance ) );
|
||||||
renderlight->diffuse[ 2 ] = std::max( 0.0, scenelight.color.z - luminance );
|
renderlight->diffuse[ 2 ] = static_cast<GLfloat>( std::max( 0.0, scenelight.color.z - luminance ) );
|
||||||
renderlight->ambient[ 0 ] = std::max( 0.0, scenelight.color.x * scenelight.intensity - luminance);
|
renderlight->ambient[ 0 ] = static_cast<GLfloat>( std::max( 0.0, scenelight.color.x * scenelight.intensity - luminance) );
|
||||||
renderlight->ambient[ 1 ] = std::max( 0.0, scenelight.color.y * scenelight.intensity - luminance );
|
renderlight->ambient[ 1 ] = static_cast<GLfloat>( std::max( 0.0, scenelight.color.y * scenelight.intensity - luminance ) );
|
||||||
renderlight->ambient[ 2 ] = std::max( 0.0, scenelight.color.z * scenelight.intensity - luminance );
|
renderlight->ambient[ 2 ] = static_cast<GLfloat>( std::max( 0.0, scenelight.color.z * scenelight.intensity - luminance ) );
|
||||||
/*
|
/*
|
||||||
// NOTE: we have no simple way to determine whether the lights are falling on objects located in darker environment
|
// NOTE: we have no simple way to determine whether the lights are falling on objects located in darker environment
|
||||||
// until this issue is resolved we're disabling reduction of light strenght based on the global luminance
|
// until this issue is resolved we're disabling reduction of light strenght based on the global luminance
|
||||||
@@ -994,7 +1255,7 @@ opengl_renderer::Update_Lights( light_array const &Lights ) {
|
|||||||
renderlight->ambient[ 1 ] = std::max( 0.0f, scenelight.color.y * scenelight.intensity );
|
renderlight->ambient[ 1 ] = std::max( 0.0f, scenelight.color.y * scenelight.intensity );
|
||||||
renderlight->ambient[ 2 ] = std::max( 0.0f, scenelight.color.z * scenelight.intensity );
|
renderlight->ambient[ 2 ] = std::max( 0.0f, scenelight.color.z * scenelight.intensity );
|
||||||
*/
|
*/
|
||||||
::glLightf( renderlight->id, GL_LINEAR_ATTENUATION, (0.25f * scenelight.count) / std::pow( scenelight.count, 2 ) * (scenelight.owner->DimHeadlights ? 1.25f : 1.0f) );
|
::glLightf( renderlight->id, GL_LINEAR_ATTENUATION, static_cast<GLfloat>( (0.25 * scenelight.count) / std::pow( scenelight.count, 2 ) * (scenelight.owner->DimHeadlights ? 1.25 : 1.0) ) );
|
||||||
::glEnable( renderlight->id );
|
::glEnable( renderlight->id );
|
||||||
|
|
||||||
renderlight->apply_intensity();
|
renderlight->apply_intensity();
|
||||||
|
|||||||
@@ -124,6 +124,8 @@ public:
|
|||||||
Render( world_environment *Environment );
|
Render( world_environment *Environment );
|
||||||
bool
|
bool
|
||||||
Render( TGround *Ground );
|
Render( TGround *Ground );
|
||||||
|
bool
|
||||||
|
Render( TGroundNode *Node );
|
||||||
bool
|
bool
|
||||||
Render( TDynamicObject *Dynamic );
|
Render( TDynamicObject *Dynamic );
|
||||||
bool
|
bool
|
||||||
@@ -134,6 +136,8 @@ public:
|
|||||||
Render( TSubModel *Submodel );
|
Render( TSubModel *Submodel );
|
||||||
void
|
void
|
||||||
Render( TMemCell *Memcell );
|
Render( TMemCell *Memcell );
|
||||||
|
bool
|
||||||
|
Render_Alpha( TGroundNode *Node );
|
||||||
bool
|
bool
|
||||||
Render_Alpha( TDynamicObject *Dynamic );
|
Render_Alpha( TDynamicObject *Dynamic );
|
||||||
bool
|
bool
|
||||||
|
|||||||
Reference in New Issue
Block a user