302 lines
9.5 KiB
C++
302 lines
9.5 KiB
C++
/*
|
|
* Copyright (C) 2014 Open Source Robotics Foundation
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*
|
|
*/
|
|
|
|
#include "gazebo/gui/Conversions.hh"
|
|
#include "gazebo/gui/building/EditorItem.hh"
|
|
#include "gazebo/gui/building/GridLines.hh"
|
|
#include "gazebo/gui/building/MeasureItem.hh"
|
|
#include "gazebo/gui/building/ImportImageDialog.hh"
|
|
#include "gazebo/gui/building/ImportImageDialogPrivate.hh"
|
|
#include "gazebo/gui/building/ImportImageView.hh"
|
|
#include "gazebo/gui/building/ImportImageViewPrivate.hh"
|
|
|
|
using namespace gazebo;
|
|
using namespace gui;
|
|
|
|
/////////////////////////////////////////////////
|
|
ImportImageView::ImportImageView(ImportImageDialog *_parent)
|
|
: QGraphicsView(_parent),
|
|
dataPtr(new ImportImageViewPrivate)
|
|
{
|
|
this->setObjectName("importImageView");
|
|
|
|
this->dataPtr->dialog = _parent;
|
|
|
|
this->dataPtr->drawInProgress = false;
|
|
|
|
this->setTransformationAnchor(QGraphicsView::AnchorUnderMouse);
|
|
this->dataPtr->gridLines = NULL;
|
|
this->dataPtr->imageItem = NULL;
|
|
this->dataPtr->imagePixmap = NULL;
|
|
|
|
this->dataPtr->noImageText = NULL;
|
|
|
|
this->dataPtr->measureItem = NULL;
|
|
this->dataPtr->drawDistanceEnabled = false;
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
ImportImageView::~ImportImageView()
|
|
{
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::SetImage(const std::string &_filename)
|
|
{
|
|
if (this->dataPtr->imageItem)
|
|
this->scene()->removeItem(this->dataPtr->imageItem);
|
|
if (this->dataPtr->gridLines)
|
|
{
|
|
this->scene()->removeItem(this->dataPtr->gridLines);
|
|
this->dataPtr->gridLines = NULL;
|
|
}
|
|
if (this->dataPtr->noImageText)
|
|
{
|
|
this->scene()->removeItem(this->dataPtr->noImageText);
|
|
this->dataPtr->noImageText = NULL;
|
|
}
|
|
if (this->dataPtr->measureItem)
|
|
this->scene()->removeItem(this->dataPtr->measureItem);
|
|
|
|
this->dataPtr->imagePixmap = new QPixmap(QString(_filename.c_str()));
|
|
this->dataPtr->imageWidthPx = this->dataPtr->imagePixmap->width();
|
|
this->dataPtr->imageItem = new QGraphicsPixmapItem(
|
|
this->dataPtr->imagePixmap->scaled(this->scene()->sceneRect().width(),
|
|
this->scene()->sceneRect().height(), Qt::KeepAspectRatio));
|
|
|
|
this->dataPtr->pixmapWidthPx = this->dataPtr->imageItem->pixmap().width();
|
|
this->dataPtr->pixmapHeightPx = this->dataPtr->imageItem->pixmap().height();
|
|
|
|
if (this->dataPtr->imageItem)
|
|
{
|
|
this->scene()->addItem(this->dataPtr->imageItem);
|
|
this->dataPtr->dialog->dataPtr->resolutionSpin->setButtonSymbols(
|
|
QAbstractSpinBox::UpDownArrows);
|
|
this->dataPtr->dialog->dataPtr->resolutionSpin->setReadOnly(false);
|
|
}
|
|
else
|
|
{
|
|
this->scene()->addItem(this->dataPtr->gridLines);
|
|
}
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::resizeEvent(QResizeEvent *_event)
|
|
{
|
|
if (this->scene())
|
|
{
|
|
this->scene()->setSceneRect(0, 0, _event->size().width(),
|
|
_event->size().height());
|
|
|
|
if (!this->dataPtr->imageItem)
|
|
{
|
|
if (!this->dataPtr->gridLines)
|
|
{
|
|
this->dataPtr->gridLines = new GridLines(_event->size().width(),
|
|
_event->size().height());
|
|
this->scene()->addItem(this->dataPtr->gridLines);
|
|
|
|
this->dataPtr->noImageText = new QGraphicsTextItem;
|
|
this->dataPtr->noImageText->setPlainText("No image selected");
|
|
this->dataPtr->noImageText->setDefaultTextColor(Qt::gray);
|
|
this->scene()->addItem(this->dataPtr->noImageText);
|
|
}
|
|
else
|
|
{
|
|
this->dataPtr->gridLines->SetSize(_event->size().width(),
|
|
_event->size().height());
|
|
}
|
|
}
|
|
else
|
|
{
|
|
this->scene()->removeItem(this->dataPtr->imageItem);
|
|
this->dataPtr->imageItem = new QGraphicsPixmapItem(
|
|
this->dataPtr->imagePixmap->scaled(this->scene()->sceneRect().width(),
|
|
this->scene()->sceneRect().height(), Qt::KeepAspectRatio));
|
|
this->scene()->addItem(this->dataPtr->imageItem);
|
|
|
|
if (this->dataPtr->measureItem)
|
|
{
|
|
double scaleWidth = this->dataPtr->imageItem->pixmap().width() /
|
|
static_cast<double>(this->dataPtr->pixmapWidthPx);
|
|
double scaleHeight = this->dataPtr->imageItem->pixmap().height() /
|
|
static_cast<double>(this->dataPtr->pixmapHeightPx);
|
|
|
|
QPointF p1 = this->dataPtr->measureItem->mapToScene(
|
|
this->dataPtr->measureItem->line().p1());
|
|
QPointF p2 = this->dataPtr->measureItem->mapToScene(
|
|
this->dataPtr->measureItem->line().p2());
|
|
|
|
p1.setX(p1.x() * scaleWidth);
|
|
p2.setX(p2.x() * scaleWidth);
|
|
p1.setY(p1.y() * scaleHeight);
|
|
p2.setY(p2.y() * scaleHeight);
|
|
|
|
this->dataPtr->measureItem->SetStartPoint(Conversions::Convert(p1));
|
|
this->dataPtr->measureItem->SetEndPoint(Conversions::Convert(p2));
|
|
}
|
|
}
|
|
|
|
if (this->dataPtr->imageItem)
|
|
{
|
|
this->dataPtr->pixmapWidthPx = this->dataPtr->imageItem->pixmap().width();
|
|
this->dataPtr->pixmapHeightPx =
|
|
this->dataPtr->imageItem->pixmap().height();
|
|
}
|
|
}
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::mouseMoveEvent(QMouseEvent *_event)
|
|
{
|
|
if (this->dataPtr->drawInProgress && this->dataPtr->measureItem)
|
|
{
|
|
QPointF p2 = this->mapToScene(_event->pos());
|
|
|
|
if (!(QApplication::keyboardModifiers() & Qt::ShiftModifier))
|
|
{
|
|
// snap to 0/90/180 degrees
|
|
QPointF p1 = this->dataPtr->measureItem->mapToScene(
|
|
this->dataPtr->measureItem->line().p1());
|
|
QLineF newLine(p1, p2);
|
|
double angle = newLine.angle();
|
|
double range = 10;
|
|
if ((angle < range) || (angle > (360 - range)) ||
|
|
((angle > (180 - range)) && (angle < (180 + range))))
|
|
{
|
|
p2 = QPointF(p2.x(), p1.y());
|
|
}
|
|
else if (((angle > (90 - range)) && (angle < (90 + range))) ||
|
|
((angle > (270 - range)) && (angle < (270 + range))))
|
|
{
|
|
p2 = QPointF(p1.x(), p2.y());
|
|
}
|
|
}
|
|
|
|
this->dataPtr->measureItem->SetEndPoint(Conversions::Convert(p2));
|
|
}
|
|
|
|
if (!this->dataPtr->drawInProgress)
|
|
{
|
|
QGraphicsView::mouseMoveEvent(_event);
|
|
}
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::mousePressEvent(QMouseEvent *_event)
|
|
{
|
|
_event->setAccepted(true);
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::mouseReleaseEvent(QMouseEvent *_event)
|
|
{
|
|
if (this->dataPtr->imageItem)
|
|
{
|
|
this->DrawMeasure(_event->pos());
|
|
}
|
|
|
|
if (!this->dataPtr->drawInProgress)
|
|
{
|
|
this->dataPtr->currentMouseItem = NULL;
|
|
}
|
|
|
|
QGraphicsView::mouseReleaseEvent(_event);
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::keyPressEvent(QKeyEvent *_event)
|
|
{
|
|
if (_event->key() == Qt::Key_Escape)
|
|
{
|
|
this->dataPtr->drawInProgress = false;
|
|
if (this->dataPtr->measureItem)
|
|
{
|
|
this->scene()->removeItem(this->dataPtr->measureItem);
|
|
}
|
|
QApplication::setOverrideCursor(QCursor(Qt::ArrowCursor));
|
|
return;
|
|
}
|
|
_event->ignore();
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::DrawMeasure(const QPoint &_pos)
|
|
{
|
|
if (!this->dataPtr->drawDistanceEnabled)
|
|
return;
|
|
|
|
if (!this->dataPtr->drawInProgress)
|
|
{
|
|
if (this->dataPtr->measureItem)
|
|
{
|
|
this->scene()->removeItem(this->dataPtr->measureItem);
|
|
}
|
|
|
|
QApplication::setOverrideCursor(QCursor(Qt::CrossCursor));
|
|
|
|
auto pointStart = Conversions::Convert(this->mapToScene(_pos));
|
|
auto pointEnd = pointStart + ignition::math::Vector2d(1, 0);
|
|
|
|
this->dataPtr->measureItem = new MeasureItem(pointStart, pointEnd);
|
|
this->dataPtr->measureItem->SetValue(
|
|
this->dataPtr->dialog->dataPtr->distanceSpin->value());
|
|
this->scene()->addItem(this->dataPtr->measureItem);
|
|
this->dataPtr->currentMouseItem = this->dataPtr->measureItem;
|
|
this->dataPtr->drawInProgress = true;
|
|
}
|
|
else
|
|
{
|
|
this->dataPtr->measureItem = dynamic_cast<MeasureItem *>(
|
|
this->dataPtr->currentMouseItem);
|
|
if (this->dataPtr->measureItem)
|
|
{
|
|
this->dataPtr->measureScenePx = this->dataPtr->measureItem->Distance();
|
|
|
|
this->dataPtr->dialog->dataPtr->distanceSpin->setButtonSymbols(
|
|
QAbstractSpinBox::UpDownArrows);
|
|
this->dataPtr->dialog->dataPtr->distanceSpin->setReadOnly(false);
|
|
}
|
|
|
|
// Calculate distance
|
|
double distanceImage = this->dataPtr->measureScenePx *
|
|
this->dataPtr->imageWidthPx / this->dataPtr->pixmapWidthPx;
|
|
this->dataPtr->dialog->dataPtr->resolutionSpin->setValue(
|
|
distanceImage / this->dataPtr->dialog->dataPtr->distanceSpin->value());
|
|
|
|
this->dataPtr->currentMouseItem = NULL;
|
|
this->dataPtr->drawInProgress = false;
|
|
this->releaseKeyboard();
|
|
this->dataPtr->dialog->dataPtr->distanceSpin->setFocus();
|
|
this->dataPtr->dialog->dataPtr->distanceSpin->selectAll();
|
|
QApplication::setOverrideCursor(QCursor(Qt::ArrowCursor));
|
|
}
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::RefreshDistance(double _distance)
|
|
{
|
|
this->dataPtr->measureItem->SetValue(_distance);
|
|
this->scene()->update();
|
|
}
|
|
|
|
/////////////////////////////////////////////////
|
|
void ImportImageView::EnableDrawDistance(bool _enable)
|
|
{
|
|
this->dataPtr->drawDistanceEnabled = _enable;
|
|
}
|