There are three coordinate systems that are important to SpatialDataView:
The screen coordinate system is made up of Qt coordinates which is based on the location relative to the view widget. The place of origin for the screen coordinates is in the upper-left corner.
Screen coordinate system
World coordinate system
Each of these layers has a separate data coordinate system.
The View::translateWorldToScreen() function converts a world coordinate to a screen coordinate while the View::translateScreenToWorld() function will do the opposite. When using the View::translateScreenToWorld() function, make sure that the screen y-coordinate parameter is correct or it may return a bad result. To get the correct screen y-coordinate, subtract the mouse y-coordinate from the view height.
Here's an example on getting the correct y-coordinate:
dScreenY = pViewWidget.height() - pMouseEvent.pos().y()
Please note that each layer may have different data coordinates so if you convert a world/screen coordinate to a data coordinate in two different layers, we can expect it will have two different values.
The following example shows how to translate from a screen coordinate to a data coordinate:
bool CustomWidget::eventfilter(QObject* pObj, QEvent* pEvent) { SpatialDataView* pView = dynamic_cast<SpatialDataView*>(pObj); if (pEvent->type() == QEvent::MouseButtonPress) { QMouseEvent* pMouseEvent = static_cast<QMouseEvent*>(pEvent); const QPoint& ptMouse = pMouseEvent->pos(); LayerList* pLayerList = pView->getLayerList(); if (pLayerList != NULL) { RasterElement* pRaster = pLayerList->getPrimaryRasterElement(); if (pRaster != NULL) { const RasterDataDescriptor* pDescriptor = dynamic_cast<const RasterDataDescriptor*>(pRaster->getDataDescriptor()); if (pDescriptor != NULL) { RasterLayer* pRasterLayer = dynamic_cast<RasterLayer*>(pLayerList->getLayer(RASTER, pRaster)); if (pRasterLayer != NULL) { LocationType dataCoord; pRasterLayer->translateScreenToData(ptMouse.x(), pView->getWidget()->height() - ptMouse.y(), dataCoord.mX, dataCoord.mY); if (dataCoord.mY >= 0 && dataCoord.mY < pDescriptor->getRows().size() && dataCoord.mX >= 0 && dataCoord.mX < pDescriptor->getColumns().size()) { ComplexComponent eComponent = pRasterLayer->getComplexComponent(); double dValue = pRaster->getPixelValue(pDescriptor->getActiveColumn(dataCoord.mX), pDescriptor->getActiveRow(dataCoord.mY), pDescriptor->getActiveBand(0), eComponent); QMessageBox::information(pView->getWidget(), "Display Pixel Value", "The pixel value is " + QString::number(dValue)); } } } } } } return QObject::eventFilter(pObject, pEvent); }
Other functions that might be helpful to data coordinates as well as other coordinates systems are View::getPixelSize() and PerspectiveView::getPixelAspect(). The View::getPixelSize() function returns the number of screen pixels between two world coordinates and the PerspectiveView::getPixelAspect() gets the view ratio of x compared to y. Since the x pixel ratio between two coordinates can be incorrect in a SpatialDataView, we'll calculate the correct x ratio by multiplying the world x coordinates by the aspect ratio of the pixel.
Here's an example on how these functions might work:
double pixelSize = pPerspectiveView->getPixelSize(llCorner, urCorner); double pixelSizeX = pixelSize * pPerspectiveView->getPixelAspect(); double pixelSizeY = pixelSize;