diff src/win32/GBPrinterDlg.cpp @ 1:f9f4f1b99eed

importing src directory
author Robert McIntyre <rlm@mit.edu>
date Sat, 03 Mar 2012 10:31:27 -0600
parents
children
line wrap: on
line diff
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/src/win32/GBPrinterDlg.cpp	Sat Mar 03 10:31:27 2012 -0600
     1.3 @@ -0,0 +1,485 @@
     1.4 +// GBPrinter.cpp : implementation file
     1.5 +//
     1.6 +
     1.7 +#include "stdafx.h"
     1.8 +#include "resource.h"
     1.9 +#include "GBPrinterDlg.h"
    1.10 +#include "FileDlg.h"
    1.11 +#include "Reg.h"
    1.12 +#include "WinResUtil.h"
    1.13 +#include "VBA.h"
    1.14 +
    1.15 +//#include "../common/System.h"
    1.16 +#include "../NLS.h"
    1.17 +#include "../common/Util.h"
    1.18 +
    1.19 +extern "C" {
    1.20 +#include <png.h>
    1.21 +}
    1.22 +
    1.23 +/////////////////////////////////////////////////////////////////////////////
    1.24 +// GBPrinter dialog
    1.25 +
    1.26 +GBPrinterDlg::GBPrinterDlg(CWnd*pParent /*=NULL*/)
    1.27 +	: CDialog(GBPrinterDlg::IDD, pParent)
    1.28 +{
    1.29 +	//{{AFX_DATA_INIT(GBPrinterDlg)
    1.30 +	m_scale = -1;
    1.31 +	//}}AFX_DATA_INIT
    1.32 +	bitmap = (BITMAPINFO *)bitmapHeader;
    1.33 +
    1.34 +	bitmap->bmiHeader.biSize            = sizeof(BITMAPINFOHEADER);
    1.35 +	bitmap->bmiHeader.biWidth           = 160;
    1.36 +	bitmap->bmiHeader.biHeight          = -144;
    1.37 +	bitmap->bmiHeader.biPlanes          = 1;
    1.38 +	bitmap->bmiHeader.biBitCount        = 8;
    1.39 +	bitmap->bmiHeader.biCompression     = BI_RGB;
    1.40 +	bitmap->bmiHeader.biSizeImage       = 160*144;
    1.41 +	bitmap->bmiHeader.biXPelsPerMeter   = 0;
    1.42 +	bitmap->bmiHeader.biYPelsPerMeter   = 0;
    1.43 +	bitmap->bmiHeader.biClrUsed         = 4;
    1.44 +	bitmap->bmiHeader.biClrImportant    = 4;
    1.45 +	bitmap->bmiColors[0].rgbBlue        =
    1.46 +	    bitmap->bmiColors[0].rgbGreen   =
    1.47 +	        bitmap->bmiColors[0].rgbRed =
    1.48 +	            255;
    1.49 +	bitmap->bmiColors[0].rgbReserved    = 0;
    1.50 +	bitmap->bmiColors[1].rgbBlue        =
    1.51 +	    bitmap->bmiColors[1].rgbGreen   =
    1.52 +	        bitmap->bmiColors[1].rgbRed =
    1.53 +	            168;
    1.54 +	bitmap->bmiColors[1].rgbReserved    = 0;
    1.55 +	bitmap->bmiColors[2].rgbBlue        =
    1.56 +	    bitmap->bmiColors[2].rgbGreen   =
    1.57 +	        bitmap->bmiColors[2].rgbRed =
    1.58 +	            96;
    1.59 +	bitmap->bmiColors[2].rgbReserved    = 0;
    1.60 +	bitmap->bmiColors[3].rgbBlue        =
    1.61 +	    bitmap->bmiColors[3].rgbGreen   =
    1.62 +	        bitmap->bmiColors[3].rgbRed =
    1.63 +	            0;
    1.64 +	bitmap->bmiColors[3].rgbReserved = 0;
    1.65 +}
    1.66 +
    1.67 +void GBPrinterDlg::DoDataExchange(CDataExchange*pDX)
    1.68 +{
    1.69 +	CDialog::DoDataExchange(pDX);
    1.70 +	//{{AFX_DATA_MAP(GBPrinterDlg)
    1.71 +	DDX_Radio(pDX, IDC_1X, m_scale);
    1.72 +	//}}AFX_DATA_MAP
    1.73 +}
    1.74 +
    1.75 +BEGIN_MESSAGE_MAP(GBPrinterDlg, CDialog)
    1.76 +//{{AFX_MSG_MAP(GBPrinterDlg)
    1.77 +ON_BN_CLICKED(ID_SAVE, OnSave)
    1.78 +ON_BN_CLICKED(ID_PRINT, OnPrint)
    1.79 +ON_BN_CLICKED(ID_OK, OnOk)
    1.80 +ON_BN_CLICKED(IDC_1X, On1x)
    1.81 +ON_BN_CLICKED(IDC_2X, On2x)
    1.82 +ON_BN_CLICKED(IDC_3X, On3x)
    1.83 +ON_BN_CLICKED(IDC_4X, On4x)
    1.84 +ON_WM_PAINT()
    1.85 +//}}AFX_MSG_MAP
    1.86 +END_MESSAGE_MAP()
    1.87 +
    1.88 +/////////////////////////////////////////////////////////////////////////////
    1.89 +// GBPrinter message handlers
    1.90 +
    1.91 +void GBPrinterDlg::saveAsBMP(const char *name)
    1.92 +{
    1.93 +	u8 writeBuffer[512 * 3];
    1.94 +
    1.95 +	FILE *fp = fopen(name, "wb");
    1.96 +
    1.97 +	if (!fp)
    1.98 +	{
    1.99 +		systemMessage(MSG_ERROR_CREATING_FILE, "Error creating file %s", name);
   1.100 +		return;
   1.101 +	}
   1.102 +
   1.103 +	struct
   1.104 +	{
   1.105 +		u8 ident[2];
   1.106 +		u8 filesize[4];
   1.107 +		u8 reserved[4];
   1.108 +		u8 dataoffset[4];
   1.109 +		u8 headersize[4];
   1.110 +		u8 width[4];
   1.111 +		u8 height[4];
   1.112 +		u8 planes[2];
   1.113 +		u8 bitsperpixel[2];
   1.114 +		u8 compression[4];
   1.115 +		u8 datasize[4];
   1.116 +		u8 hres[4];
   1.117 +		u8 vres[4];
   1.118 +		u8 colors[4];
   1.119 +		u8 importantcolors[4];
   1.120 +		u8 pad[2];
   1.121 +	} bmpheader;
   1.122 +	memset(&bmpheader, 0, sizeof(bmpheader));
   1.123 +
   1.124 +	bmpheader.ident[0] = 'B';
   1.125 +	bmpheader.ident[1] = 'M';
   1.126 +
   1.127 +	u32 fsz = sizeof(bmpheader) + 160*144*3;
   1.128 +	utilPutDword(bmpheader.filesize, fsz);
   1.129 +	utilPutDword(bmpheader.dataoffset, 0x38);
   1.130 +	utilPutDword(bmpheader.headersize, 0x28);
   1.131 +	utilPutDword(bmpheader.width, 160);
   1.132 +	utilPutDword(bmpheader.height, 144);
   1.133 +	utilPutDword(bmpheader.planes, 1);
   1.134 +	utilPutDword(bmpheader.bitsperpixel, 24);
   1.135 +	utilPutDword(bmpheader.datasize, 160*144);
   1.136 +
   1.137 +	fwrite(&bmpheader, 1, sizeof(bmpheader), fp);
   1.138 +
   1.139 +	u8 *b    = writeBuffer;
   1.140 +	u8 *data = (u8 *)bitmapData;
   1.141 +	u8 *p    = data + (160*143);
   1.142 +	for (int y = 0; y < 144; y++)
   1.143 +	{
   1.144 +		for (int x = 0; x < 160; x++)
   1.145 +		{
   1.146 +			u8 c = *p++;
   1.147 +
   1.148 +			*b++ = bitmap->bmiColors[c].rgbBlue;
   1.149 +			*b++ = bitmap->bmiColors[c].rgbGreen;
   1.150 +			*b++ = bitmap->bmiColors[c].rgbRed;
   1.151 +		}
   1.152 +		p -= 2*(160);
   1.153 +		fwrite(writeBuffer, 1, 3*160, fp);
   1.154 +
   1.155 +		b = writeBuffer;
   1.156 +	}
   1.157 +
   1.158 +	fclose(fp);
   1.159 +}
   1.160 +
   1.161 +void GBPrinterDlg::saveAsPNG(const char *name)
   1.162 +{
   1.163 +	u8 writeBuffer[160 * 3];
   1.164 +
   1.165 +	FILE *fp = fopen(name, "wb");
   1.166 +
   1.167 +	if (!fp)
   1.168 +	{
   1.169 +		systemMessage(MSG_ERROR_CREATING_FILE, "Error creating file %s",
   1.170 +		              name);
   1.171 +		return;
   1.172 +	}
   1.173 +
   1.174 +	png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING,
   1.175 +	                                              NULL,
   1.176 +	                                              NULL,
   1.177 +	                                              NULL);
   1.178 +	if (!png_ptr)
   1.179 +	{
   1.180 +		fclose(fp);
   1.181 +		return;
   1.182 +	}
   1.183 +
   1.184 +	png_infop info_ptr = png_create_info_struct(png_ptr);
   1.185 +
   1.186 +	if (!info_ptr)
   1.187 +	{
   1.188 +		png_destroy_write_struct(&png_ptr, NULL);
   1.189 +		fclose(fp);
   1.190 +		return;
   1.191 +	}
   1.192 +
   1.193 +	if (setjmp(png_ptr->jmpbuf))
   1.194 +	{
   1.195 +		png_destroy_write_struct(&png_ptr, NULL);
   1.196 +		fclose(fp);
   1.197 +		return;
   1.198 +	}
   1.199 +
   1.200 +	png_init_io(png_ptr, fp);
   1.201 +
   1.202 +	png_set_IHDR(png_ptr,
   1.203 +	             info_ptr,
   1.204 +	             160,
   1.205 +	             144,
   1.206 +	             8,
   1.207 +	             PNG_COLOR_TYPE_RGB,
   1.208 +	             PNG_INTERLACE_NONE,
   1.209 +	             PNG_COMPRESSION_TYPE_DEFAULT,
   1.210 +	             PNG_FILTER_TYPE_DEFAULT);
   1.211 +
   1.212 +	png_write_info(png_ptr, info_ptr);
   1.213 +
   1.214 +	u8 *b = writeBuffer;
   1.215 +
   1.216 +	int sizeX = 160;
   1.217 +	int sizeY = 144;
   1.218 +
   1.219 +	u8 *pixU8 = (u8 *)bitmapData;
   1.220 +	for (int y = 0; y < sizeY; y++)
   1.221 +	{
   1.222 +		for (int x = 0; x < sizeX; x++)
   1.223 +		{
   1.224 +			u8 c = *pixU8++;
   1.225 +			*b++ = bitmap->bmiColors[c].rgbRed;
   1.226 +			*b++ = bitmap->bmiColors[c].rgbGreen;
   1.227 +			*b++ = bitmap->bmiColors[c].rgbBlue;
   1.228 +		}
   1.229 +		png_write_row(png_ptr, writeBuffer);
   1.230 +
   1.231 +		b = writeBuffer;
   1.232 +	}
   1.233 +
   1.234 +	png_write_end(png_ptr, info_ptr);
   1.235 +
   1.236 +	png_destroy_write_struct(&png_ptr, &info_ptr);
   1.237 +
   1.238 +	fclose(fp);
   1.239 +}
   1.240 +
   1.241 +void GBPrinterDlg::OnSave()
   1.242 +{
   1.243 +	CString captureBuffer;
   1.244 +
   1.245 +	if (theApp.captureFormat == 0)
   1.246 +		captureBuffer = "printer.png";
   1.247 +	else
   1.248 +		captureBuffer = "printer.bmp";
   1.249 +
   1.250 +	LPCTSTR exts[] = {".png", ".bmp", NULL };
   1.251 +
   1.252 +	CString filter = winResLoadFilter(IDS_FILTER_PNG);
   1.253 +	CString title  = winResLoadString(IDS_SELECT_CAPTURE_NAME);
   1.254 +
   1.255 +	FileDlg dlg(this,
   1.256 +	            captureBuffer,
   1.257 +	            filter,
   1.258 +	            theApp.captureFormat ? 2 : 1,
   1.259 +	            theApp.captureFormat ? "BMP" : "PNG",
   1.260 +	            exts,
   1.261 +	            "",
   1.262 +	            title,
   1.263 +	            true);
   1.264 +
   1.265 +	if (dlg.DoModal() == IDCANCEL)
   1.266 +	{
   1.267 +		return;
   1.268 +	}
   1.269 +
   1.270 +	captureBuffer = dlg.GetPathName();
   1.271 +
   1.272 +	if (dlg.getFilterIndex() == 2)
   1.273 +		saveAsBMP(captureBuffer);
   1.274 +	else
   1.275 +		saveAsPNG(captureBuffer);
   1.276 +}
   1.277 +
   1.278 +void GBPrinterDlg::OnPrint()
   1.279 +{
   1.280 +	CPrintDialog dlg(FALSE);
   1.281 +
   1.282 +	dlg.m_pd.nFromPage = 1;
   1.283 +	dlg.m_pd.nToPage   = 1;
   1.284 +	dlg.m_pd.nMinPage  = 1;
   1.285 +	dlg.m_pd.nMaxPage  = 1;
   1.286 +	dlg.m_pd.nCopies   = 1;
   1.287 +
   1.288 +	if (dlg.DoModal() == IDOK)
   1.289 +	{
   1.290 +		DOCINFO di;
   1.291 +		float   fLogPelsX1 = 0;
   1.292 +		float   fLogPelsX2 = 0;
   1.293 +		float   fLogPelsY1 = 0;
   1.294 +		float   fLogPelsY2 = 0;
   1.295 +		float   fScaleX    = 0, fScaleY = 0;
   1.296 +		CDC *   winDC      = NULL;
   1.297 +		memset(&di, 0, sizeof(di));
   1.298 +		di.cbSize = sizeof(DOCINFO);
   1.299 +		CString docName = winResLoadString(IDS_POCKET_PRINTER);
   1.300 +		di.lpszDocName = docName;
   1.301 +		CDC dc;
   1.302 +		dc.Attach(dlg.GetPrinterDC());
   1.303 +		int nError = dc.StartDoc(&di);
   1.304 +
   1.305 +		if (nError == SP_ERROR)
   1.306 +		{
   1.307 +			systemMessage(IDS_ERROR_ON_STARTDOC, "Error on StartDoc");
   1.308 +			goto error;
   1.309 +		}
   1.310 +		nError = dc.StartPage();
   1.311 +		if (nError <= 0)
   1.312 +		{
   1.313 +			systemMessage(IDS_ERROR_ON_STARTPAGE, "Error on StartPage");
   1.314 +			goto error;
   1.315 +		}
   1.316 +
   1.317 +		winDC      = GetDC();
   1.318 +		fLogPelsX1 = (float)winDC->GetDeviceCaps(LOGPIXELSX);
   1.319 +		fLogPelsY1 = (float)winDC->GetDeviceCaps(LOGPIXELSY);
   1.320 +		ReleaseDC(winDC);
   1.321 +
   1.322 +		fLogPelsX2 = (float)dc.GetDeviceCaps(LOGPIXELSX);
   1.323 +		fLogPelsY2 = (float)dc.GetDeviceCaps(LOGPIXELSY);
   1.324 +
   1.325 +		if (fLogPelsX1 > fLogPelsX2)
   1.326 +			fScaleX = fLogPelsX1 / fLogPelsX2;
   1.327 +		else
   1.328 +			fScaleX = fLogPelsX2 / fLogPelsX1;
   1.329 +
   1.330 +		if (fLogPelsY1 > fLogPelsY2)
   1.331 +			fScaleY = fLogPelsY1 / fLogPelsY2;
   1.332 +		else
   1.333 +			fScaleY = fLogPelsY2 / fLogPelsY1;
   1.334 +
   1.335 +		fScaleX *= (scale+1);
   1.336 +		fScaleY *= (scale+1);
   1.337 +
   1.338 +		if (StretchDIBits(dc,
   1.339 +		                  0,
   1.340 +		                  0,
   1.341 +		                  (int)((float)160*fScaleX),
   1.342 +		                  (int)((float)144*fScaleY),
   1.343 +		                  0,
   1.344 +		                  0,
   1.345 +		                  160,
   1.346 +		                  144,
   1.347 +		                  bitmapData,
   1.348 +		                  bitmap,
   1.349 +		                  DIB_RGB_COLORS,
   1.350 +		                  SRCCOPY) == GDI_ERROR)
   1.351 +		{
   1.352 +			systemMessage(IDS_ERROR_PRINTING_ON_STRETCH,
   1.353 +			              "Error printing on StretchDIBits");
   1.354 +		}
   1.355 +
   1.356 +		nError = dc.EndPage();
   1.357 +
   1.358 +		if (nError <= 0)
   1.359 +		{
   1.360 +			systemMessage(IDS_ERROR_ON_ENDPAGE, "Error on EndPage");
   1.361 +			goto error;
   1.362 +		}
   1.363 +
   1.364 +		nError = dc.EndDoc();
   1.365 +
   1.366 +		if (nError <= 0)
   1.367 +			systemMessage(IDS_ERROR_ON_ENDDOC, "Error on EndDoc");
   1.368 +error:
   1.369 +		dc.DeleteDC();
   1.370 +	}
   1.371 +}
   1.372 +
   1.373 +void GBPrinterDlg::processData(u8 *data)
   1.374 +{
   1.375 +	for (int y = 0; y < 0x12; y++)
   1.376 +	{
   1.377 +		for (int x = 0; x < 0x14; x++)
   1.378 +		{
   1.379 +			for (int k = 0; k < 8; k++)
   1.380 +			{
   1.381 +				int a = *data++;
   1.382 +				int b = *data++;
   1.383 +				for (int j = 0; j < 8; j++)
   1.384 +				{
   1.385 +					int mask = 1 << (7-j);
   1.386 +					int c    = 0;
   1.387 +					if (a & mask)
   1.388 +						c++;
   1.389 +					if (b & mask)
   1.390 +						c += 2;
   1.391 +					bitmapData[x*8+j + 160*(y*8+k)] = c;
   1.392 +				}
   1.393 +			}
   1.394 +		}
   1.395 +	}
   1.396 +}
   1.397 +
   1.398 +BOOL GBPrinterDlg::OnInitDialog()
   1.399 +{
   1.400 +	CDialog::OnInitDialog();
   1.401 +
   1.402 +	scale = regQueryDwordValue("printerScale", 0);
   1.403 +	if (scale < 0 || scale > 3)
   1.404 +		scale = 0;
   1.405 +	m_scale = scale;
   1.406 +	UpdateData(FALSE);
   1.407 +
   1.408 +	CenterWindow();
   1.409 +
   1.410 +	return TRUE; // return TRUE unless you set the focus to a control
   1.411 +	             // EXCEPTION: OCX Property Pages should return FALSE
   1.412 +}
   1.413 +
   1.414 +void GBPrinterDlg::OnOk()
   1.415 +{
   1.416 +	EndDialog(TRUE);
   1.417 +}
   1.418 +
   1.419 +void GBPrinterDlg::On1x()
   1.420 +{
   1.421 +	regSetDwordValue("printerScale", 0);
   1.422 +	scale = 0;
   1.423 +}
   1.424 +
   1.425 +void GBPrinterDlg::On2x()
   1.426 +{
   1.427 +	regSetDwordValue("printerScale", 1);
   1.428 +	scale = 1;
   1.429 +}
   1.430 +
   1.431 +void GBPrinterDlg::On3x()
   1.432 +{
   1.433 +	regSetDwordValue("printerScale", 2);
   1.434 +	scale = 2;
   1.435 +}
   1.436 +
   1.437 +void GBPrinterDlg::On4x()
   1.438 +{
   1.439 +	regSetDwordValue("printerScale", 3);
   1.440 +	scale = 3;
   1.441 +}
   1.442 +
   1.443 +void GBPrinterDlg::OnPaint()
   1.444 +{
   1.445 +	CPaintDC dc(this); // device context for painting
   1.446 +
   1.447 +	RECT  rect;
   1.448 +	CWnd *h = GetDlgItem(IDC_GB_PRINTER);
   1.449 +	h->GetWindowRect(&rect);
   1.450 +	POINT p;
   1.451 +	p.x = rect.left;
   1.452 +	p.y = rect.top;
   1.453 +	ScreenToClient((POINT *)&p);
   1.454 +	rect.left = p.x+1;
   1.455 +	rect.top  = p.y+1;
   1.456 +	p.x       = rect.right;
   1.457 +	p.y       = rect.bottom;
   1.458 +	ScreenToClient((POINT *)&p);
   1.459 +	rect.right  = p.x-1;
   1.460 +	rect.bottom = p.y-1;
   1.461 +
   1.462 +	StretchDIBits(dc,
   1.463 +	              rect.left,
   1.464 +	              rect.top,
   1.465 +	              rect.right - rect.left,
   1.466 +	              rect.bottom - rect.top,
   1.467 +	              0,
   1.468 +	              0,
   1.469 +	              160,
   1.470 +	              144,
   1.471 +	              bitmapData,
   1.472 +	              bitmap,
   1.473 +	              DIB_RGB_COLORS,
   1.474 +	              SRCCOPY);
   1.475 +}
   1.476 +
   1.477 +void systemGbPrint(u8 *data,
   1.478 +                   int pages,
   1.479 +                   int feed,
   1.480 +                   int palette,
   1.481 +                   int contrast)
   1.482 +{
   1.483 +	theApp.winCheckFullscreen();
   1.484 +	GBPrinterDlg printer;
   1.485 +	printer.processData(data);
   1.486 +	printer.DoModal();
   1.487 +}
   1.488 +