JP
Julia PominchukApril 18, 2016, 10:15 a.m.

Построение схем из графических элементов

QGraphicsScene, GridLayout, Qt, scheme

Добрый день!
Прошу, пожалуйста, помочь с таким вопросом.
Создаю программу, которая рассчитывает электрические или комбинационые схемы (точно пока не определилась, но это не особо влияет на суть вопроса). Целью задачи есть сложить эту схему.
Нажимая на кнопку, мы поучаем нужный элемент и перетаскиваем в нужную позицию.
На этом сайте нашла урок о графической сцене и перетаскиванию по ней элементов, он очень помог, но осталось два вопроса:
1) как сделать так, чтобы элемент становился не в произвольную позицию, а как будто разбить поле на прямоугольные участки;
2) приоритетный в решении момент. Как понять, что два элемента стоят рядом, то есть соединены в цепь или что выходы одного элемента подключены ко входам второго.
We recommend hosting TIMEWEB
We recommend hosting TIMEWEB
Stable hosting, on which the social network EVILEG is located. For projects on Django we recommend VDS hosting.

Do you like it? Share on social networks!

2
Evgenii Legotckoi
  • April 18, 2016, 12:41 p.m.
  • The answer was marked as a solution.

Добрый день. Давайте по порядку разберёмся.

1) как сделать так, чтобы элемент становился не в произвольную позицию, а как будто разбить поле на прямоугольные участки;

Я так понимаю, смотрели вот этот урок про перетаскивание графических элементов на графической сцене?

Чтобы все объекты перемещались по строго заданным координатам, то можно урок просто модифицировать следующим образом.

Widget::Widget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::Widget)
{
    ui->setupUi(this);
 
    // Косметическая подготовка приложения
    this->resize(640, 640);          // Устанавливаем размеры окна приложения
    this->setFixedSize(640, 640);
 
    scene = new QGraphicsScene(this);   // Инициализируем графическую сцену
    scene->setItemIndexMethod(QGraphicsScene::NoIndex); // настраиваем индексацию элементов
 
    ui->graphicsView->resize(600, 600);  // Устанавливаем размер graphicsView
    ui->graphicsView->setScene(scene);  // Устанавливаем графическую сцену в graphicsView
    ui->graphicsView->setCacheMode(QGraphicsView::CacheBackground); // Кэш фона
    ui->graphicsView->setViewportUpdateMode(QGraphicsView::BoundingRectViewportUpdate);
 
    scene->setSceneRect(0, 0, 500, 500); // Устанавливаем размер сцены
    
    /// Добавляем этот кусок, чтобы сделать сетку
    for(auto i = 0; i < 21; ++i){
        scene->addLine(i*25, 0, i*25, 500, QPen(Qt::gray));
        scene->addLine(0, i*25, 500, i*25, QPen(Qt::gray));
    }
}
void Widget::on_pushButton_clicked()
{
    MoveItem *item = new MoveItem();        // Создаём графический элемент
    item->setPos(250, 250);  // Делаем строго заданную позици появления квадрата
    scene->addItem(item);   // Добавляем элемент на графическую сцену
}

И модифицируем метод события перемещения мыши в самом классе квадрата

void MoveItem::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
{
    /* Устанавливаем позицию графического элемента
     * в графической сцене, транслировав координаты
     * курсора внутри графического элемента
     * в координатную систему графической сцены
     * */
    QPointF position = event->pos();
    int x = position.x();
    int y = position.y();
 
    x = x % 25;
    y = y % 25;
 
    if(x >= 13){
        x = position.x() - x + 25;
    } else {
        x = position.x() - x;
    }
 
    if(y >= 13){
        y = position.y() - y + 25;
    } else {
        y = position.y() - y;
    }
    this->setPos(mapToScene(QPointF(x, y)));
}

Также я немного уменьшил размеры квадратов для наглядности.

QRectF MoveItem::boundingRect() const
{
    return QRectF (-20, -20, 40, 40);
}
 
void MoveItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget)
{
    painter->setPen(Qt::black);
    painter->setBrush(Qt::green);
    painter->drawRect(-20, -20, 40, 40);
    Q_UNUSED(option);
    Q_UNUSED(widget);
}

После этих изменений объекты будут двигаться с заданным шагом в 25 пикселей.

2) приоритетный в решении момент. Как понять, что два элемента стоят рядом, то есть соединены в цепь или что выходы одного элемента подключены ко входам второго.

А относительно присоединений.. Вам тогда нужно разработать собственный дизайн графических элементов, чтобы ключевые точки были посередине граней условных квадратов, областей QRect, в которых будут лежать Ваши электрические элементы. В данном примере условная область QRect будет занимать 4 клетки.

Тогда останется отслеживать пересечения данных условных точек, как показано в уроке про определение коллизий.

Останется только правильно составить алгоритм из пересекающихся элементов для расчёта. Но это уже довольно большой объём работы. В двух словах сходу не придумаешь. Нужно пораскинуть мозгами.

    JP
    • April 18, 2016, 1:59 p.m.
    Спасибо большое! Вы очень помогли!

      Comments

      Only authorized users can post comments.
      Please, Log in or Sign up
      Дмитрий

      C ++ - Test 004. Pointers, Arrays and Loops

      • Result:60points,
      • Rating points-1
      Дмитрий

      C++ - Тест 003. Условия и циклы

      • Result:92points,
      • Rating points8
      d
      • dsfs
      • April 26, 2024, 4:56 p.m.

      C ++ - Test 004. Pointers, Arrays and Loops

      • Result:80points,
      • Rating points4
      Last comments
      k
      kmssrFeb. 9, 2024, 7:43 a.m.
      Qt Linux - Lesson 001. Autorun Qt application under Linux как сделать автозапуск для флэтпака, который не даёт создавать файлы в ~/.config - вот это вопрос ))
      Qt WinAPI - Lesson 007. Working with ICMP Ping in Qt Без строки #include <QRegularExpressionValidator> в заголовочном файле не работает валидатор.
      EVA
      EVADec. 25, 2023, 11:30 p.m.
      Boost - static linking in CMake project under Windows Ошибка LNK1104 часто возникает, когда компоновщик не может найти или открыть файл библиотеки. В вашем случае, это файл libboost_locale-vc142-mt-gd-x64-1_74.lib из библиотеки Boost для C+…
      J
      JonnyJoDec. 25, 2023, 9:38 p.m.
      Boost - static linking in CMake project under Windows Сделал всё по-как у вас, но выдаёт ошибку [build] LINK : fatal error LNK1104: не удается открыть файл "libboost_locale-vc142-mt-gd-x64-1_74.lib" Хоть убей, не могу понять в чём дел…
      G
      GvozdikDec. 19, 2023, 10:01 a.m.
      Qt/C++ - Lesson 056. Connecting the Boost library in Qt for MinGW and MSVC compilers Для решения твой проблемы добавь в файл .pro строчку "LIBS += -lws2_32" она решит проблему , лично мне помогло.
      Now discuss on the forum
      G
      George13May 7, 2024, 12:27 p.m.
      добавить qlineseries в функции в функции: "GPlotter::addSeries(QString title, QVector &arr)" я вызываю метод setChart(...), я в конструктор передал адрес на QChartView элемент
      BlinCT
      BlinCTMay 5, 2024, 5:46 p.m.
      Написать свой GraphsView Всем привет. В Qt есть давольно старый обьект дял работы с графиками ChartsView и есть в 6.7 новый но очень сырой и со слабым функционалом GraphsView. По этой причине я хочу написать х…
      PS
      Peter SonMay 4, 2024, 5:57 a.m.
      Best Indian Food Restaurant In Cincinnati OH Ready to embark on a gastronomic journey like no other? Join us at App india restaurant and discover why we're renowned as the Best Indian Food Restaurant In Cincinnati OH . Whether y…
      Evgenii Legotckoi
      Evgenii LegotckoiMay 3, 2024, 2:07 a.m.
      Мобильное приложение на C++Qt и бэкенд к нему на Django Rest Framework Добрый день. По моему мнению - да, но то, что будет касаться вызовов к функционалу Андроида, может создать огромные трудности.
      IscanderChe
      IscanderCheApril 30, 2024, 4:22 p.m.
      Во Flask рендер шаблона не передаётся в браузер Доброе утро! Имеется вот такой шаблон: <!doctype html><html> <head> <title>{{ title }}</title> <link rel="stylesheet" href="{{ url_…

      Follow us in social networks