|
|
Comments and Discussions
|
|
 |

|
Great article!
One quick question.
What piece of code should I change to remove the blank spacing between the pages?
So that each page would be beside each other in other words?
I have tried everything.
Thank you!
|
|
|
|

|
Could I send email to you?
I have some question about printing in MFC. thank you.
|
|
|
|

|
You can get/set the current printer orientation without having to modify your application class because it's not necessary to access CWinApp::m_hDevMode - you find another hDevMode in the PRINTDLG structure retrieved with GetPrinterDeviceDefaults which is ready for use. Just try this, which can go right into the view's message handler: CWinApp *const pApp = AfxGetApp(); if (pApp!=NULL) { PRINTDLG pd; pd.lStructSize = sizeof(PRINTDLG); if (pApp->GetPrinterDeviceDefaults(&pd)) { DEVMODE FAR *const pDevMode = reinterpret_cast<DEVMODE FAR *>(::GlobalLock(pd.hDevMode)); pDevMode->dmOrientation = DMORIENT_LANDSCAPE: ::GlobalUnlock(pd.hDevMode); } } And it looks just better without those ugly C casts.
|
|
|
|

|
In a network printer, when the printer print the document, How many pages printer lets print & which system sent the data to print.
How to find this job fron VC++/VB
Please help me
|
|
|
|

|
First, great work!!!
I wonder if it's possible to change your code to have opportunity to add pages with different size and orientation!?
To have portrait and landscape together!?
Thank you in advance and Good luck!
Stoil Todorov
|
|
|
|

|
I understood how to combine pages with portrait and landscape.
I found Microsoft Knowledge Base Article - 214617 "Changing the Page Orientation to Landscape Without Interacting with the Print Dialog Box in an MFC-Based Application" in MSDN and I used the given code in my project.
Now I can change orientation of page during printing and in print preview. The key was in OnPrepareDC(CDC* pDC, CPrintInfo* pInfo) where I change orientation with this function: pDC->ResetDC(m_lpDevMode) - m_lpDevMode show page orientation.
Stoil Todorov
|
|
|
|

|
Why the Print Preview font (Page X of X) change from Courier to Arial, and back to courier depending of the zooming factor and the orientation ?
I'm using WinXP and Win2K and have this issue on both systems
|
|
|
|

|
Instead of just limiting your code to landscape and portrait why not add the setup dialog.
CWinApp *pApp = AfxGetApp();
CPrintDialog pd(TRUE);
pApp->DoPrintDialog(&pd); // print setup dialog
CPrintInfo *pInfo = m_pPreviewInfo;
m_pPreviewInfo = NULL;
m_dcPrint.Detach(); // print DC is deleted by CPrintInfo destructor
delete pInfo;
SetPrintView(m_pPrintView);
This allows the view to change options, printer and orientation
Asconaga
|
|
|
|

|
Hello,
first very nice job, seems to be very helpfull
But before i could even think using this new Print Preview, maybe somebody could help me with following problem.
I use Visual STudio .Net (VC++7.0), migrated a middlesized Application from VC++6.0, But experiences hangups when I try to switch into Print preview.
I debugged the project and found out that so far everything seems right, Until in
CFrameWnd::OnSetPreviewMode,
following code is executed
HWND hWnd = ::GetDlgItem(m_hWnd, pState->nIDMainPane);
ASSERT(hWnd != NULL); // must be one that we are hiding!
::ShowWindow(hWnd, SW_HIDE);
where
pState->nIDMainPane==AFX_IDW_PANE_FIRST
which should be correct, and the retrieved hWnd seems to be ok too (Its not NULL) but then on the ::ShowWindow command, somehow the application went into an endless loop...
Did anybody had the same Problems and could solve this?
THanks in Advance
Wolfbert
|
|
|
|

|
This is great! thanks Roger!
|
|
|
|

|
Good work.
I know this article is about one year old, but I am new here and there is still something to do:
If the orientation is already landscape, the Checkbox is not checked when you open the preview.
To fix this, we need another additional function in our CWinApp derived class. This is for the same reason, you provided the SetPrintOrientation function. The prototype of this function and the code for it is as follows:
short GetPrintOrientation(void) ;
short CYourApp::GetPrintOrientation()
{
short sReturnvalue;
PRINTDLG pd;
pd.lStructSize = (DWORD)sizeof(PRINTDLG);
BOOL bRet = GetPrinterDeviceDefaults(&pd);
if (bRet)
{
DEVMODE *pDevMode = (DEVMODE*)::GlobalLock(m_hDevMode);
sReturnvalue = pDevMode->dmOrientation;
::GlobalUnlock(m_hDevMode);
}
return sReturnvalue;
}
Don't forget to mod the code so it uses your CWinApp derived class name and not that of the demo project.
Now we just have to put the following code in the CMultiPagePreviewView::OnCreate function, just before the return:
CWinApp *pApp = AfxGetApp();
CPrinterTestApp *pOurApp = static_cast<CYourApp*>(pApp) ;
ASSERT(pOurApp);
short sOrientation = pOurApp->GetPrintOrientation();
CWnd *pWnd = m_pToolBar->GetDlgItem(IDC_LANDSCAPE);
ASSERT(pWnd);
CButton *pButton = static_cast<CButton*>(pWnd);
ASSERT(pButton);
if(sOrientation == DMORIENT_LANDSCAPE)
pButton->SetCheck(BST_CHECKED);
else
pButton->SetCheck(BST_UNCHECKED);
I hope i did not forget something...
By the way, does someone have a solution for this problem:
When you set the preview to show one page, leave the preview and enter it again, the page is not shown centered as expected. It is shown in the left side of the window, just like it would be, if there were 2 pages to show. If you try this in the landscape mode, it is even more obvious.
Thanks
|
|
|
|

|
can i have ur mail id.. otherwise say how to attach one zipfile to u?..
Balaji
|
|
|
|

|
is it Posible to Print richtext with in a given rectangle area
don't worry with the size of file..
is a simple thing i expliend in lot..
Trying: Edit,RichEdit control printing,
with in a rectangle as per they are drawn
in scroll view..
----
//***************************************************************************************
// I want to draw the RichTextControl content in a specified rectangle on my printing page
// (as i done with editbox control) using FormatRange function with the different
// Font styles as in RichEditControl - HelpMe please!.
// DrawRichText(CDC *pDC) -> could u solve the problem that i have in this function ?..
//***************************************************************************************
//The partial code
//RTCtrlPrint1View.h
public:
CRTCtrlPrint1Doc* GetDocument();
//My*************************************
void RTCtrlCreate();
void DrawRichText(CDC *pDC);
void DrawEditText(CDC *pDC);
CRichEditCtrl m_redit;
CRect m_redRect;
CEdit m_edit;
CRect m_edRect;
UINT r;
CFont font;
//***************************************
//RTCtrlPrint1View.cpp
//=======================
void CRTCtrlPrint1View::OnInitialUpdate()
{
CScrollView::OnInitialUpdate();
//edith box displaytext font
font.CreateFont(14,0,0,0,FW_NORMAL,FALSE,FALSE,
0,ANSI_CHARSET,OUT_DEFAULT_PRECIS,
CLIP_DEFAULT_PRECIS,DEFAULT_QUALITY,
DEFAULT_PITCH|FF_MODERN,"Arial");
r=14;
m_edRect = CRect(50*r,-100*r,240*r,-700*r);
m_redRect = CRect(250*r,-100*r,750*r,-700*r);
CSize sizeTotal;
sizeTotal.cx = 850*r;
sizeTotal.cy = 1100*r;
SetScrollSizes(MM_TWIPS, sizeTotal); //MM_TWIPS
RTCtrlCreate();
}
void CRTCtrlPrint1View::OnDraw(CDC* pDC)
{
CRTCtrlPrint1Doc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
pDC->Rectangle(1*r,1*r,800*r,-1100*r);//Print Area Rect
if(pDC->IsPrinting())
{
DrawEditText(pDC);//Simple Edit box text
DrawRichText(pDC);//My RichEdit box text
}
}
#define IDC_REDIT 4001 //defining a resource ID
#define IDC_EDIT 4002 //defining a resource ID
void CRTCtrlPrint1View::RTCtrlCreate() //creates both Rich edit & Edit Controls
{
CRect m_temp;
CClientDC dc(this);
OnPrepareDC(&dc);
//creating edit box in scroll view
m_temp = m_edRect;
dc.LPtoDP(m_temp);
m_edit.Create(WS_CHILD|WS_VISIBLE|WS_BORDER|ES_MULTILINE,m_temp,this,IDC_EDIT);
m_edit.SetFont(&font,FALSE);
m_edit.SetWindowText("Help Me! Thank u");
//creating rich edit box in scroll view
m_temp = m_redRect;
dc.LPtoDP(m_temp);
m_redit.Create(WS_CHILD|WS_VISIBLE|WS_BORDER|ES_MULTILINE,m_temp,this,IDC_REDIT);
//writing some text in richtext control
CString str;
str="{\\rtf1\\ansi\\ansicpg1252\\deff0\\deflang2057{\\fonttbl{\\f0\froman\\fprq2\\fcharset0 Times New Roman;}{\\f1\\fswiss\\fprq2\\fcharset0 System;}}{\\colortbl ;\\red255\\green0\\blue0;\\red51\\green153\\blue102;\\red0\\green0\\blue255;}\\viewkind4\\uc1\\pard\\cf1\\i\\f0\\fs24 ThankYou\
\\cf0\\i0 \\cf2\\b for\
\\cf0\\b0 \\cf3 Trying\
\\cf0 !\\b\\f1\\fs20 \\par }";
EDITSTREAM es;
es.dwCookie = (DWORD)&str;
es.pfnCallback = RichEditStreamInCallback;
m_redit.StreamIn(SF_RTF,es);
}
void CRTCtrlPrint1View::OnPrepareDC(CDC* pDC, CPrintInfo* pInfo)
{
CScrollView::OnPrepareDC(pDC, pInfo);
// pDC->SetMapMode(MM_ANISOTROPIC);
pDC->SetMapMode(MM_TWIPS);
}
void CRTCtrlPrint1View::DrawEditText(CDC *pDC)
{
CRect m_temp;
m_temp = m_edRect;
CString str;
m_edit.GetWindowText(str);
pDC->SetBkMode(TRANSPARENT);
pDC->Rectangle(m_temp);
//Draws with Fonts as we wish
pDC->DrawText(str,m_temp,DT_WORDBREAK|DT_EXPANDTABS|DT_NOPREFIX);
}
//****************************************************************************
// I want to draw the RichTextControl content in a specified rectangle on my
// printing page (as i done with editbox control) using FormatRange function
// with the different Font styles as in RichEditControl - HelpMe please!.
// DrawRichText(CDC *pDC) -> could u solve the problem that i have in this
// function ?..
//****************************************************************************
void CRTCtrlPrint1View::DrawRichText(CDC *pDC)
{
CRect m_temp;
FORMATRANGE fmtRange;
long lLineWidth;
m_temp = m_redRect;
// pDC->LPtoDP(m_temp);
pDC->Rectangle(m_temp);
lLineWidth = ::MulDiv(pDC->GetDeviceCaps(PHYSICALWIDTH), 1440,
pDC->GetDeviceCaps(LOGPIXELSX));
fmtRange.hdc = pDC->m_hDC;
fmtRange.hdcTarget = pDC->m_hDC;
fmtRange.rc = m_temp;
fmtRange.rcPage = m_temp;
fmtRange.chrg.cpMin = 0;
fmtRange.chrg.cpMax = -1;
m_redit.SetTargetDevice(pDC->m_hDC, lLineWidth);
m_redit.FormatRange(&fmtRange, TRUE);
}
my MailID: cpbalaji2000@yahoo.com
Balaji
|
|
|
|

|
I need to provide that my aplication, which inherits CWinApp class, has it's own clipboard - that is, to provide copying, cuting and pasteing only in my aplication's scope.
I would be gratefull for any kind of tip or a hint...
|
|
|
|

|
I have used this code in a VC++ 6 project and it works very well - great!
However (I think) I want to convert this project to VC++7, and there seem to be a couple of problems.
One is easy to fix: in MultiPagePreview.h,
#include <..\src\afximpl.h>
needs changing to
#include <..\src\mfc\afximpl.h>
(I think this has been referred to in another article)
The other seems more tricky, and seems to be caused by the different presentation of the Print Preview in VC++7 - you can still see the main frame window. If you Exit while in Preview mode, "OnEndPrinting" never gets called so any fonts created in OnBeginPrinting don't get deleted - memory leaks! It seems likely that the same problem would occur with the "standard" print preview.
Having had a look at the VC++7 documentation, print/preview seems to be done in a somewhat different way. So the question is, is it worth struggling with VC++7 to make this part work? Or does somebody have a quick fix?
|
|
|
|

|
I had abandoned VC++7 for other reasons - back to trying it now. And I've solved this problem.
I found it occured when switching from Portrait to Landscape mode within the view.
I was creating some new fonts inside my OnBeginPrinting function, and then deleteing them inside my OnEndPrinting. In VC++6 the latter is called when switching from Portrait to Landscape, but in VC++7 it is not - only when closing the print preview.
Improving the new / delete logic stopped this problem.
Hope this is of some assistance to somebody - evan after all this time!
Paul
|
|
|
|

|
When you switch between Landscape and Portrait view, you did a very nice job of figuring out how to reset the PreviewView with very little duplicated code. SetPrintView goes through the process of OnPreparePrinting and OnBeginPrinting. The only thing that I found, via my own implementation, was that I perform some operations in OnBeginPrinting that need to be reversed in OnEndPrinting. Therefore, I found that I need to call OnEndPrinting before destroying the PrintInfo class, etc. You will also need to declare this class as a "friend" to the AppView class or make OnEndPrinting a "public" function.
void CMultiPagePreviewView::OnLandscape()
{
.
.
.
int state = pButton->GetCheck() ; // portrait or landscape mode?
(OurAppView *)m_pPrintView)->OnEndPrinting(m_pPreviewDC, m_pPreviewInfo);
// get the current CPrintInfo object
CPrintInfo *pInfo = m_pPreviewInfo ;
m_pPreviewInfo = NULL ;
.
.
.
SetPrintView(m_pPrintView) ;
}
Eldon Zacek
VP of Engineering
Czech-Mate Enterprises, LLC
|
|
|
|

|
I have finished a program using MFC D/V. I used CStrollView class. But I can realize multipage printpreview for every page having the same text.
I have overload OnPreparDC function like this:
if (pDC->IsPrinting())
{int pageHeight = pDC->GetDeviceCaps(VERTRES);
int originY = pageHeight * (pInfo->m_nCurPage - 1);
pDC->SetViewportOrg(0, originY);
}
and in the OnPrint function like this to set mapmode:
pDC->SetMapMode(MM_ISOTROPIC);
pDC->SetWindowExt(70,70);
pDC->SetViewportExt(pDC->GetDeviceCaps (LOGPIXELSX), pDC->GetDeviceCaps(LOGPIXELSX));
willima
|
|
|
|

|
william_shen wrote:
But I can realize multipage printpreview for every page having the same text
This will not be a problem in OnPrepareDC() it will be the OnPrint(). This function needs to generate the correct output based on the value of pInfo->m_nCurPage which is the current page being printed. OnPrint() is called once by the MFC for every page of output generated when printing or previewing (everytime a page needs to be re-drawn). THis value is the only thing which tells you what output needs to be generated.
Roger Allen
Sonork 100.10016
This is a multiple choice question, choose wisely
Why did the hedgehog cross the road?
A: To show he had guts?
B: To see his flat mate?
|
|
|
|

|
I would like to retrieve the height and the width of the paper selected in
the CPrintDialog by the user.
When I display the CPrintDialog then if the user change the paper,
dmPaperLength and dmPaperWidth are not updated but dmFormName is updated.
dmPaperLength and dmPaperWidth are updated only if I reload the CPrintDialog and
press ok button again.
I remarq that dmpapersize is updated but how can I retrieve the height and the width
from dmpapersize??
Thank you,
Christophe from Belgium
This is my code :
//-------------------------------------------
int ret;
PRINTDLG PRT_DLG;
LPDEVMODE lpDevMode;
CPrintDialog pd( true,PD_ALLPAGES|PD_RETURNDC|PD_HIDEPRINTTOFILE,NULL);
ret = AfxGetApp()->DoPrintDialog(&pd);
if(ret == IDOK)
{
AfxGetApp()->GetPrinterDeviceDefaults(&PRT_DLG);
lpDevMode = (LPDEVMODE)::GlobalLock(PRT_DLG.hDevMode);
if(lpDevMode != NULL)
{
CString str2;
m_paperHeight.cm = (float)(lpDevMode->dmPaperLength/100) ;
m_paperHeight.inches = (lpDevMode->dmPaperLength/100) * (float)0.39;
m_paperWidth.cm =(float) (lpDevMode->dmPaperWidth/100) ;
m_paperWidth.inches = (lpDevMode->dmPaperWidth/100) * (float)0.39;
CEdit * ptre=(CEdit *) GetDlgItem(IDC_EDIT14);
ptre->SetWindowText(( char*) lpDevMode->dmFormName);
initWidthHeightofPaper();
::GlobalUnlock(PRT_DLG.hDevMode);
}
}
//--------------------------------------------
|
|
|
|

|
I have a multi-document application linking a doc/view DLL. The code works great except the OnLandscape() function.
What I want to do is to preview doc in the DLL. In the code you provided, we need get an object of the CMultiPagePrintApp by using AfxGetApp() in OnLandscape(). I could not figure out how to do this in the DLL. When linking the DLL, SetPrintOrientation(int) could not be resolved. Hope you understand my question and kindly provide a solution.
Thanks a lot.
Lubin
|
|
|
|

|
I recently cam back to this and found this solution for those of you who need to do this:
bool CMultiPagePreviewView::SetPrintOrientation(int mode) const
{
PRINTDLG pd;
pd.lStructSize = (DWORD)sizeof(PRINTDLG);
BOOL bRet = AfxGetApp()->GetPrinterDeviceDefaults(&pd);
if (bRet)
{
switch (mode)
{
case DMORIENT_PORTRAIT :
{
LPDEVMODE pDevMode = (LPDEVMODE)::GlobalLock(pd.hDevMode) ;
pDevMode->dmOrientation = DMORIENT_PORTRAIT ;
::GlobalUnlock(pd.hDevMode) ;
}
break ;
case DMORIENT_LANDSCAPE :
{
LPDEVMODE pDevMode = (LPDEVMODE)::GlobalLock(pd.hDevMode) ;
pDevMode->dmOrientation = DMORIENT_LANDSCAPE ;
::GlobalUnlock(pd.hDevMode) ;
}
break ;
default :
ASSERT(FALSE) ; return false ;
}
return true ;
}
return false;
}
This avoids all the requirement of having functions as part of the CWinApp derived class
Roger Allen - Sonork 100.10016
Strong Sad: I am sad I am flying
Who is your favorite Strong?
|
|
|
|

|
You must override the OnDraw function from the CMultiPagePreviewView class and there should be this code into it to avoid the blank page at the end of the document:
//Set the number of displayed pages to avoid MFC to display a blank page at the end...
int OldnPages=m_nPages;
m_nPages=min(m_nPages,max(1,m_pPreviewInfo->GetMaxPage()-m_nCurrentPage+1));
CPreviewView::OnDraw(pDC);
m_nPages=OldnPages;
Mulot
|
|
|
|
|

|
I tried this class in an rtf application. When I get to:
if (!pView->Create(NULL, NULL, AFX_WS_DEFAULT_VIEW,
CRect(0,0,0,0), pParent, AFX_IDW_PANE_FIRST, &context))
The app crashes. Any suggestions as to what might be wrong would be appreciated.
|
|
|
|
 |
|
|
General News Suggestion Question Bug Answer Joke Rant Admin
|
How to improve the standard MFC print preview options to allow preview of from 1 to 9 pages at a time
| Type | Article |
| Licence | CPOL |
| First Posted | 23 Apr 2002 |
| Views | 121,196 |
| Bookmarked | 30 times |
|
|