На этих снимках экрана, взятых из моего приложения MFC, показаны строки 2, которые должны быть параллельны.
Линии рисуются с использованием Gdiplus::Graphics::Drawline()
.
Незначительная проблема заключается в том, что пунктирные линии не прямые, а ломаные. Вы замечаете это, но это не имеет большого значения...
Настоящая проблема в том, что это непоследовательно, и линии, нарисованные с помощью Gdiplus::DashStyleSolid
, действительно прямые.
Это ошибка в GDI+? Есть ли обходной путь?
Обновление 1
Я попытался сделать минимальный пример, но я изо всех сил пытаюсь его воспроизвести... Это может иметь какое-то отношение к очень большим значениям координат и небольшой разнице между их координатами. Вот некоторые примерные координаты линии:
Line 1: PointF(2.21866e+006, 1.40198e+006), PointF(2.21732e+006, 1.40111e+006)
Line 2: PointF(2.21866e+006, 1.40198e+006), PointF(2.21732e+006, 1.40112e+006)
Я заметил, что начальные точки идентичны, но это может быть вызвано округлением в выводе отладки...
Обновление 2
Я мог воспроизвести это сейчас: пример приложения был сгенерирован как проект SDI, а класс представления наследует CScrollView (код и снимок экрана ниже). Эффект ломаной линии также связан с толщиной пера. Линия проходит немного по-разному с разной толщиной, но я не нашел значения, которое все время приводит к параллельным линиям.
Винсент Порвик предполагает в комментарии, что это может быть результатом ошибок округления, поскольку Gdiplus::REAL
определяется как float
. Я тоже считаю, что это так...
Есть ли у меня какие-либо другие варианты, кроме как использовать здесь меньшие значения координат?
Код и скриншот
Эти функции были добавлены/изменены (в дополнение к коду инициализации GDI+):
void CgdiplusLinesView::OnDraw(CDC* pDC)
{
CgdiplusLinesDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
if (!pDoc)
return;
pDC->SetBkMode(TRANSPARENT);
using namespace Gdiplus;
Graphics g(pDC->m_hDC);
g.SetSmoothingMode(Gdiplus::SmoothingModeHighQuality);
Pen solidPen(Color(0,0,0), 2.f);
Pen dashedPen(Color(0,0,0), 2.f);
dashedPen.SetDashStyle(DashStyleDash);
g.DrawLine(&dashedPen, PointF(4438749.500000, 2805806.500000), PointF(4434280.500000, 2802106.500000));
g.DrawLine(&solidPen, PointF(4438746.500000, 2805809.500000), PointF(4434277.500000, 2802109.500000));
}
void CgdiplusLinesView::OnPrepareDC(CDC* pDC, CPrintInfo* pInfo)
{
pDC->SetMapMode(MM_ISOTROPIC);
const int mapSizePixels = 8388608;
pDC->SetWindowExt(mapSizePixels, mapSizePixels);
pDC->SetViewportExt(mapSizePixels, mapSizePixels);
pDC->SetWindowOrg(GetScrollPos(SB_HORZ), GetScrollPos(SB_VERT));
//__super::OnPrepareDC(pDC, pInfo);
}
void CgdiplusLinesView::OnInitialUpdate()
{
CScrollView::OnInitialUpdate();
SetScrollSizes(MM_TEXT, CSize(8388608, 8388608), CSize(1361, 1054));
SetScrollPos(SB_HORZ, 4434897.5);
SetScrollPos(SB_VERT, 2802645.);
}