打印:DC畫圖,打印設置等

T:打印圖標的問題 
Q:DrawIconEx 可以顯示到屏幕上,打印其他圖形也行,

但就是 DrawIconEx 往打印機上打不出來,爲何?
A:這個有點難,你要先把圖標華在一個dc上,然後從這個dc得到一個位圖,然後把位圖轉化成DIB位圖,然後用StretchDIBits打印
T:打印??在線等待。 
Q:HANDLE hPRN = CreateFile("prn"...);
if(hPRN)
{
    WriteFile(hPRN, "asdf中文asdf"...)
    CloseHandle(hPRN);
}

爲什麼打印時"中文"兩個子沒有打印出來!?
A:
向樓上說的那樣,你要得到這個打印機的DC,然後在DC上面寫寫畫畫,,然或結束打印就OK拉,建議你跟蹤進去OnPrint等函數,就能知道Windows是怎樣打印的了
T:如何讓CPrintDialog 一打開就選種 
Q:LandScape的紙行
A:CPrintDialog的m_pPD成員的一個什麼mode參數可以改變,具體代碼我回家後看看,現在沒有VC
m_pd->hDevMode中的dmOrientation設爲DMORIENT_LANDSCAPE試試
T:怎樣讀取或更改“打印設置”裏的內容,比如紙張大小,橫向,縱向? 
Q:我想用程序更改紙張方向和選擇紙張大小怎麼實現?謝謝!
A:/* 設置系統打印模式      
#define DMORIENT_PORTRAIT   1   //縱向
#define DMORIENT_LANDSCAPE  2   //橫向                                      */
/************************************************************************/

void SetLandscapeMode(int PrintMode)
{
 PRINTDLG pd;
 pd.lStructSize=(DWORD)sizeof(PRINTDLG);
 BOOL bRet=AfxGetApp()->GetPrinterDeviceDefaults(&pd);
 if(bRet)
 {
  // protect memory handle with ::GlobalLock and ::GlobalUnlock
  DEVMODE FAR *pDevMode=(DEVMODE FAR *)::GlobalLock(pd.hDevMode);
  // set orientation to landscape
  if(PrintMode==1)//縱向打印
   pDevMode->dmOrientation=DMORIENT_PORTRAIT;
  else if(PrintMode==2)//橫向打印
   pDevMode->dmOrientation=DMORIENT_LANDSCAPE;  
  ::GlobalUnlock(pd.hDevMode);
 }
}

pDevMode的其它成員變量可以控制紙張大小
T:通過位圖的句柄打印位圖(高分等待,不夠再給) 
Q:小弟有難,請大俠們幫忙,得到了一個位圖的句柄,如何打印
A:一個打印位圖的例子
View類添加成員
 CDC  m_MemDC; // 內存設備環境指針,在視的整個存在過程都將存在
 CBitmap m_Bitmap; 
 CSize  m_szSource, m_szDest; // 記錄源位圖尺寸和最終顯示尺寸
————————————————————————————————————————
int CPrintBmpView::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
 if (CScrollView::OnCreate(lpCreateStruct) == -1)
  return -1;
 
 // TODO: Add your specialized creation code here
 BITMAP bm;
 if(m_MemDC.GetSafeHdc() == NULL)
 {
  CClientDC dc(this);
  m_Bitmap.LoadBitmap(IDB_BITMAP1);
  m_MemDC.CreateCompatibleDC(&dc);
  m_MemDC.SelectObject(&m_Bitmap);
  m_Bitmap.GetObject(sizeof(bm),&bm);
  m_szSource.cx = bm.bmWidth;
  m_szSource.cy = bm.bmHeight;
  m_szDest = m_szSource;
  dc.DPtoLP(&m_szDest);
 }
 
 return 0;
}
———————————————————————————————————————————
void CPrintBmpView::OnInitialUpdate()
{
 CScrollView::OnInitialUpdate();

 CSize sizeTotal;
 sizeTotal.cx = 800;
 sizeTotal.cy = 1050;
 CSize sizeLine = CSize(sizeTotal.cx / 100, sizeTotal.cy / 100);
 SetScrollSizes(MM_LOENGLISH, sizeTotal, sizeTotal, sizeLine);
 
 
}
————————————————————————————————————————————
void CPrintBmpView::OnDraw(CDC* pDC)
{
 CPrintBmpDoc* pDoc = GetDocument();
 ASSERT_VALID(pDoc);
 // TODO: add draw code for native data here
 pDC->StretchBlt(100, -100, m_szDest.cx, -m_szDest.cy,
  &m_MemDC, 0, 0, m_szSource.cx, m_szSource.cy, SRCCOPY);
}
————————————————————————————————————————————
void CPrintBmpView::OnDestroy()
{
 CScrollView::OnDestroy();
 
 // TODO: Add your message handler code here
 m_Bitmap.DeleteObject();
 m_MemDC.DeleteDC();
}

T:非常簡單的打印問題! 
Q:我現在要打印圖形可視部分的打印,應該怎麼做啊?
圖形是在0.1mm模式下繪製的,在OnPrint()函數中把映射模式改爲MM_TWIPS,
如果我沒有添加什麼代碼的話,程序就是出圖形最做上角的那部分,但是我只要打印可以看見的那部分,我用InvalidateRect()函數,可是沒有什麼變化?這個到底應該怎麼弄呢?
A:我覺得最好打印和繪圖的繪圖模式一致,並且都不是MM_TEXT,這樣的話就用不着座標轉換了,否則的話,你可以記下可視部分的打印區域,打印時使用CDC::SelectClipRgn設置打印區域,基本就是這樣子吧
T:請問各位高手,怎麼把視圖變爲一個BMP文件? 
Q:我想把我的視圖變爲一個BMP文件,我該如何辦呢?請各位大俠教教我,最好有源碼相送
A:前幾天你的那幾個打印的問題解決了吧?
下面兩個函數中一個是得到dc的位圖,一個是把位圖保存爲文件,記得給分哦:)
hDC傳入視圖的pDC->GetSafeHdc()即可
HBITMAP GetSrcBit(HDC hDC,DWORD BitWidth, DWORD BitHeight)
{
 HDC hBufDC;
 HBITMAP hBitmap, hBitTemp;

 //創建設備上下文(HDC)
 hBufDC = CreateCompatibleDC(hDC);

 //創建HBITMAP
 hBitmap = CreateCompatibleBitmap(hDC, BitWidth, BitHeight);
 hBitTemp = (HBITMAP) SelectObject(hBufDC, hBitmap);
 
 //得到位圖緩衝區
 StretchBlt(hBufDC, 0, 0, BitWidth, BitHeight,
   hDC, 0, 0, BitWidth, BitHeight, SRCCOPY);

 //得到最終的位圖信息
 hBitmap = (HBITMAP) SelectObject(hBufDC, hBitTemp);

 //釋放內存

 DeleteObject(hBitTemp);
 ::DeleteDC(hBufDC);

 return hBitmap;
}

BOOL SaveBmp(HBITMAP hBitmap, CString FileName)
{
 //設備描述表
 HDC hDC;
 //當前分辨率下每象素所佔字節數
 int iBits;
 //位圖中每象素所佔字節數
 WORD wBitCount;
 //定義調色板大小, 位圖中像素字節大小 ,位圖文件大小 , 寫入文件字節數
 DWORD dwPaletteSize=0, dwBmBitsSize=0, dwDIBSize=0, dwWritten=0;
 //位圖屬性結構
 BITMAP Bitmap; 
 //位圖文件頭結構
 BITMAPFILEHEADER bmfHdr; 
 //位圖信息頭結構
 BITMAPINFOHEADER bi; 
 //指向位圖信息頭結構 
 LPBITMAPINFOHEADER lpbi; 
 //定義文件,分配內存句柄,調色板句柄
 HANDLE fh, hDib, hPal,hOldPal=NULL;
 
 //計算位圖文件每個像素所佔字節數
 hDC = CreateDC("DISPLAY", NULL, NULL, NULL);
 iBits = GetDeviceCaps(hDC, BITSPIXEL) * GetDeviceCaps(hDC, PLANES);
 DeleteDC(hDC);
 if (iBits <= 1)  wBitCount = 1;
 else if (iBits <= 4)  wBitCount = 4;
 else if (iBits <= 8)  wBitCount = 8;
 else      wBitCount = 24;
 
 GetObject(hBitmap, sizeof(Bitmap), (LPSTR)&Bitmap);
 bi.biSize   = sizeof(BITMAPINFOHEADER);
 bi.biWidth   = Bitmap.bmWidth;
 bi.biHeight   = Bitmap.bmHeight;
 bi.biPlanes   = 1;
 bi.biBitCount  = wBitCount;
 bi.biCompression = BI_RGB;
 bi.biSizeImage  = 0;
 bi.biXPelsPerMeter = 0;
 bi.biYPelsPerMeter = 0;
 bi.biClrImportant = 0;
 bi.biClrUsed  = 0;
 
 dwBmBitsSize = ((Bitmap.bmWidth * wBitCount + 31) / 32) * 4 * Bitmap.bmHeight;
 
 //爲位圖內容分配內存
 hDib = GlobalAlloc(GHND,dwBmBitsSize + dwPaletteSize + sizeof(BITMAPINFOHEADER));
 lpbi = (LPBITMAPINFOHEADER)GlobalLock(hDib);
 *lpbi = bi;

 // 處理調色板 
 hPal = GetStockObject(DEFAULT_PALETTE);
 if (hPal)
 {
  hDC = ::GetDC(NULL);
  hOldPal = ::SelectPalette(hDC, (HPALETTE)hPal, FALSE);
  RealizePalette(hDC);
 }

 // 獲取該調色板下新的像素值
 GetDIBits(hDC, hBitmap, 0, (UINT) Bitmap.bmHeight, (LPSTR)lpbi + sizeof(BITMAPINFOHEADER)
   +dwPaletteSize, (BITMAPINFO *)lpbi, DIB_RGB_COLORS);
 
 //恢復調色板 
 if (hOldPal)
 {
  ::SelectPalette(hDC, (HPALETTE)hOldPal, TRUE);
  RealizePalette(hDC);
  ::ReleaseDC(NULL, hDC);
 }

 //創建位圖文件 
 fh = CreateFile(FileName, GENERIC_WRITE,0, NULL, CREATE_ALWAYS,
     FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, NULL);
 
 if (fh == INVALID_HANDLE_VALUE)  return FALSE;
 
 // 設置位圖文件頭
 bmfHdr.bfType = 0x4D42; // "BM"
 dwDIBSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + dwPaletteSize + dwBmBitsSize; 
 bmfHdr.bfSize = dwDIBSize;
 bmfHdr.bfReserved1 = 0;
 bmfHdr.bfReserved2 = 0;
 bmfHdr.bfOffBits = (DWORD)sizeof(BITMAPFILEHEADER) + (DWORD)sizeof(BITMAPINFOHEADER) + dwPaletteSize;
 // 寫入位圖文件頭
 WriteFile(fh, (LPSTR)&bmfHdr, sizeof(BITMAPFILEHEADER), &dwWritten, NULL);
 // 寫入位圖文件其餘內容
// WriteFile(fh, (LPSTR)lpbi, dwDIBSize, &dwWritten, NULL);
 //清除 
 GlobalUnlock(hDib);
 GlobalFree(hDib);
 CloseHandle(fh);

 return TRUE;
}
T:   如何控制打印機的進紙長度  
Q:小弟在做VC關於打印的時候,發現通過pDC指針可以控制走紙的頁數  可是怎麼控制走紙的長度啊,譬如紙張的長度是8*13/2的,小弟很着急,希望那位高手可以幫小地解決.
A:首先你可以通過自定義紙張大小(改變DEVMODE的下列成員)
  DWORD  dmFields;
 short dmOrientation;
 short dmPaperSize;
 short dmPaperLength;
 short dmPaperWidth;
 這也要打印機驅動的支持,如果打印機支持捲筒紙或自定義紙張大小的話就沒問題,否則………… //設備描述表
T:打印設置問題!急急急急急急急急!!!!
Q:打印時不彈出打印對話框,打印頁面的大小等參數由程序中設定
頁面大小不是標準的紙張,打印機是網絡中的打印機。
不知那爲兄弟能夠解決,最好有源碼,分不夠可以在加
A:下面的程序可以通過改變pDevMode成員改變紙張大小
void SetLandscapeMode(int PrintMode)
{
 PRINTDLG pd;
 pd.lStructSize=(DWORD)sizeof(PRINTDLG);
 BOOL bRet=AfxGetApp()->GetPrinterDeviceDefaults(&pd);
 if(bRet)
 {
  // protect memory handle with ::GlobalLock and ::GlobalUnlock
  DEVMODE FAR *pDevMode=(DEVMODE FAR *)::GlobalLock(pd.hDevMode);
  // set orientation to landscape
  if(PrintMode==1)//縱向打印
   pDevMode->dmOrientation=DMORIENT_PORTRAIT;
  else if(PrintMode==2)//橫向打印
   pDevMode->dmOrientation=DMORIENT_LANDSCAPE;  
  ::GlobalUnlock(pd.hDevMode);
 }
}

呵呵,發現我的代碼終於也被別人傳來傳去了,好現象
T:200分在線等待:如何取得打印機打印的時候設置的“每sheet打幾頁”(一張紙打幾頁) 
Q:用getjob得到的結構devmode中好象都不是啊。大俠幫忙
A:dmCopies;
並且dmFields=dmFields|DM_COPIES
T:有沒有辦法按打印按鈕時不彈出那個打印對話框,而直接打印?(前提我已知道打印機的名字)
Q:謝謝
我是不想讓他設置打印機,而用我所確定的打印機幫他打印,
所以想屏蔽掉那個打印對話框,有什麼辦法嗎???
A:以下代碼摘自bluebohe(薄荷)發給我的。
回覆人: bluebohe(薄荷) ( ) 信譽:127  2003-12-22 12:53:00  得分:0
 
 
  void PrintTest()
{
 CPrintDialog pd(FALSE, PD_ALLPAGES | PD_COLLATE | PD_NOPAGENUMS | PD_HIDEPRINTTOFILE);
 if(pd.GetDefaults())
 {
  DOCINFO di;
  memset( &di, 0, sizeof(DOCINFO) );
  di.cbSize = sizeof(DOCINFO);
  di.lpszDocName = "Printing Test";
  di.lpszOutput = (LPTSTR) NULL;
  di.fwType = 0;
  HDC hDC=pd.CreatePrinterDC();
  CDC dc;
  dc.Attach(hDC);
  dc.StartDoc(&di);
  dc.StartPage();
  dc.MoveTo(0,0);
  dc.LineTo(1000,1000);
  dc.EndPage();
  dc.EndDoc(); 
  dc.DeleteDC();
 }
}

T:一千分求教,在線等待。如何使TrueType中文字體無論大小均按單線條筆畫顯示和打印? 
Q:一個TrueType中文字體,如何使其不管字高如何,字體的筆畫總是單線條,像AutoCAD的效果一樣?英文字體的情況已能解決,但中文TrueType中似乎含有位圖,不能解決,請指教。在線等待,一千分候教,分頁給分。
A:如果做出來的話,我也給你一千分
我這裏有讀AutoCAD字體的程序
另外,英文你是怎麼解決的?

我做了三年也沒做出來……最後只能用單線體
你能把AutoCAD字體文件的說明給我發過來嗎?[email protected]或者AutoCAD的幫助中的關於字體文件格式的一個幫助文件,我這裏沒有AutoCAD。

好吧,謝謝
大多數TrueType字體並不是文字充滿字模空間的,所以如果按照字模的高度去顯示文字的話,可能文字就要小很多,想改大了並非不可以,但是因爲前面已經發布了一些版本,好多文字就是按照小字寫的,所以爲了文字的標準,就添加了單線體

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章