Уроки, алгоритмы, программы, примеры

Материалы по разделам

Построения
на плоскости (2D)
Графика
в пространстве (3D)
Вычислительная
геометрия
Физическое
моделирование
Фрактальная
графика

Новые комментарии

У меня проблема вот с этим: gl.Clear(OpenGL.GL_COLOR_BUFFER_BIT | OpenGL.GL_DEPTH_BUFFER_BIT);. Вылезает ошибка: CS1061 "object" не содержит определения "GL_COLOR_BUFFER_BIT", и не удалось найти доступный метод расширения "GL_COLOR_BUFFER_BIT",...
Большое спасибо. Единственный код который прошел без каких либо ошибок. Ура!!!
Скажите пожалуйста, подскажите алгоритм по которому по заданным точкам можно определить тип многогранника, скажем это куб или прямоугольный параллелепипед. Нашел теорию по этим фигурам: https://www.mat... https://www.mat... Акцентировать внимание...
Всем у кого не работает. файл wizard.script Ещё одно упоминание Glut32 в строке "if (!VerifyLibFile(dir_nomacro_lib, _T("glut32"), _T("GLUT's"))) return false;" меняем на "if (!VerifyLibFile(dir_nomacro_lib, _T("freeglut"), _T("GLUT's"))) return...
Не получается, емаё

Счетчики и рейтинг

Рейтинг@Mail.ru Яндекс.Метрика
Скриншот к примеру
Среда программирования: 
CodeBlocks 13.12
Статья по теме: 

Вход : множество точек, представляющих полигон в порядке обхода вершин в любом направлении.
Результат : определение типа полигона (выпуклый; не выпуклый).

Как использовать.
Набросать левой клавишей мыши (ЛКМ) вершины:
вид до проверки

Нажать правую клавишу мыши(ПКМ), произойдет проверка.
Результат может быть таким:
выпуклый полигон

или таким:
 не выпуклый полигон

Проверка основывается на том факте, что у выпуклого полигона все повороты смежных ребер одного знака.

Код программы: 

// пример работы с векторным произведением
 
#include <SFML/Graphics.hpp>
#include <SFML/Window.hpp>
 
#include <iostream>     // удобно для отладки
 
void handleMouseLeft(sf::VertexArray& pVertex, sf::Vector2i iCurrPos, sf::Text& pText, sf::ConvexShape& polygon);
void handleMouseRight(sf::VertexArray& pVertex, sf::Text& pText, sf::ConvexShape& polygon);
bool isConvexPolygon(const sf::VertexArray& mVertex);
int getSignVertex(sf::Vertex fVertex1, sf::Vertex fVertex2, sf::Vertex fVertex);
 
bool polygonCheked = false;
 
int main()
{
    // без кнопки максимизации
    sf::RenderWindow window(sf::VideoMode(640, 480), "is convex polygon",
                            sf::Style::Close|sf::Style::Titlebar);
 
    // LinesStrip - связывать 2 рядом идущие точки линией
    sf::VertexArray lines(sf::LinesStrip, 0);
 
    sf::ConvexShape polygon;
    polygon.setFillColor(sf::Color::Cyan);
    polygon.setOutlineThickness(2);
    polygon.setOutlineColor(sf::Color::Green);
 
    sf::Font font;
    font.loadFromFile("Sansation.ttf");
 
    // ЛКМ - набрасывание точек;  ПКМ - построение
    sf::Text mText("LKM - nabrasyvaniye tochek;   PKM - postroeniye", font, 20);
    mText.setPosition(5.f, 425.f);
    mText.setColor(sf::Color::Cyan);
 
    // полигон не определен
    sf::Text mTextIs("polygon not defined", font, 20);
    mTextIs.setPosition(5.f, 450.f);
    mTextIs.setColor(sf::Color::Cyan);
 
    while (window.isOpen())     // цикл опроса событий
    {
        sf::Event event;
        while (window.pollEvent(event))
        {
            if (event.type == sf::Event::Closed)
                window.close();
            // ЛКМ
            if ((event.type == sf::Event::MouseButtonPressed) &
                    (sf::Mouse::isButtonPressed(sf::Mouse::Left)) )
                {
                    sf::Vector2i iCurrPos = sf::Mouse::getPosition(window) ;
                    handleMouseLeft(lines, iCurrPos, mTextIs, polygon);
                }
            // ПКМ
            if ((event.type == sf::Event::MouseButtonPressed) &
                    (sf::Mouse::isButtonPressed(sf::Mouse::Right)) )
                handleMouseRight(lines, mTextIs, polygon);
        }
        window.clear();
        window.draw(lines);
        window.draw(polygon);
        window.draw(mText);
        window.draw(mTextIs);
        window.display();
    }
}
 
void handleMouseLeft(sf::VertexArray& pVertex, sf::Vector2i iCurrPos,
                     sf::Text& pText, sf::ConvexShape& polygon)
{
    // если новое ипользование
    if (polygonCheked) {
        pVertex.clear();
        pText.setColor(sf::Color::Cyan);
        pText.setString("polygon not defined");
        polygon.setPointCount(0);
        polygonCheked = false;
    }
    // VertexArray - только float (кроссплатформенность),
    // sf::Mouse::getPosition(window) - pair<int>
    sf::Vector2f fCurrPos(0.0 + iCurrPos.x, 0.0 + iCurrPos.y);
    // sf::VertexArray.append принимает вектор с float значениями; кроссплатформенность
    pVertex.append(fCurrPos);
};
 
void handleMouseRight(sf::VertexArray& lines, sf::Text& pText, sf::ConvexShape& polygon)
{
    polygonCheked = true;
    if (isConvexPolygon(lines) ) {
        pText.setString("convex polygon");
        pText.setColor(sf::Color::Green);
        polygon.setPointCount(lines.getVertexCount());
        sf::Vector2f fVector;
        for (unsigned int i = 0; i < lines.getVertexCount(); i++){
            fVector.x = lines[i].position.x;
            fVector.y = lines[i].position.y;
            polygon.setPoint(i, fVector);
        }
        lines.clear();
    }
    else {
        pText.setColor(sf::Color::Red);
        pText.setString("not convex polygon");
    }
    // добавляем ребро к начальной точке
    lines.append(lines[0]);
};
 
// Вход     : множество вершин в порядке обхода в любом направлении
// Выход    : булево-значение [выпуклый <--> не выпуклый]
bool isConvexPolygon(const sf::VertexArray& pVertex)
{
    bool bRetVal = false;
    int signPrime = 0;
    int iVertexCount = pVertex.getVertexCount();
    // взять первый ненулевой знак, если 0 - вернуть false
    int i = 0;  // vertex 'iterator'
    for ( ; i < iVertexCount; ++i) {
        // getSignVertex(vertex[i], vertex[i+1], vertex[i+2]) ; n+2=2
        // нет оператора присваивания: xxx = pVertex[i] ,
        // выдержка: Vertex &  operator[] (unsigned int index)
        //           sf::Vertex::Vertex  ( const Vector2f &  thePosition )
        signPrime = getSignVertex(  pVertex[i],
                                    pVertex[(i+1)%iVertexCount],
                                    pVertex[(i+2)%iVertexCount]);
        if (signPrime != 0) break;
    } // for
    if (signPrime == 0) return bRetVal;  // линия
    // сравниваем остальные знаки с образцом
    for ( ; i < iVertexCount; ++i) {
        int signNext = getSignVertex(pVertex[i],
                                     pVertex[(i+1)%iVertexCount],
                                     pVertex[(i+2)%iVertexCount]);
        // если знаки разные
        if ( (signNext != signPrime) & (signNext != 0) ) {
            return bRetVal;
        } // if
    }
    bRetVal = true;
    return bRetVal;
};
 
// вычисление знака угла поворота
// возврат -1, 0, 1
int getSignVertex(sf::Vertex fVertex1, sf::Vertex fVertex2, sf::Vertex fVertex3)
{
    // уравнение прямой ab: Ax + By + C = 0;
    //  A = a.y-b.y, B = b.x-a.x, C = -(a.x*A + a.y*B)
    // площадь на основе векторов ab и ac
    float fArea = ( (fVertex2.position.x - fVertex1.position.x)*
                    (fVertex3.position.y - fVertex1.position.y) -
                    (fVertex3.position.x - fVertex1.position.x)*
                    (fVertex2.position.y - fVertex1.position.y) );
    int iRetVal = 0;
    if (fArea == 0) return iRetVal;
    iRetVal  = (fArea > 0) ? 1 : -1;
    return iRetVal;
};

Прикрепленный файлРазмер
isConvex.rar477.16 кб
source_is_convex.rar13.91 кб