Initial commit: OtozaiPrinter (AveryDennisonUtil) ラベル/レシート レイアウト設計・印刷 MFC アプリ

- 用紙設計キャンバス(1/100mm 基準)・テキスト/画像/矩形/直線アイテム
- コピー/複製/Zオーダー/整列/グリッドスナップ、原紙(下絵)読込と印刷可否
- GDI 直接印刷、.otz 保存/再読込(版数つき)
- MFC/CRT 静的リンクで VS2022 IDE から F5 デバッグ可
This commit is contained in:
yoshikazu
2026-06-05 17:27:29 +09:00
commit 19d1c39370
33 changed files with 3049 additions and 0 deletions
+101
View File
@@ -0,0 +1,101 @@
// RenderScene.cpp
#include "pch.h"
#include "RenderScene.h"
#include "LabelLayout.h"
#include "PrintItem.h"
#include "ImageItem.h"
#pragma comment(lib, "msimg32.lib") // CDC::AlphaBlend(原紙の薄表示)
// レイアウト1枚分を dc に描画する。画面エディタと印刷の共通描画パス。
// 描画順は 用紙白地(画面のみ)→ 原紙 → グリッド/余白ガイド(画面のみ)→ 各アイテム。
// screen=true : 画面用。用紙の白地・グリッド・余白ガイド・選択枠を描く。原紙は薄く表示。
// screen=false: 印刷用。原紙は m_printTemplate のときだけ・等倍・薄表示なしで描く。
// map がDPI/ズーム/原点を吸収するので、同じコードで解像度差を正しく出力できる。
void Render::DrawLayout(CDC& dc, const CLabelLayout& layout, const CoordMap& map,
bool screen, const CPrintItem* selected, int gridHu)
{
CRect paper(0, 0, layout.m_paperWidthHu, layout.m_paperHeightHu);
CRect paperDev = map.MmToDev(paper);
if (screen)
{
CBrush white(RGB(255, 255, 255));
dc.FillRect(paperDev, &white);
}
// 原紙(背景下絵): 全アイテムの背面。画面では常に・印刷は許可時のみ。
CImageItem* tpl = layout.Template();
if (tpl && (screen || layout.m_printTemplate))
{
tpl->SetRect(paper); // 常に用紙全体へ
tpl->Draw(dc, map, /*selected=*/false);
if (screen && paperDev.Width() > 0 && paperDev.Height() > 0)
{
// 画面では原紙を薄く被せ、上に載るアイテムを見やすくする
CDC tmp;
tmp.CreateCompatibleDC(&dc);
CBitmap wb;
wb.CreateCompatibleBitmap(&dc, 1, 1);
CBitmap* pOldB = tmp.SelectObject(&wb);
tmp.SetPixelV(0, 0, RGB(255, 255, 255));
BLENDFUNCTION bf = { AC_SRC_OVER, 0, 110, 0 }; // 白を約43%重ねる
dc.AlphaBlend(paperDev.left, paperDev.top, paperDev.Width(), paperDev.Height(),
&tmp, 0, 0, 1, 1, bf);
tmp.SelectObject(pOldB);
}
}
if (screen)
{
// グリッド(アイテムの下・用紙内)。デバイス間隔が細かすぎる時は描かない。
if (gridHu > 0 && map.LenToDevX(gridHu) >= 5)
{
CPen grid(PS_SOLID, 1, RGB(225, 225, 225));
CPen* pOldG = dc.SelectObject(&grid);
for (int x = gridHu; x < layout.m_paperWidthHu; x += gridHu)
{
int dx = map.MmToDevX(x);
dc.MoveTo(dx, paperDev.top);
dc.LineTo(dx, paperDev.bottom);
}
for (int y = gridHu; y < layout.m_paperHeightHu; y += gridHu)
{
int dy = map.MmToDevY(y);
dc.MoveTo(paperDev.left, dy);
dc.LineTo(paperDev.right, dy);
}
dc.SelectObject(pOldG);
}
// 余白ガイド(破線)
if (layout.m_marginHu > 0)
{
CRect mdev = map.MmToDev(layout.ContentRect());
int oldBk = dc.SetBkMode(TRANSPARENT);
CPen mpen(PS_DOT, 1, RGB(150, 150, 200));
CPen* pOldM = dc.SelectObject(&mpen);
CBrush* pOldMB = (CBrush*)dc.SelectStockObject(NULL_BRUSH);
dc.Rectangle(mdev);
dc.SelectObject(pOldMB);
dc.SelectObject(pOldM);
dc.SetBkMode(oldBk);
}
CPen edge(PS_SOLID, 1, RGB(120, 120, 120));
CPen* pOld = dc.SelectObject(&edge);
CBrush* pOldBrush = (CBrush*)dc.SelectStockObject(NULL_BRUSH);
dc.Rectangle(paperDev);
dc.SelectObject(pOldBrush);
dc.SelectObject(pOld);
}
for (int i = 0; i < layout.GetItemCount(); ++i)
{
CPrintItem* p = layout.GetItem(i);
bool sel = screen && (p == selected);
p->Draw(dc, map, sel);
}
}