Пример #1
0
void CatapultStone::Draw(const GameWorldView& gwv, const int xoffset, const int yoffset)
{
    // Stein überhaupt zeichnen (wenn Quelle und Ziel nicht sichtbar sind, dann nicht!)
    if(gwv.GetGameWorldViewer()->GetVisibility(dest_building) != VIS_VISIBLE &&
            gwv.GetGameWorldViewer()->GetVisibility(dest_map) != VIS_VISIBLE)
        return;

    int world_width = gwg->GetWidth() * TR_W;
    int world_height = gwg->GetHeight() * TR_H;

    if(explode)
    {
        // Stein explodierend am Ziel zeichnen
        LOADER.GetMapImageN(3102 + GAMECLIENT.Interpolate(4, event))->
        Draw((dest_x - xoffset + world_width) % world_width, (dest_y - yoffset + world_height) % world_height);
    }
    else
    {
        // Linear interpolieren zwischen Ausgangs- und Zielpunkt
        int x = GAMECLIENT.Interpolate(start_x, dest_x, event);
        int y = GAMECLIENT.Interpolate(start_y, dest_y, event);

        int whole = int(std::sqrt(double((dest_x - start_x) * (dest_x - start_x) + (dest_y - start_y) * (dest_y - start_y))));
        int s = GAMECLIENT.Interpolate(whole , event);


        double dx = double(s) / double(whole)  - 0.5;

        // Y-Verschiebung ausrechnen, damit die Nullpunkte beim Start- und Endpunkt liegen
        double y_diff = 0.5 * 0.5;

        // Verschiebung ausrechnen von Y
        int diff = int((dx * dx - y_diff) * 200);

        // Schatten auf linearer Linie zeichnen
        LOADER.GetMapImageN(3101)->Draw((x - xoffset + world_width) % world_width, (y - yoffset + world_height) % world_height, 0, 0, 0, 0, 0, 0, COLOR_SHADOW);
        // Stein auf Parabel zeichnen
        LOADER.GetMapImageN(3100)->Draw((x - xoffset + world_width) % world_width, (y - yoffset + world_height + diff) % world_height);
    }
}
Пример #2
0
void TerrainRenderer::PrepareWaysPoint(PreparedRoads& sorted_roads, const GameWorldView& gwv, MapPoint t, const PointI& offset)
{
    PointI startPos = PointI(GetTerrain(t)) - gwv.GetOffset() + offset;

    GameWorldViewer& gwViewer = gwv.GetGameWorldViewer();
    Visibility visibility = gwViewer.GetVisibility(t);

	int totalWidth  = gwViewer.GetWidth()  * TR_W;
	int totalHeight = gwViewer.GetHeight() * TR_H;

    // Wegtypen für die drei Richtungen
    for(unsigned dir = 0; dir < 3; ++dir)
    {
        unsigned char type = gwViewer.GetVisibleRoad(t, dir, visibility);
        if (!type)
            continue;
        MapPoint ta = gwViewer.GetNeighbour(t, 3 + dir);

        PointI endPos = PointI(GetTerrain(ta)) - gwv.GetOffset() + offset;
        PointI diff = startPos - endPos;

        // Gehen wir über einen Kartenrand (horizontale Richung?)
        if(std::abs(diff.x) >= totalWidth / 2)
        {
            if(std::abs(endPos.x - totalWidth - startPos.x) < std::abs(diff.x))
                endPos.x -= totalWidth;
            else
                endPos.x += totalWidth;
        }
        // Und dasselbe für vertikale Richtung
        if(std::abs(diff.y) >= totalHeight / 2)
        {
            if(std::abs(endPos.y - totalHeight - startPos.y) < std::abs(diff.y))
                endPos.y -= totalHeight;
            else
                endPos.y += totalHeight;
        }

        --type;

        // Wegtypen "konvertieren"
        switch(type)
        {
            case RoadSegment::RT_DONKEY:
            case RoadSegment::RT_NORMAL:
            {
                TerrainType t1 = gwViewer.GetTerrainAround(t, dir + 2);
                TerrainType t2 = gwViewer.GetTerrainAround(t, dir + 3);

                // Prüfen, ob Bergwege gezeichnet werden müssen, indem man guckt, ob der Weg einen
                // Berg "streift" oder auch eine Bergwiese
                if(TerrainData::IsMountain(t1) || TerrainData::IsMountain(t2))
                    type = 3;

                break;
            }
            case RoadSegment::RT_BOAT:
                type = 2;
                break;
        }

        sorted_roads[type].push_back(
            PreparedRoad(type, startPos, endPos, GetColor(t), GetColor(ta), dir)
        );
    }
}
Пример #3
0
/**
 *  zeichnet den Kartenausschnitt.
 *
 *  @author OLiver
 *  @author FloSoft
 */
void TerrainRenderer::Draw(const GameWorldView& gwv, unsigned int* water)
{
    assert(!gl_vertices.empty());
    assert(!borders.empty());

    /*  if ((gwv.GetXOffset() == gwv.terrain_last_xoffset) && (gwv.GetYOffset() == gwv.terrain_last_yoffset) && (gwv.terrain_list != 0) && (GAMECLIENT.GetGlobalAnimation(4, 5, 4, 0) == gwv.terrain_last_global_animation))
        {
            glCallList(gwv.terrain_list);
            *water = gwv.terrain_last_water;
            return;
        }

        gwv.terrain_last_xoffset = gwv.GetXOffset();
        gwv.terrain_last_yoffset = gwv.GetYOffset();
        gwv.terrain_last_global_animation = GAMECLIENT.GetGlobalAnimation(4, 5, 4, 0);

        if (gwv.terrain_list == 0)
            gwv.terrain_list = glGenLists(1);

        glNewList(gwv.terrain_list, GL_COMPILE_AND_EXECUTE);*/

    // nach Texture in Listen sortieren
    boost::array< std::vector<MapTile>, TT_COUNT> sorted_textures;
    boost::array< std::vector<BorderTile>, 5> sorted_borders;
    PreparedRoads sorted_roads;

    Point<int> lastOffset(0, 0);
 
    // Beim zeichnen immer nur beginnen, wo man auch was sieht
    for(int y = gwv.GetFirstPt().y; y < gwv.GetLastPt().y; ++y)
    {
        unsigned char lastTerrain = 255;
        unsigned char lastBorder  = 255;

        for(int x = gwv.GetFirstPt().x; x < gwv.GetLastPt().x; ++x)
        {
            Point<int> posOffset;
            MapPoint tP = ConvertCoords(Point<int>(x, y), &posOffset);

            TerrainType t = gwv.GetGameWorldViewer().GetNode(tP).t1;
            if(posOffset != lastOffset)
                lastTerrain = 255;

            if(t == lastTerrain && tP != MapPoint(0, 0))
                ++sorted_textures[t].back().count;
            else
            {
                MapTile tmp(GetTriangleIdx(tP), posOffset);
                sorted_textures[t].push_back(tmp);
                lastTerrain = t;
            }

            t = gwv.GetGameWorldViewer().GetNode(tP).t2;

            if(t == lastTerrain)
                ++sorted_textures[t].back().count;
            else
            {
                MapTile tmp(GetTriangleIdx(tP) + 1, posOffset);
                sorted_textures[t].push_back(tmp);
            }

            lastTerrain = t;

            const Borders& curBorders = borders[GetVertexIdx(tP)];
            boost::array<unsigned char, 6> tiles =
            {{
                curBorders.left_right[0],
                curBorders.left_right[1],
                curBorders.right_left[0],
                curBorders.right_left[1],
                curBorders.top_down[0],
                curBorders.top_down[1]
            }};

            // Offsets into gl_* arrays
            boost::array<unsigned, 6> offsets = 
            {{
                curBorders.left_right_offset[0],
                curBorders.left_right_offset[1],
                curBorders.right_left_offset[0],
                curBorders.right_left_offset[1],
                curBorders.top_down_offset[0],
                curBorders.top_down_offset[1]
            }};

            for(unsigned char i = 0; i < 6; ++i)
            {
                if(!tiles[i])
                    continue;
                if(tiles[i] == lastBorder)
                {
                    BorderTile& curTile = sorted_borders[lastBorder - 1].back();
                    // Check that we did not wrap around the map and the expected offset matches
                    if(curTile.tileOffset + curTile.count == offsets[i])
                    {
                        ++curTile.count;
                        continue;
                    }
                }
                lastBorder = tiles[i];
                BorderTile tmp(offsets[i], posOffset);
                sorted_borders[lastBorder - 1].push_back(tmp);
            }

            PrepareWaysPoint(sorted_roads, gwv, tP, posOffset);

            lastOffset = posOffset;
        }
    }

    if (water)
    {
        unsigned water_count = 0;

        for(unsigned char t = 0; t < TT_COUNT; ++t){
            if(!TerrainData::IsWater(TerrainType(t)))
                continue;
            for(std::vector<MapTile>::iterator it = sorted_textures[t].begin(); it != sorted_textures[t].end(); ++it)
            {
                water_count += it->count;
            }
        }

        PointI diff = gwv.GetLastPt() - gwv.GetFirstPt();
        if( diff.x && diff.y )
            *water = 50 * water_count / ( diff.x * diff.y );
        else
            *water = 0;
    }

    lastOffset = PointI(0, 0);

    if(vboBuffersUsed)
    {
        glBindBufferARB(GL_ARRAY_BUFFER_ARB, vbo_vertices);
        glVertexPointer(2, GL_FLOAT, 0, NULL);

        glBindBufferARB(GL_ARRAY_BUFFER_ARB, vbo_texcoords);
        glTexCoordPointer(2, GL_FLOAT, 0, NULL);

        glBindBufferARB(GL_ARRAY_BUFFER_ARB, vbo_colors);
        glColorPointer(3, GL_FLOAT, 0, NULL);
    }
    else
    {
        glVertexPointer(2, GL_FLOAT, 0, &gl_vertices.front());
        glTexCoordPointer(2, GL_FLOAT, 0, &gl_texcoords.front());
        glColorPointer(3, GL_FLOAT, 0, &gl_colors.front());
    }

    // Arrays aktivieren
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
    glEnableClientState(GL_COLOR_ARRAY);

    // Modulate2x
    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT);
    glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 2.0f);

    // Verschieben gem#ß x und y offset
    glTranslatef( float(-gwv.GetXOffset()), float(-gwv.GetYOffset()), 0.0f);

    // Alphablending aus
    glDisable(GL_BLEND);

    for(unsigned char t = 0; t < TT_COUNT; ++t)
    {
        if(sorted_textures[t].empty())
            continue;
        unsigned animationFrame;
        TerrainType tt = TerrainType(t);
        if(TerrainData::IsLava(tt))
            animationFrame = GAMECLIENT.GetGlobalAnimation(TerrainData::GetFrameCount(tt), 5, 4, 0);
        else if(TerrainData::IsWater(tt))
            animationFrame = GAMECLIENT.GetGlobalAnimation(TerrainData::GetFrameCount(tt), 5, 2, 0);
        else
            animationFrame = 0;

        VIDEODRIVER.BindTexture(LOADER.GetTerrainTexture(tt, animationFrame).GetTexture());

        for(std::vector<MapTile>::iterator it = sorted_textures[t].begin(); it != sorted_textures[t].end(); ++it)
        {
            if(it->posOffset != lastOffset)
            {
                PointI trans = it->posOffset - lastOffset;
                glTranslatef( float(trans.x), float(trans.y), 0.0f);
                lastOffset = it->posOffset;
            }

            assert(it->tileOffset + it->count <= width * height * 2u);
            glDrawArrays(GL_TRIANGLES, it->tileOffset * 3, it->count * 3); // Arguments are in Elements. 1 triangle has 3 values
        }
    }

    glEnable(GL_BLEND);

    glLoadIdentity();
    glTranslatef( float(-gwv.GetXOffset()), float(-gwv.GetYOffset()), 0.0f);

    lastOffset = PointI(0, 0);
    for(unsigned short i = 0; i < 5; ++i)
    {
        if(sorted_borders[i].empty())
            continue;
        VIDEODRIVER.BindTexture(GetImage(borders, i)->GetTexture());

        for(std::vector<BorderTile>::iterator it = sorted_borders[i].begin(); it != sorted_borders[i].end(); ++it)
        {
            if(it->posOffset != lastOffset)
            {
                PointI trans = it->posOffset - lastOffset;
                glTranslatef( float(trans.x), float(trans.y), 0.0f);
                lastOffset = it->posOffset;
            }
            assert(it->tileOffset + it->count <= gl_vertices.size());
            glDrawArrays(GL_TRIANGLES, it->tileOffset * 3, it->count * 3); // Arguments are in Elements. 1 triangle has 3 values
        }
    }
    glLoadIdentity();

    DrawWays(sorted_roads);

    // Wieder zurück ins normale modulate
    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
}