mirror of
https://github.com/ultimatepp/ultimatepp.git
synced 2026-05-16 14:16:09 -06:00
260 lines
5 KiB
C++
260 lines
5 KiB
C++
#include "MapLevel.h"
|
|
|
|
MapLevel& MapLevel::PagePos(const Point& p)
|
|
{
|
|
Size rsz = GetRenderSize();
|
|
Size psz = GetPageSize();
|
|
|
|
if ( psz.cx < rsz.cx )
|
|
{
|
|
if (p.x < 0)
|
|
_pagePos.x = 0;
|
|
else if (p.x >= rsz.cx - psz.cx)
|
|
_pagePos.x = rsz.cx - psz.cx - 1;
|
|
else
|
|
_pagePos.x = p.x;
|
|
}
|
|
else
|
|
{
|
|
_pagePos.x = 0;
|
|
}
|
|
|
|
if ( psz.cy < rsz.cy )
|
|
{
|
|
if (p.y < 0)
|
|
_pagePos.y = 0;
|
|
else if (p.y >= rsz.cy - psz.cy)
|
|
_pagePos.y = rsz.cy - psz.cy - 1;
|
|
else
|
|
_pagePos.y = p.y;
|
|
}
|
|
else
|
|
{
|
|
_pagePos.y = 0;
|
|
}
|
|
|
|
return *this;
|
|
}
|
|
|
|
MapLevel& MapLevel::MoveTo(const Point& p)
|
|
{
|
|
PagePos(p);
|
|
UpdateMap();
|
|
return *this;
|
|
}
|
|
|
|
MapLevel& MapLevel::MoveBy(const Point& p)
|
|
{
|
|
PagePos(GetPagePos() + p);
|
|
UpdateMap();
|
|
return *this;
|
|
}
|
|
|
|
Point MapLevel::PointZoomIn()
|
|
{
|
|
if (!_zoomLevels.GetCount())
|
|
return Point(0, 0);
|
|
|
|
int newZoom = _zoomLevel + 1;
|
|
if (newZoom >= _zoomLevels.GetCount())
|
|
return Point(0, 0);
|
|
|
|
_zoomLevel = newZoom;
|
|
|
|
// before
|
|
Point s = GetPagePos();
|
|
Size ss = GetSize();
|
|
|
|
// after
|
|
double x = (double)s.x * _zoomLevels[_zoomLevel].GetZoom();
|
|
double y = (double)s.y * _zoomLevels[_zoomLevel].GetZoom();
|
|
|
|
double cx = (double)ss.cx * _zoomLevels[_zoomLevel].GetZoom();
|
|
double cy = (double)ss.cy * _zoomLevels[_zoomLevel].GetZoom();
|
|
|
|
// calculating new pos
|
|
x -= (ss.cx - cx) / 2;
|
|
y -= (ss.cy - cy) / 2;
|
|
Point pos = Point((int)x, (int)y);
|
|
|
|
return pos;
|
|
}
|
|
|
|
Point MapLevel::PointZoomOut()
|
|
{
|
|
if (!_zoomLevels.GetCount())
|
|
return Point(0, 0);
|
|
|
|
int newZoom = _zoomLevel - 1;
|
|
if (newZoom < 0)
|
|
return Point(0, 0);
|
|
|
|
_zoomLevel = newZoom;
|
|
|
|
// before
|
|
Point s = GetPagePos();
|
|
Size ss = GetPageSize();
|
|
|
|
// after
|
|
double x = (double)s.x / _zoomLevels[_zoomLevel].GetZoom();
|
|
double y = (double)s.y / _zoomLevels[_zoomLevel].GetZoom();
|
|
|
|
double cx = (double)ss.cx / _zoomLevels[_zoomLevel].GetZoom();
|
|
double cy = (double)ss.cy / _zoomLevels[_zoomLevel].GetZoom();
|
|
|
|
// calculating new pos
|
|
x -= (ss.cx - cx) / 2;
|
|
y -= (ss.cy - cy) / 2;
|
|
Point pos = Point((int)x, (int)y);
|
|
|
|
return pos;
|
|
}
|
|
|
|
MapLevel& MapLevel::ZoomTo(int zoom)
|
|
{
|
|
if (zoom == _zoomLevel)
|
|
return *this;
|
|
|
|
Point pos = Point(0, 0);
|
|
|
|
if (zoom > _zoomLevel)
|
|
{
|
|
for (int i = _zoomLevel; i < zoom; ++i)
|
|
pos = PointZoomIn();
|
|
}
|
|
|
|
if (zoom < _zoomLevel)
|
|
{
|
|
for (int i = _zoomLevel; i > zoom; --i)
|
|
pos = PointZoomOut();
|
|
}
|
|
|
|
Zoom(_zoomLevel);
|
|
MoveTo(pos);
|
|
|
|
return *this;
|
|
}
|
|
|
|
MapLevel& MapLevel::ZoomIn()
|
|
{
|
|
Point pos = PointZoomIn();
|
|
Zoom(_zoomLevel);
|
|
MoveTo(pos);
|
|
return *this;
|
|
}
|
|
|
|
MapLevel& MapLevel::ZoomOut()
|
|
{
|
|
Point pos = PointZoomOut();
|
|
Zoom(_zoomLevel);
|
|
MoveTo(pos);
|
|
return *this;
|
|
}
|
|
|
|
Point MapLevel::SceneToView(const Point& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return p;
|
|
|
|
Point res = p - GetPageOffset() + GetPagePos();
|
|
for (int i = GetCurrentZoom() + 1; i < GetZoomCount(); ++i)
|
|
res = Point((double)res.x * GetZoom(i), (double)res.y * GetZoom(i));
|
|
|
|
return res;
|
|
}
|
|
|
|
Point MapLevel::ViewToScene(const Point& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return p;
|
|
|
|
Point res = p;
|
|
for (int i = GetZoomCount() - 1; i > GetCurrentZoom(); --i)
|
|
res = Point((double)res.x / GetZoom(i), (double)res.y / GetZoom(i));
|
|
|
|
return res + GetPageOffset() - GetPagePos();
|
|
}
|
|
|
|
Size MapLevel::SceneToView(const Size& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return p;
|
|
|
|
Size res = p;
|
|
for (int i = GetCurrentZoom() + 1; i < GetZoomCount(); ++i)
|
|
res = Size((double)res.cx * GetZoom(i), (double)res.cy * GetZoom(i));
|
|
|
|
return res;
|
|
}
|
|
|
|
Size MapLevel::ViewToScene(const Size& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return p;
|
|
|
|
Size res = p;
|
|
for (int i = GetZoomCount() - 1; i > GetCurrentZoom(); --i)
|
|
res = Size((double)res.cx / GetZoom(i), (double)res.cx / GetZoom(i));
|
|
|
|
return res;
|
|
}
|
|
|
|
Rect MapLevel::SceneToView(const Rect& rt)
|
|
{
|
|
return GetZoomCount() > 0 ? Rect(SceneToView(rt.TopLeft()), SceneToView(rt.GetSize())) : rt;
|
|
}
|
|
|
|
Rect MapLevel::ViewToScene(const Rect& rt)
|
|
{
|
|
return GetZoomCount() > 0 ? Rect(ViewToScene(rt.TopLeft()), ViewToScene(rt.GetSize())) : rt;
|
|
}
|
|
|
|
Array<Point> MapLevel::SceneToView(const Array<Point>& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return clone(p);
|
|
Array<Point> res;
|
|
for (int i = 0; i < p.GetCount(); ++i)
|
|
res << SceneToView(p[i]);
|
|
return res;
|
|
}
|
|
|
|
Array<Point> MapLevel::ViewToScene(const Array<Point>& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return p;
|
|
Array<Point> res;
|
|
for (int i = 0; i < p.GetCount(); ++i)
|
|
res << ViewToScene(p[i]);
|
|
return res;
|
|
}
|
|
|
|
Vector<Point> MapLevel::SceneToView(const Vector<Point>& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return clone(p);
|
|
Vector<Point> res;
|
|
for (int i = 0; i < p.GetCount(); ++i)
|
|
res << SceneToView(p[i]);
|
|
return res;
|
|
}
|
|
|
|
Vector<Point> MapLevel::ViewToScene(const Vector<Point>& p)
|
|
{
|
|
if (!GetZoomCount())
|
|
return clone(p);
|
|
Vector<Point> res;
|
|
for (int i = 0; i < p.GetCount(); ++i)
|
|
res << ViewToScene(p[i]);
|
|
return res;
|
|
}
|
|
|
|
Rect MapLevel::CurrentViewRect()
|
|
{
|
|
return SceneToView(CurrentSceneRect());
|
|
}
|
|
|
|
Rect MapLevel::CurrentSceneRect()
|
|
{
|
|
return GetPageRect() - GetPagePos();
|
|
}
|