Enables the configuration of headers and footers, via 6 string in the nsIPrintOptions

3 for the header and 3 for the footer.
The new codes are &T,&U,&D,&P,&PT (see bug for explanation)
Bug 99415 r=kmcclusk, sr=attinasi a=pdt
This commit is contained in:
rods%netscape.com 2001-09-26 14:01:26 +00:00
parent 4350e45c02
commit f90b35f264
11 changed files with 920 additions and 281 deletions

View File

@ -63,12 +63,7 @@ interface nsIPrintOptions : nsISupports
/* Print Option Flags for Bit Field*/
const long kOptPrintOddPages = 0x00000001;
const long kOptPrintEvenPages = 0x00000002;
const long kOptPrintDocTitle = 0x00000004;
const long kOptPrintDocLoc = 0x00000008;
const long kOptPrintPageNums = 0x00000010;
const long kOptPrintPageTotal = 0x00000020;
const long kOptPrintDatePrinted = 0x00000040;
const long kPrintOptionsEnableSelectionRB = 0x00000080;
const long kPrintOptionsEnableSelectionRB = 0x00000004;
/* Print Range Enums */
const long kRangeAllPages = 0;
@ -151,10 +146,18 @@ interface nsIPrintOptions : nsISupports
attribute double marginRight;
attribute short printRange;
attribute short pageNumJust;
attribute wstring title;
attribute wstring docURL;
attribute wstring headerStrLeft;
attribute wstring headerStrCenter;
attribute wstring headerStrRight;
attribute wstring footerStrLeft;
attribute wstring footerStrCenter;
attribute wstring footerStrRight;
attribute short howToEnableFrameUI;
attribute short printFrameType;
attribute boolean isCancelled;

View File

@ -1,4 +1,4 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: NPL 1.1/GPL 2.0/LGPL 2.1
*
@ -16,7 +16,7 @@
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 1998
* Portions created by the Initial Developer are Copyright (C) 2000
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
@ -77,12 +77,12 @@ const char * kMarginRight = "print.print_margin_right";
// Prefs for Print Options
const char * kPrintEvenPages = "print.print_evenpages";
const char * kPrintOddPages = "print.print_oddpages";
const char * kPrintDocTitle = "print.print_doctitle";
const char * kPrintDocLoc = "print.print_doclocation";
const char * kPageNums = "print.print_pagenumbers";
const char * kPageNumsJust = "print.print_pagenumjust";
const char * kPrintPageTotals = "print.print_pagetotals";
const char * kPrintDate = "print.print_date";
const char * kPrintHeaderStr1 = "print.print_headerleft";
const char * kPrintHeaderStr2 = "print.print_headercenter";
const char * kPrintHeaderStr3 = "print.print_headerright";
const char * kPrintFooterStr1 = "print.print_footerleft";
const char * kPrintFooterStr2 = "print.print_footercenter";
const char * kPrintFooterStr3 = "print.print_footerright";
// Additional Prefs
const char * kPrintReversed = "print.print_reversed";
@ -105,7 +105,7 @@ const char * kLeftJust = "left";
const char * kCenterJust = "center";
const char * kRightJust = "right";
#define form_properties "chrome://communicator/locale/printing.properties"
nsFont* nsPrintOptions::mDefaultFont = nsnull;
/** ---------------------------------------------------
* See documentation in nsPrintOptionsImpl.h
@ -123,7 +123,6 @@ nsPrintOptions::nsPrintOptions() :
mPrintToFile(PR_FALSE),
mPrintFrameType(kFramesAsIs),
mHowToEnableFrameUI(kFrameEnableNone),
mPageNumJust(kJustLeft),
mIsCancelled(PR_FALSE),
mPrintPageDelay(500),
mPrintSilent(PR_FALSE)
@ -134,18 +133,21 @@ nsPrintOptions::nsPrintOptions() :
nscoord halfInch = NS_INCHES_TO_TWIPS(0.5);
mMargin.SizeTo(halfInch, halfInch, halfInch, halfInch);
mPrintOptions = kOptPrintOddPages |
kOptPrintEvenPages |
kOptPrintDocTitle |
kOptPrintDocLoc |
kOptPrintPageNums |
kOptPrintPageTotal |
kOptPrintDatePrinted;
mPrintOptions = kOptPrintOddPages | kOptPrintEvenPages;
mDefaultFont = new nsFont("Times", NS_FONT_STYLE_NORMAL,NS_FONT_VARIANT_NORMAL,
NS_FONT_WEIGHT_NORMAL,0,NSIntPointsToTwips(10));
if (mDefaultFont == nsnull) {
mDefaultFont = new nsFont("Times", NS_FONT_STYLE_NORMAL,NS_FONT_VARIANT_NORMAL,
NS_FONT_WEIGHT_NORMAL,0,NSIntPointsToTwips(10));
}
mHeaderStrs[0].AssignWithConversion("&T");
mHeaderStrs[2].AssignWithConversion("&U");
mFooterStrs[0].AssignWithConversion("&P"); // Use &P (Page Num Only) or &PT (Page Num of Page Total)
mFooterStrs[2].AssignWithConversion("&D");
ReadPrefs();
}
/** ---------------------------------------------------
@ -156,6 +158,7 @@ nsPrintOptions::~nsPrintOptions()
{
if (mDefaultFont != nsnull) {
delete mDefaultFont;
mDefaultFont = nsnull;
}
}
@ -288,13 +291,13 @@ nsPrintOptions::ReadPrefs()
ReadBitFieldPref(prefs, kPrintEvenPages, kOptPrintEvenPages);
ReadBitFieldPref(prefs, kPrintOddPages, kOptPrintOddPages);
ReadBitFieldPref(prefs, kPrintDocTitle, kOptPrintDocTitle);
ReadBitFieldPref(prefs, kPrintDocLoc, kOptPrintDocLoc);
ReadBitFieldPref(prefs, kPageNums, kOptPrintPageNums);
ReadBitFieldPref(prefs, kPrintPageTotals, kOptPrintPageTotal);
ReadBitFieldPref(prefs, kPrintDate, kOptPrintDatePrinted);
ReadJustification(prefs, kPageNumsJust, mPageNumJust, kJustLeft);
ReadPrefString(prefs, kPrintHeaderStr1, mHeaderStrs[0]);
ReadPrefString(prefs, kPrintHeaderStr2, mHeaderStrs[1]);
ReadPrefString(prefs, kPrintHeaderStr3, mHeaderStrs[2]);
ReadPrefString(prefs, kPrintFooterStr1, mFooterStrs[0]);
ReadPrefString(prefs, kPrintFooterStr2, mFooterStrs[1]);
ReadPrefString(prefs, kPrintFooterStr3, mFooterStrs[2]);
// Read Additional XP Prefs
prefs->GetBoolPref(kPrintReversed, &mPrintReversed);
@ -327,13 +330,13 @@ nsPrintOptions::WritePrefs()
WriteBitFieldPref(prefs, kPrintEvenPages, kOptPrintEvenPages);
WriteBitFieldPref(prefs, kPrintOddPages, kOptPrintOddPages);
WriteBitFieldPref(prefs, kPrintDocTitle, kOptPrintDocTitle);
WriteBitFieldPref(prefs, kPrintDocLoc, kOptPrintDocLoc);
WriteBitFieldPref(prefs, kPageNums, kOptPrintPageNums);
WriteBitFieldPref(prefs, kPrintPageTotals, kOptPrintPageTotal);
WriteBitFieldPref(prefs, kPrintDate, kOptPrintDatePrinted);
WriteJustification(prefs, kPageNumsJust, mPageNumJust);
WritePrefString(prefs, kPrintHeaderStr1, mHeaderStrs[0]);
WritePrefString(prefs, kPrintHeaderStr2, mHeaderStrs[1]);
WritePrefString(prefs, kPrintHeaderStr3, mHeaderStrs[2]);
WritePrefString(prefs, kPrintFooterStr1, mFooterStrs[0]);
WritePrefString(prefs, kPrintFooterStr2, mFooterStrs[1]);
WritePrefString(prefs, kPrintFooterStr3, mFooterStrs[2]);
// Write Additional XP Prefs
prefs->SetBoolPref(kPrintReversed, mPrintReversed);
@ -544,19 +547,6 @@ NS_IMETHODIMP nsPrintOptions::SetPrintRange(PRInt16 aPrintRange)
return NS_OK;
}
/* attribute long pageNumJust; */
NS_IMETHODIMP nsPrintOptions::GetPageNumJust(PRInt16 *aPageNumJust)
{
NS_ENSURE_ARG_POINTER(aPageNumJust);
*aPageNumJust = mPageNumJust;
return NS_OK;
}
NS_IMETHODIMP nsPrintOptions::SetPageNumJust(PRInt16 aPageNumJust)
{
mPageNumJust = aPageNumJust;
return NS_OK;
}
/* attribute wstring docTitle; */
NS_IMETHODIMP nsPrintOptions::GetTitle(PRUnichar * *aTitle)
{
@ -585,6 +575,114 @@ NS_IMETHODIMP nsPrintOptions::SetDocURL(const PRUnichar * aDocURL)
return NS_OK;
}
/* attribute wstring docTitle; */
nsresult
nsPrintOptions::GetMarginStrs(PRUnichar * *aTitle,
nsHeaderFooterEnum aType,
PRInt16 aJust)
{
NS_ENSURE_ARG_POINTER(aTitle);
*aTitle = nsnull;
if (aType == eHeader) {
switch (aJust) {
case kJustLeft: *aTitle = mHeaderStrs[0].ToNewUnicode();break;
case kJustCenter: *aTitle = mHeaderStrs[1].ToNewUnicode();break;
case kJustRight: *aTitle = mHeaderStrs[2].ToNewUnicode();break;
} //switch
} else {
switch (aJust) {
case kJustLeft: *aTitle = mFooterStrs[0].ToNewUnicode();break;
case kJustCenter: *aTitle = mFooterStrs[1].ToNewUnicode();break;
case kJustRight: *aTitle = mFooterStrs[2].ToNewUnicode();break;
} //switch
}
return NS_OK;
}
nsresult
nsPrintOptions::SetMarginStrs(const PRUnichar * aTitle,
nsHeaderFooterEnum aType,
PRInt16 aJust)
{
NS_ENSURE_ARG_POINTER(aTitle);
if (aType == eHeader) {
switch (aJust) {
case kJustLeft: mHeaderStrs[0] = aTitle;break;
case kJustCenter: mHeaderStrs[1] = aTitle;break;
case kJustRight: mHeaderStrs[2] = aTitle;break;
} //switch
} else {
switch (aJust) {
case kJustLeft: mFooterStrs[0] = aTitle;break;
case kJustCenter: mFooterStrs[1] = aTitle;break;
case kJustRight: mFooterStrs[2] = aTitle;break;
} //switch
}
return NS_OK;
}
/* attribute wstring Header String Left */
NS_IMETHODIMP nsPrintOptions::GetHeaderStrLeft(PRUnichar * *aTitle)
{
return GetMarginStrs(aTitle, eHeader, kJustLeft);
}
NS_IMETHODIMP nsPrintOptions::SetHeaderStrLeft(const PRUnichar * aTitle)
{
return SetMarginStrs(aTitle, eHeader, kJustLeft);
}
/* attribute wstring Header String Center */
NS_IMETHODIMP nsPrintOptions::GetHeaderStrCenter(PRUnichar * *aTitle)
{
return GetMarginStrs(aTitle, eHeader, kJustCenter);
}
NS_IMETHODIMP nsPrintOptions::SetHeaderStrCenter(const PRUnichar * aTitle)
{
return SetMarginStrs(aTitle, eHeader, kJustCenter);
}
/* attribute wstring Header String Right */
NS_IMETHODIMP nsPrintOptions::GetHeaderStrRight(PRUnichar * *aTitle)
{
return GetMarginStrs(aTitle, eHeader, kJustRight);
}
NS_IMETHODIMP nsPrintOptions::SetHeaderStrRight(const PRUnichar * aTitle)
{
return SetMarginStrs(aTitle, eHeader, kJustRight);
}
/* attribute wstring Footer String Left */
NS_IMETHODIMP nsPrintOptions::GetFooterStrLeft(PRUnichar * *aTitle)
{
return GetMarginStrs(aTitle, eFooter, kJustLeft);
}
NS_IMETHODIMP nsPrintOptions::SetFooterStrLeft(const PRUnichar * aTitle)
{
return SetMarginStrs(aTitle, eFooter, kJustLeft);
}
/* attribute wstring Footer String Center */
NS_IMETHODIMP nsPrintOptions::GetFooterStrCenter(PRUnichar * *aTitle)
{
return GetMarginStrs(aTitle, eFooter, kJustCenter);
}
NS_IMETHODIMP nsPrintOptions::SetFooterStrCenter(const PRUnichar * aTitle)
{
return SetMarginStrs(aTitle, eFooter, kJustCenter);
}
/* attribute wstring Footer String Right */
NS_IMETHODIMP nsPrintOptions::GetFooterStrRight(PRUnichar * *aTitle)
{
return GetMarginStrs(aTitle, eFooter, kJustRight);
}
NS_IMETHODIMP nsPrintOptions::SetFooterStrRight(const PRUnichar * aTitle)
{
return SetMarginStrs(aTitle, eFooter, kJustRight);
}
/* attribute boolean isPrintFrame; */
NS_IMETHODIMP nsPrintOptions::GetHowToEnableFrameUI(PRInt16 *aHowToEnableFrameUI)
{

View File

@ -50,6 +50,14 @@ protected:
nsresult ReadPrefString(nsIPref * aPref, const char * aPrefId, nsString& aString);
nsresult WritePrefString(nsIPref * aPref, const char * aPrefId, nsString& aString);
typedef enum {
eHeader,
eFooter
} nsHeaderFooterEnum;
nsresult GetMarginStrs(PRUnichar * *aTitle, nsHeaderFooterEnum aType, PRInt16 aJust);
nsresult SetMarginStrs(const PRUnichar * aTitle, nsHeaderFooterEnum aType, PRInt16 aJust);
// Members
nsMargin mMargin;
PRInt32 mPrintOptions;
@ -58,7 +66,6 @@ protected:
PRInt16 mPrintRange;
PRInt32 mStartPageNum; // only used for ePrintRange_SpecifiedRange
PRInt32 mEndPageNum;
PRInt16 mPageNumJust;
PRInt16 mPrintFrameType;
PRBool mHowToEnableFrameUI;
@ -66,9 +73,11 @@ protected:
PRBool mPrintSilent;
PRInt32 mPrintPageDelay;
nsFont* mDefaultFont;
nsString mTitle;
nsString mURL;
nsString mPageNumberFormat;
nsString mHeaderStrs[3];
nsString mFooterStrs[3];
PRBool mPrintReversed;
PRBool mPrintInColor; // a false means grayscale
@ -78,6 +87,7 @@ protected:
PRBool mPrintToFile;
nsString mToFileName;
static nsFont* mDefaultFont;
};

View File

@ -36,22 +36,20 @@
// for page number localization formatting
#include "nsTextFormatter.h"
// DateTime Includes
#include "nsDateTimeFormatCID.h"
#include "nsIDateTimeFormat.h"
#include "nsIServiceManager.h"
#include "nsILocale.h"
#include "nsLocaleCID.h"
#include "nsILocaleService.h"
static NS_DEFINE_CID(kDateTimeFormatCID, NS_DATETIMEFORMAT_CID);
static NS_DEFINE_CID(kLocaleServiceCID, NS_LOCALESERVICE_CID);
// Temporary
#include "nsIFontMetrics.h"
// tstaic data members
// Print Options
#include "nsIPrintOptions.h"
#include "nsGfxCIID.h"
#include "nsIServiceManager.h"
static NS_DEFINE_CID(kPrintOptionsCID, NS_PRINTOPTIONS_CID);
// static data members
PRUnichar * nsPageFrame::mDateTimeStr = nsnull;
nsFont * nsPageFrame::mHeadFootFont = nsnull;
PRUnichar * nsPageFrame::mPageNumFormat = nsnull;
PRUnichar * nsPageFrame::mPageNumAndTotalsFormat = nsnull;
#if defined(DEBUG_rods) || defined(DEBUG_dcone)
#define DEBUG_PRINTING
@ -87,7 +85,6 @@ NS_NewPageFrame(nsIPresShell* aPresShell, nsIFrame** aNewFrame)
}
nsPageFrame::nsPageFrame() :
mHeadFootFont(nsnull),
mSupressHF(PR_FALSE),
mClipRect(-1, -1, -1, -1)
@ -95,17 +92,38 @@ nsPageFrame::nsPageFrame() :
#ifdef NS_DEBUG
mDebugFD = stdout;
#endif
nsresult rv;
mPrintOptions = do_GetService(kPrintOptionsCID, &rv);
if (mHeadFootFont == nsnull) {
mHeadFootFont = new nsFont("serif", NS_FONT_STYLE_NORMAL,NS_FONT_VARIANT_NORMAL,
NS_FONT_WEIGHT_NORMAL,0,NSIntPointsToTwips(10));
}
// now get the default font form the print options
mPrintOptions->GetDefaultFont(*mHeadFootFont);
}
nsPageFrame::~nsPageFrame()
{
if (mHeadFootFont)
if (mHeadFootFont != nsnull) {
delete mHeadFootFont;
mHeadFootFont = nsnull;
}
if (mDateTimeStr) {
nsMemory::Free(mDateTimeStr);
mDateTimeStr = nsnull;
}
if (mPageNumFormat) {
nsMemory::Free(mPageNumFormat);
mPageNumFormat = nsnull;
}
if (mPageNumAndTotalsFormat) {
nsMemory::Free(mPageNumAndTotalsFormat);
mPageNumAndTotalsFormat = nsnull;
}
}
NS_METHOD nsPageFrame::Reflow(nsIPresContext* aPresContext,
@ -235,6 +253,116 @@ nsPageFrame::IsPercentageBase(PRBool& aBase) const
return NS_OK;
}
//------------------------------------------------------------------------------
// helper function for converting from char * to unichar
static PRUnichar *
GetUStr(const char * aCStr)
{
nsAutoString str;
str.AssignWithConversion(aCStr);
return str.ToNewUnicode();
}
// replace the &<code> with the value, but if the value is empty
// set the string to zero length
static void
SubstValueForCode(nsString& aStr, const PRUnichar * aUKey, const PRUnichar * aUStr)
{
nsAutoString str;
str = aUStr;
if (str.Length() == 0) {
aStr.SetLength(0);
} else {
aStr.ReplaceSubstring(aUKey, aUStr);
}
}
// done with static helper functions
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
void
nsPageFrame::ProcessSpecialCodes(const nsString& aStr, nsString& aNewStr)
{
aNewStr = aStr;
// Search to see if the &D code is in the string
// then subst in the current date/time
PRUnichar * kDate = GetUStr("&D");
if (kDate != nsnull) {
if (aStr.Find(kDate) > -1) {
if (mDateTimeStr != nsnull) {
aNewStr.ReplaceSubstring(kDate, mDateTimeStr);
} else {
nsAutoString empty;
PRUnichar * uEmpty = empty.ToNewUnicode();
aNewStr.ReplaceSubstring(kDate, uEmpty);
nsMemory::Free(uEmpty);
}
nsMemory::Free(kDate);
return;
}
nsMemory::Free(kDate);
}
// NOTE: Must search for &PT before searching for &P
//
// Search to see if the "page number and page" total code are in the string
// and replace the page number and page total code with the actual values
PRUnichar * kPage = GetUStr("&PT");
if (kPage != nsnull) {
if (aStr.Find(kPage) > -1) {
PRUnichar * uStr = nsTextFormatter::smprintf(mPageNumAndTotalsFormat, mPageNum, mTotNumPages);
aNewStr.ReplaceSubstring(kPage, uStr);
nsMemory::Free(uStr);
nsMemory::Free(kPage);
return;
}
nsMemory::Free(kPage);
}
// Search to see if the page number code is in the string
// and replace the page number code with the actual values
kPage = GetUStr("&P");
if (kPage != nsnull) {
if (aStr.Find(kPage) > -1) {
PRUnichar * uStr = nsTextFormatter::smprintf(mPageNumFormat, mPageNum);
aNewStr.ReplaceSubstring(kPage, uStr);
nsMemory::Free(uStr);
nsMemory::Free(kPage);
return;
}
nsMemory::Free(kPage);
}
PRUnichar * kTitle = GetUStr("&T");
if (kTitle != nsnull) {
if (aStr.Find(kTitle) > -1) {
PRUnichar * uTitle;
mPrintOptions->GetTitle(&uTitle); // creates memory
SubstValueForCode(aNewStr, kTitle, uTitle);
nsMemory::Free(uTitle);
nsMemory::Free(kTitle);
return;
}
nsMemory::Free(kTitle);
}
PRUnichar * kDocURL = GetUStr("&U");
if (kDocURL != nsnull) {
if (aStr.Find(kDocURL) > -1) {
PRUnichar * uDocURL;
mPrintOptions->GetDocURL(&uDocURL); // creates memory
SubstValueForCode(aNewStr, kDocURL, uDocURL);
nsMemory::Free(uDocURL);
nsMemory::Free(kDocURL);
return;
}
nsMemory::Free(kDocURL);
}
}
//------------------------------------------------------------------------------
nscoord nsPageFrame::GetXPosition(nsIRenderingContext& aRenderingContext,
const nsRect& aRect,
@ -273,6 +401,45 @@ nscoord nsPageFrame::GetXPosition(nsIRenderingContext& aRenderingContext,
// @parm aUseHalfThePage - indicates whether the text should limited to the width
// of the entire page or just half the page
void
nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
nsIFrame * aFrame,
nsHeaderFooterEnum aHeaderFooter,
PRInt32 aJust,
const nsString& aStr1,
const nsString& aStr2,
const nsString& aStr3,
const nsRect& aRect,
nscoord aHeight)
{
PRInt32 numStrs = 0;
if (!aStr1.IsEmpty()) numStrs++;
if (!aStr2.IsEmpty()) numStrs++;
if (!aStr3.IsEmpty()) numStrs++;
nscoord strSpace = aRect.width / numStrs;
if (numStrs == 0) return;
if (!aStr1.IsEmpty()) {
DrawHeaderFooter(aRenderingContext, aFrame, aHeaderFooter, nsIPrintOptions::kJustLeft, aStr1, aRect, aHeight, strSpace);
}
if (!aStr2.IsEmpty()) {
DrawHeaderFooter(aRenderingContext, aFrame, aHeaderFooter, nsIPrintOptions::kJustCenter, aStr2, aRect, aHeight, strSpace);
}
if (!aStr3.IsEmpty()) {
DrawHeaderFooter(aRenderingContext, aFrame, aHeaderFooter, nsIPrintOptions::kJustRight, aStr3, aRect, aHeight, strSpace);
}
}
//------------------------------------------------------------------------------
// Draw a Header or footer text lrft,right or center justified
// @parm aRenderingContext - rendering content ot draw into
// @parm aHeaderFooter - indicates whether it is a header or footer
// @parm aJust - indicates the justification of the text
// @parm aStr - The string to be drawn
// @parm aRect - the rect of the page
// @parm aHeight - the height of the text
// @parm aWidth - available width for any one of the strings
void
nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
nsIFrame * aFrame,
nsHeaderFooterEnum aHeaderFooter,
@ -280,7 +447,7 @@ nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
const nsString& aStr,
const nsRect& aRect,
nscoord aHeight,
PRBool aUseHalfThePage)
nscoord aWidth)
{
// first make sure we have a vaild string and that the height of the
@ -289,16 +456,15 @@ nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
((aHeaderFooter == eHeader && aHeight < mMargin.top) ||
(aHeaderFooter == eFooter && aHeight < mMargin.bottom))) {
// measure the width of the text
nsString str = aStr;
nsAutoString str;
ProcessSpecialCodes(aStr, str);
PRInt32 width;
aRenderingContext.GetWidth(str, width);
PRBool addEllipse = PR_FALSE;
nscoord halfWidth = aRect.width;
if (aUseHalfThePage) {
halfWidth /= 2;
}
// trim the text and add the elipses if it won't fit
while (width >= halfWidth && str.Length() > 1) {
while (width >= aWidth && str.Length() > 1) {
str.SetLength(str.Length()-1);
aRenderingContext.GetWidth(str, width);
addEllipse = PR_TRUE;
@ -347,8 +513,7 @@ nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
PRINT_DEBUG_MSG2(" HF: %s ", aHeaderFooter==eHeader?"Header":"Footer");
PRINT_DEBUG_MSG2(" JST: %s ", justStr);
PRINT_DEBUG_MSG3(" x,y: %d,%d", x, y);
PRINT_DEBUG_MSG2(" Hgt: %d ", aHeight);
PRINT_DEBUG_MSG2(" Half: %s\n", aUseHalfThePage?"Yes":"No");
PRINT_DEBUG_MSG2(" Hgt: %d \n", aHeight);
#endif
}
}
@ -362,6 +527,9 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
PRUint32 aFlags)
{
aRenderingContext.PushState();
aRenderingContext.SetColor(NS_RGB(255,255,255));
nsRect rect;
PRBool clipEmpty;
if (mClipRect.width != -1 || mClipRect.height != -1) {
#ifdef DEBUG_PRINTING
@ -372,6 +540,16 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
mClipRect.x = 0;
mClipRect.y = 0;
aRenderingContext.SetClipRect(mClipRect, nsClipCombine_kReplace, clipEmpty);
rect = mClipRect;
} else {
rect = mRect;
}
if (NS_FRAME_PAINT_LAYER_BACKGROUND == aWhichLayer) {
aRenderingContext.SetColor(NS_RGB(255,255,255));
rect.x = 0;
rect.y = 0;
aRenderingContext.FillRect(rect);
}
nsresult rv = nsContainerFrame::Paint(aPresContext, aRenderingContext, aDirtyRect, aWhichLayer);
@ -388,7 +566,7 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
// get the current margin
mPrintOptions->GetMarginInTwips(mMargin);
nsRect rect(0,0,mRect.width, mRect.height);
nsRect rect(0,0,mRect.width, mRect.height);
#if defined(DEBUG_rods) || defined(DEBUG_dcone)
// XXX Paint a one-pixel border around the page so it's easy to see where
@ -401,10 +579,11 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
rect.Inflate(NSToCoordRound(p2t), NSToCoordRound(p2t));
fprintf(mDebugFD, "PageFr::PaintChild -> Painting Frame %p Page No: %d\n", this, mPageNum);
#endif
// use the whole page
rect.width += mMargin.left + mMargin.right;
rect.x -= mMargin.left;
aRenderingContext.SetFont(*mHeadFootFont);
aRenderingContext.SetColor(NS_RGB(0,0,0));
@ -419,76 +598,25 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
fontMet->GetHeight(visibleHeight);
}
// get the print options bits so we can figure out all the
// the extra pieces of text that need to be drawn
PRInt32 printOptBits;
mPrintOptions->GetPrintOptionsBits(&printOptBits);
// print document headers and footers
PRUnichar * headers[3];
mPrintOptions->GetHeaderStrLeft(&headers[0]); // creates memory
mPrintOptions->GetHeaderStrCenter(&headers[1]); // creates memory
mPrintOptions->GetHeaderStrRight(&headers[2]); // creates memory
DrawHeaderFooter(aRenderingContext, this, eHeader, nsIPrintOptions::kJustLeft,
nsAutoString(headers[0]), nsAutoString(headers[1]), nsAutoString(headers[2]),
rect, visibleHeight);
PRInt32 i;
for (i=0;i<3;i++) nsMemory::Free(headers[i]);
// print page numbers
if (printOptBits & nsIPrintOptions::kOptPrintPageNums && mPageNumFormat != nsnull) {
PRInt16 justify = nsIPrintOptions::kJustLeft;
mPrintOptions->GetPageNumJust(&justify);
PRUnichar * valStr;
// print page number totals "x of x"
if (printOptBits & nsIPrintOptions::kOptPrintPageTotal) {
valStr = nsTextFormatter::smprintf(mPageNumFormat, mPageNum, mTotNumPages);
} else {
valStr = nsTextFormatter::smprintf(mPageNumFormat, mPageNum);
}
nsAutoString pageNoStr(valStr);
nsMemory::Free(valStr);
DrawHeaderFooter(aRenderingContext, this, eFooter, justify, pageNoStr, rect, visibleHeight);
}
// print localized date
if (printOptBits & nsIPrintOptions::kOptPrintDatePrinted) {
// Get Locale for Formating DateTime
nsCOMPtr<nsILocale> locale;
nsCOMPtr<nsILocaleService> localeSvc =
do_GetService(kLocaleServiceCID, &rv);
if (NS_SUCCEEDED(rv)) {
rv = localeSvc->GetApplicationLocale(getter_AddRefs(locale));
if (NS_SUCCEEDED(rv) && locale) {
nsCOMPtr<nsIDateTimeFormat> dateTime;
rv = nsComponentManager::CreateInstance(kDateTimeFormatCID,
NULL,
NS_GET_IID(nsIDateTimeFormat),
(void**) getter_AddRefs(dateTime));
if (NS_SUCCEEDED(rv)) {
nsAutoString dateString;
time_t ltime;
time( &ltime );
rv = dateTime->FormatTime(locale, kDateFormatShort, kTimeFormatNoSeconds, ltime, dateString);
if (NS_SUCCEEDED(rv)) {
DrawHeaderFooter(aRenderingContext, this, eFooter, nsIPrintOptions::kJustRight, dateString, rect, visibleHeight);
}
}
}
}
}
PRBool usingHalfThePage = (printOptBits & nsIPrintOptions::kOptPrintDocTitle) &&
(printOptBits & nsIPrintOptions::kOptPrintDocLoc);
// print document title
PRUnichar * title;
mPrintOptions->GetTitle(&title); // creates memory
if (title != nsnull && (printOptBits & nsIPrintOptions::kOptPrintDocTitle)) {
DrawHeaderFooter(aRenderingContext, this, eHeader, nsIPrintOptions::kJustLeft, nsAutoString(title), rect, visibleHeight, usingHalfThePage);
nsMemory::Free(title);
}
// print document URL
PRUnichar * url;
mPrintOptions->GetDocURL(&url);
if ((nsnull != url) && (printOptBits & nsIPrintOptions::kOptPrintDocLoc)) {
DrawHeaderFooter(aRenderingContext, this, eHeader, nsIPrintOptions::kJustRight, nsAutoString(url), rect, visibleHeight, usingHalfThePage);
nsMemory::Free(url);
}
PRUnichar * footers[3];
mPrintOptions->GetFooterStrLeft(&footers[0]); // creates memory
mPrintOptions->GetFooterStrCenter(&footers[1]); // creates memory
mPrintOptions->GetFooterStrRight(&footers[2]); // creates memory
DrawHeaderFooter(aRenderingContext, this, eFooter, nsIPrintOptions::kJustRight,
nsAutoString(footers[0]), nsAutoString(footers[1]), nsAutoString(footers[2]),
rect, visibleHeight);
for (i=0;i<3;i++) nsMemory::Free(footers[i]);
}
@ -521,12 +649,31 @@ nsPageFrame::SetPageNumInfo(PRInt32 aPageNumber, PRInt32 aTotalPages)
//------------------------------------------------------------------------------
void
nsPageFrame::SetPageNumberFormat(PRUnichar * aFormatStr)
nsPageFrame::SetPageNumberFormat(PRUnichar * aFormatStr, PRBool aForPageNumOnly)
{
NS_ASSERTION(aFormatStr != nsnull, "Format string cannot be null!");
if (mPageNumFormat != nsnull) {
nsMemory::Free(mPageNumFormat);
if (aForPageNumOnly) {
if (mPageNumFormat != nsnull) {
nsMemory::Free(mPageNumFormat);
}
mPageNumFormat = aFormatStr;
} else {
if (mPageNumAndTotalsFormat != nsnull) {
nsMemory::Free(mPageNumAndTotalsFormat);
}
mPageNumAndTotalsFormat = aFormatStr;
}
mPageNumFormat = aFormatStr;
}
//------------------------------------------------------------------------------
void
nsPageFrame::SetDateTimeStr(PRUnichar * aDateTimeStr)
{
NS_ASSERTION(aDateTimeStr != nsnull, "DateTime string cannot be null!");
if (mDateTimeStr != nsnull) {
nsMemory::Free(mDateTimeStr);
}
mDateTimeStr = aDateTimeStr;
}

View File

@ -71,8 +71,10 @@ public:
virtual void SuppressHeadersAndFooters(PRBool aDoSup) { mSupressHF = aDoSup; }
virtual void SetClipRect(nsRect* aClipRect) { mClipRect = *aClipRect; }
static void SetDateTimeStr(PRUnichar * aDateTimeStr);
// This is class is now responsible for freeing the memory
static void SetPageNumberFormat(PRUnichar * aFormatStr);
static void SetPageNumberFormat(PRUnichar * aFormatStr, PRBool aForPageNumOnly);
protected:
nsPageFrame();
@ -95,19 +97,32 @@ protected:
const nsString& sStr,
const nsRect& aRect,
nscoord aHeight,
PRBool aUseHalfThePage = PR_TRUE);
nscoord aWidth);
void DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
nsIFrame * aFrame,
nsHeaderFooterEnum aHeaderFooter,
PRInt32 aJust,
const nsString& aStr1,
const nsString& aStr2,
const nsString& aStr3,
const nsRect& aRect,
nscoord aHeight);
void ProcessSpecialCodes(const nsString& aStr, nsString& aNewStr);
nsCOMPtr<nsIPrintOptions> mPrintOptions;
PRInt32 mPageNum;
PRInt32 mTotNumPages;
nsMargin mMargin;
nsFont * mHeadFootFont;
PRPackedBool mSupressHF;
nsRect mClipRect;
static PRUnichar * mDateTimeStr;
static nsFont * mHeadFootFont;
static PRUnichar * mPageNumFormat;
static PRUnichar * mPageNumAndTotalsFormat;
};

View File

@ -35,6 +35,16 @@
#include "nsIPrintOptions.h"
#include "nsPageFrame.h"
// DateTime Includes
#include "nsDateTimeFormatCID.h"
#include "nsIDateTimeFormat.h"
#include "nsIServiceManager.h"
#include "nsILocale.h"
#include "nsLocaleCID.h"
#include "nsILocaleService.h"
static NS_DEFINE_CID(kDateTimeFormatCID, NS_DATETIMEFORMAT_CID);
static NS_DEFINE_CID(kLocaleServiceCID, NS_LOCALESERVICE_CID);
#define OFFSET_NOT_SET -1
// This is for localization of the "x of n" pages string
@ -364,6 +374,7 @@ nsSimplePageSequenceFrame::Reflow(nsIPresContext* aPresContext,
kidReflowState.mComputedWidth = kidReflowState.availableWidth;
//kidReflowState.mComputedHeight = kidReflowState.availableHeight;
PRINT_DEBUG_MSG3("AV W: %d H: %d\n", kidReflowState.availableWidth, kidReflowState.availableHeight);
// Place and size the page. If the page is narrower than our
// max width then center it horizontally
@ -403,6 +414,49 @@ nsSimplePageSequenceFrame::Reflow(nsIPresContext* aPresContext,
// Get the next page
kidFrame->GetNextSibling(&kidFrame);
}
// Get Total Page Count
nsIFrame* page;
PRInt32 pageTot = 0;
for (page = mFrames.FirstChild(); nsnull != page; page->GetNextSibling(&page)) {
pageTot++;
}
// Set Page Number Info
PRInt32 pageNum = 1;
for (page = mFrames.FirstChild(); nsnull != page; page->GetNextSibling(&page)) {
nsPageFrame * pf = NS_STATIC_CAST(nsPageFrame*, page);
if (pf != nsnull) {
//pf->SetPrintOptions(aPrintOptions);
pf->SetPageNumInfo(pageNum, pageTot);
}
pageNum++;
}
// Create current Date/Time String
nsresult rv;
nsCOMPtr<nsILocale> locale;
nsCOMPtr<nsILocaleService> localeSvc = do_GetService(kLocaleServiceCID, &rv);
if (NS_SUCCEEDED(rv)) {
rv = localeSvc->GetApplicationLocale(getter_AddRefs(locale));
if (NS_SUCCEEDED(rv) && locale) {
nsCOMPtr<nsIDateTimeFormat> dateTime;
rv = nsComponentManager::CreateInstance(kDateTimeFormatCID,
NULL,
NS_GET_IID(nsIDateTimeFormat),
(void**) getter_AddRefs(dateTime));
if (NS_SUCCEEDED(rv)) {
nsAutoString dateString;
time_t ltime;
time( &ltime );
if (NS_SUCCEEDED(dateTime->FormatTime(locale, kDateFormatShort, kTimeFormatNoSeconds, ltime, dateString))) {
PRUnichar * uStr = dateString.ToNewUnicode();
nsPageFrame::SetDateTimeStr(uStr); // nsPageFrame will own memory
}
}
}
}
}
// Return our desired size
@ -501,6 +555,30 @@ nsSimplePageSequenceFrame::GetPrintRange(PRInt32* aFromPage, PRInt32* aToPage)
return NS_OK;
}
// Helper Function
void
nsSimplePageSequenceFrame::SetPageNumberFormat(const char* aPropName, const char* aDefPropVal, PRBool aPageNumOnly)
{
// Doing this here so we only have to go get these formats once
nsAutoString pageNumberFormat;
// Now go get the Localized Page Formating String
nsAutoString propName;
propName.AssignWithConversion(aPropName);
PRUnichar* uPropName = propName.ToNewUnicode();
if (uPropName != nsnull) {
nsresult rv = nsFormControlHelper::GetLocalizedString(PRINTING_PROPERTIES, uPropName, pageNumberFormat);
if (NS_FAILED(rv)) { // back stop formatting
pageNumberFormat.AssignWithConversion(aDefPropVal);
}
nsMemory::Free(uPropName);
}
// Sets the format into a static data memeber which will own the memory and free it
PRUnichar* uStr = pageNumberFormat.ToNewUnicode();
if (uStr != nsnull) {
nsPageFrame::SetPageNumberFormat(uStr, aPageNumOnly); // nsPageFrame will own the memory
}
}
NS_IMETHODIMP
nsSimplePageSequenceFrame::StartPrint(nsIPresContext* aPresContext,
@ -649,19 +727,9 @@ nsSimplePageSequenceFrame::StartPrint(nsIPresContext* aPresContext,
}
aPrintOptions->SetFontNamePointSize(fontName, pointSize);
// Now go get the Localized Page Formating String
PRBool doingPageTotals = PR_TRUE;
aPrintOptions->GetPrintOptions(nsIPrintOptions::kOptPrintPageTotal, &doingPageTotals);
nsAutoString pageFormatStr;
rv = nsFormControlHelper::GetLocalizedString(PRINTING_PROPERTIES,
doingPageTotals? NS_LITERAL_STRING("pageofpages").get():NS_LITERAL_STRING("pagenumber").get(),
pageFormatStr);
if (NS_FAILED(rv)) { // back stop formatting
pageFormatStr.AssignWithConversion(doingPageTotals?"%ld of %ld":"%ld");
}
// Sets the format into a static data memeber which will own the memory and free it
nsPageFrame::SetPageNumberFormat(pageFormatStr.ToNewUnicode());
// Doing this here so we only have to go get these formats once
SetPageNumberFormat("pagenumber", "%1$d", PR_TRUE);
SetPageNumberFormat("pageofpages", "%1$d of %2$d", PR_FALSE);
mPageNum = 1;
mPrintedPageNum = 1;
@ -870,3 +938,29 @@ nsSimplePageSequenceFrame::SetDebugFD(FILE* aFD)
return NS_OK;
}
#endif
//------------------------------------------------------------------------------
NS_IMETHODIMP
nsSimplePageSequenceFrame::Paint(nsIPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
const nsRect& aDirtyRect,
nsFramePaintLayer aWhichLayer)
{
aRenderingContext.PushState();
aRenderingContext.SetColor(NS_RGB(255,255,255));
if (NS_FRAME_PAINT_LAYER_BACKGROUND == aWhichLayer) {
nsRect rect = mRect;
aRenderingContext.SetColor(NS_RGB(255,255,255));
rect.x = 0;
rect.y = 0;
aRenderingContext.FillRect(rect);
}
nsresult rv = nsContainerFrame::Paint(aPresContext, aRenderingContext, aDirtyRect, aWhichLayer);
PRBool clipEmpty;
aRenderingContext.PopState(clipEmpty);
return rv;
}

View File

@ -41,6 +41,11 @@ public:
const nsHTMLReflowState& aMaxSize,
nsReflowStatus& aStatus);
NS_IMETHOD Paint(nsIPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
const nsRect& aDirtyRect,
nsFramePaintLayer aWhichLayer);
// nsIPageSequenceFrame
NS_IMETHOD Print(nsIPresContext* aPresContext,
nsIPrintOptions* aPrintOptions,
@ -85,6 +90,9 @@ protected:
nsresult CreateContinuingPageFrame(nsIPresContext* aPresContext,
nsIFrame* aPageFrame,
nsIFrame** aContinuingFrame);
void SetPageNumberFormat(const char* aPropName, const char* aDefPropVal, PRBool aPageNumOnly);
NS_IMETHOD_(nsrefcnt) AddRef(void) {return nsContainerFrame::AddRef();}
NS_IMETHOD_(nsrefcnt) Release(void) {return nsContainerFrame::Release();}

View File

@ -36,22 +36,20 @@
// for page number localization formatting
#include "nsTextFormatter.h"
// DateTime Includes
#include "nsDateTimeFormatCID.h"
#include "nsIDateTimeFormat.h"
#include "nsIServiceManager.h"
#include "nsILocale.h"
#include "nsLocaleCID.h"
#include "nsILocaleService.h"
static NS_DEFINE_CID(kDateTimeFormatCID, NS_DATETIMEFORMAT_CID);
static NS_DEFINE_CID(kLocaleServiceCID, NS_LOCALESERVICE_CID);
// Temporary
#include "nsIFontMetrics.h"
// tstaic data members
// Print Options
#include "nsIPrintOptions.h"
#include "nsGfxCIID.h"
#include "nsIServiceManager.h"
static NS_DEFINE_CID(kPrintOptionsCID, NS_PRINTOPTIONS_CID);
// static data members
PRUnichar * nsPageFrame::mDateTimeStr = nsnull;
nsFont * nsPageFrame::mHeadFootFont = nsnull;
PRUnichar * nsPageFrame::mPageNumFormat = nsnull;
PRUnichar * nsPageFrame::mPageNumAndTotalsFormat = nsnull;
#if defined(DEBUG_rods) || defined(DEBUG_dcone)
#define DEBUG_PRINTING
@ -87,7 +85,6 @@ NS_NewPageFrame(nsIPresShell* aPresShell, nsIFrame** aNewFrame)
}
nsPageFrame::nsPageFrame() :
mHeadFootFont(nsnull),
mSupressHF(PR_FALSE),
mClipRect(-1, -1, -1, -1)
@ -95,17 +92,38 @@ nsPageFrame::nsPageFrame() :
#ifdef NS_DEBUG
mDebugFD = stdout;
#endif
nsresult rv;
mPrintOptions = do_GetService(kPrintOptionsCID, &rv);
if (mHeadFootFont == nsnull) {
mHeadFootFont = new nsFont("serif", NS_FONT_STYLE_NORMAL,NS_FONT_VARIANT_NORMAL,
NS_FONT_WEIGHT_NORMAL,0,NSIntPointsToTwips(10));
}
// now get the default font form the print options
mPrintOptions->GetDefaultFont(*mHeadFootFont);
}
nsPageFrame::~nsPageFrame()
{
if (mHeadFootFont)
if (mHeadFootFont != nsnull) {
delete mHeadFootFont;
mHeadFootFont = nsnull;
}
if (mDateTimeStr) {
nsMemory::Free(mDateTimeStr);
mDateTimeStr = nsnull;
}
if (mPageNumFormat) {
nsMemory::Free(mPageNumFormat);
mPageNumFormat = nsnull;
}
if (mPageNumAndTotalsFormat) {
nsMemory::Free(mPageNumAndTotalsFormat);
mPageNumAndTotalsFormat = nsnull;
}
}
NS_METHOD nsPageFrame::Reflow(nsIPresContext* aPresContext,
@ -235,6 +253,116 @@ nsPageFrame::IsPercentageBase(PRBool& aBase) const
return NS_OK;
}
//------------------------------------------------------------------------------
// helper function for converting from char * to unichar
static PRUnichar *
GetUStr(const char * aCStr)
{
nsAutoString str;
str.AssignWithConversion(aCStr);
return str.ToNewUnicode();
}
// replace the &<code> with the value, but if the value is empty
// set the string to zero length
static void
SubstValueForCode(nsString& aStr, const PRUnichar * aUKey, const PRUnichar * aUStr)
{
nsAutoString str;
str = aUStr;
if (str.Length() == 0) {
aStr.SetLength(0);
} else {
aStr.ReplaceSubstring(aUKey, aUStr);
}
}
// done with static helper functions
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
void
nsPageFrame::ProcessSpecialCodes(const nsString& aStr, nsString& aNewStr)
{
aNewStr = aStr;
// Search to see if the &D code is in the string
// then subst in the current date/time
PRUnichar * kDate = GetUStr("&D");
if (kDate != nsnull) {
if (aStr.Find(kDate) > -1) {
if (mDateTimeStr != nsnull) {
aNewStr.ReplaceSubstring(kDate, mDateTimeStr);
} else {
nsAutoString empty;
PRUnichar * uEmpty = empty.ToNewUnicode();
aNewStr.ReplaceSubstring(kDate, uEmpty);
nsMemory::Free(uEmpty);
}
nsMemory::Free(kDate);
return;
}
nsMemory::Free(kDate);
}
// NOTE: Must search for &PT before searching for &P
//
// Search to see if the "page number and page" total code are in the string
// and replace the page number and page total code with the actual values
PRUnichar * kPage = GetUStr("&PT");
if (kPage != nsnull) {
if (aStr.Find(kPage) > -1) {
PRUnichar * uStr = nsTextFormatter::smprintf(mPageNumAndTotalsFormat, mPageNum, mTotNumPages);
aNewStr.ReplaceSubstring(kPage, uStr);
nsMemory::Free(uStr);
nsMemory::Free(kPage);
return;
}
nsMemory::Free(kPage);
}
// Search to see if the page number code is in the string
// and replace the page number code with the actual values
kPage = GetUStr("&P");
if (kPage != nsnull) {
if (aStr.Find(kPage) > -1) {
PRUnichar * uStr = nsTextFormatter::smprintf(mPageNumFormat, mPageNum);
aNewStr.ReplaceSubstring(kPage, uStr);
nsMemory::Free(uStr);
nsMemory::Free(kPage);
return;
}
nsMemory::Free(kPage);
}
PRUnichar * kTitle = GetUStr("&T");
if (kTitle != nsnull) {
if (aStr.Find(kTitle) > -1) {
PRUnichar * uTitle;
mPrintOptions->GetTitle(&uTitle); // creates memory
SubstValueForCode(aNewStr, kTitle, uTitle);
nsMemory::Free(uTitle);
nsMemory::Free(kTitle);
return;
}
nsMemory::Free(kTitle);
}
PRUnichar * kDocURL = GetUStr("&U");
if (kDocURL != nsnull) {
if (aStr.Find(kDocURL) > -1) {
PRUnichar * uDocURL;
mPrintOptions->GetDocURL(&uDocURL); // creates memory
SubstValueForCode(aNewStr, kDocURL, uDocURL);
nsMemory::Free(uDocURL);
nsMemory::Free(kDocURL);
return;
}
nsMemory::Free(kDocURL);
}
}
//------------------------------------------------------------------------------
nscoord nsPageFrame::GetXPosition(nsIRenderingContext& aRenderingContext,
const nsRect& aRect,
@ -273,6 +401,45 @@ nscoord nsPageFrame::GetXPosition(nsIRenderingContext& aRenderingContext,
// @parm aUseHalfThePage - indicates whether the text should limited to the width
// of the entire page or just half the page
void
nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
nsIFrame * aFrame,
nsHeaderFooterEnum aHeaderFooter,
PRInt32 aJust,
const nsString& aStr1,
const nsString& aStr2,
const nsString& aStr3,
const nsRect& aRect,
nscoord aHeight)
{
PRInt32 numStrs = 0;
if (!aStr1.IsEmpty()) numStrs++;
if (!aStr2.IsEmpty()) numStrs++;
if (!aStr3.IsEmpty()) numStrs++;
nscoord strSpace = aRect.width / numStrs;
if (numStrs == 0) return;
if (!aStr1.IsEmpty()) {
DrawHeaderFooter(aRenderingContext, aFrame, aHeaderFooter, nsIPrintOptions::kJustLeft, aStr1, aRect, aHeight, strSpace);
}
if (!aStr2.IsEmpty()) {
DrawHeaderFooter(aRenderingContext, aFrame, aHeaderFooter, nsIPrintOptions::kJustCenter, aStr2, aRect, aHeight, strSpace);
}
if (!aStr3.IsEmpty()) {
DrawHeaderFooter(aRenderingContext, aFrame, aHeaderFooter, nsIPrintOptions::kJustRight, aStr3, aRect, aHeight, strSpace);
}
}
//------------------------------------------------------------------------------
// Draw a Header or footer text lrft,right or center justified
// @parm aRenderingContext - rendering content ot draw into
// @parm aHeaderFooter - indicates whether it is a header or footer
// @parm aJust - indicates the justification of the text
// @parm aStr - The string to be drawn
// @parm aRect - the rect of the page
// @parm aHeight - the height of the text
// @parm aWidth - available width for any one of the strings
void
nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
nsIFrame * aFrame,
nsHeaderFooterEnum aHeaderFooter,
@ -280,7 +447,7 @@ nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
const nsString& aStr,
const nsRect& aRect,
nscoord aHeight,
PRBool aUseHalfThePage)
nscoord aWidth)
{
// first make sure we have a vaild string and that the height of the
@ -289,16 +456,15 @@ nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
((aHeaderFooter == eHeader && aHeight < mMargin.top) ||
(aHeaderFooter == eFooter && aHeight < mMargin.bottom))) {
// measure the width of the text
nsString str = aStr;
nsAutoString str;
ProcessSpecialCodes(aStr, str);
PRInt32 width;
aRenderingContext.GetWidth(str, width);
PRBool addEllipse = PR_FALSE;
nscoord halfWidth = aRect.width;
if (aUseHalfThePage) {
halfWidth /= 2;
}
// trim the text and add the elipses if it won't fit
while (width >= halfWidth && str.Length() > 1) {
while (width >= aWidth && str.Length() > 1) {
str.SetLength(str.Length()-1);
aRenderingContext.GetWidth(str, width);
addEllipse = PR_TRUE;
@ -347,8 +513,7 @@ nsPageFrame::DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
PRINT_DEBUG_MSG2(" HF: %s ", aHeaderFooter==eHeader?"Header":"Footer");
PRINT_DEBUG_MSG2(" JST: %s ", justStr);
PRINT_DEBUG_MSG3(" x,y: %d,%d", x, y);
PRINT_DEBUG_MSG2(" Hgt: %d ", aHeight);
PRINT_DEBUG_MSG2(" Half: %s\n", aUseHalfThePage?"Yes":"No");
PRINT_DEBUG_MSG2(" Hgt: %d \n", aHeight);
#endif
}
}
@ -362,6 +527,9 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
PRUint32 aFlags)
{
aRenderingContext.PushState();
aRenderingContext.SetColor(NS_RGB(255,255,255));
nsRect rect;
PRBool clipEmpty;
if (mClipRect.width != -1 || mClipRect.height != -1) {
#ifdef DEBUG_PRINTING
@ -372,6 +540,16 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
mClipRect.x = 0;
mClipRect.y = 0;
aRenderingContext.SetClipRect(mClipRect, nsClipCombine_kReplace, clipEmpty);
rect = mClipRect;
} else {
rect = mRect;
}
if (NS_FRAME_PAINT_LAYER_BACKGROUND == aWhichLayer) {
aRenderingContext.SetColor(NS_RGB(255,255,255));
rect.x = 0;
rect.y = 0;
aRenderingContext.FillRect(rect);
}
nsresult rv = nsContainerFrame::Paint(aPresContext, aRenderingContext, aDirtyRect, aWhichLayer);
@ -388,7 +566,7 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
// get the current margin
mPrintOptions->GetMarginInTwips(mMargin);
nsRect rect(0,0,mRect.width, mRect.height);
nsRect rect(0,0,mRect.width, mRect.height);
#if defined(DEBUG_rods) || defined(DEBUG_dcone)
// XXX Paint a one-pixel border around the page so it's easy to see where
@ -401,10 +579,11 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
rect.Inflate(NSToCoordRound(p2t), NSToCoordRound(p2t));
fprintf(mDebugFD, "PageFr::PaintChild -> Painting Frame %p Page No: %d\n", this, mPageNum);
#endif
// use the whole page
rect.width += mMargin.left + mMargin.right;
rect.x -= mMargin.left;
aRenderingContext.SetFont(*mHeadFootFont);
aRenderingContext.SetColor(NS_RGB(0,0,0));
@ -419,76 +598,25 @@ nsPageFrame::Paint(nsIPresContext* aPresContext,
fontMet->GetHeight(visibleHeight);
}
// get the print options bits so we can figure out all the
// the extra pieces of text that need to be drawn
PRInt32 printOptBits;
mPrintOptions->GetPrintOptionsBits(&printOptBits);
// print document headers and footers
PRUnichar * headers[3];
mPrintOptions->GetHeaderStrLeft(&headers[0]); // creates memory
mPrintOptions->GetHeaderStrCenter(&headers[1]); // creates memory
mPrintOptions->GetHeaderStrRight(&headers[2]); // creates memory
DrawHeaderFooter(aRenderingContext, this, eHeader, nsIPrintOptions::kJustLeft,
nsAutoString(headers[0]), nsAutoString(headers[1]), nsAutoString(headers[2]),
rect, visibleHeight);
PRInt32 i;
for (i=0;i<3;i++) nsMemory::Free(headers[i]);
// print page numbers
if (printOptBits & nsIPrintOptions::kOptPrintPageNums && mPageNumFormat != nsnull) {
PRInt16 justify = nsIPrintOptions::kJustLeft;
mPrintOptions->GetPageNumJust(&justify);
PRUnichar * valStr;
// print page number totals "x of x"
if (printOptBits & nsIPrintOptions::kOptPrintPageTotal) {
valStr = nsTextFormatter::smprintf(mPageNumFormat, mPageNum, mTotNumPages);
} else {
valStr = nsTextFormatter::smprintf(mPageNumFormat, mPageNum);
}
nsAutoString pageNoStr(valStr);
nsMemory::Free(valStr);
DrawHeaderFooter(aRenderingContext, this, eFooter, justify, pageNoStr, rect, visibleHeight);
}
// print localized date
if (printOptBits & nsIPrintOptions::kOptPrintDatePrinted) {
// Get Locale for Formating DateTime
nsCOMPtr<nsILocale> locale;
nsCOMPtr<nsILocaleService> localeSvc =
do_GetService(kLocaleServiceCID, &rv);
if (NS_SUCCEEDED(rv)) {
rv = localeSvc->GetApplicationLocale(getter_AddRefs(locale));
if (NS_SUCCEEDED(rv) && locale) {
nsCOMPtr<nsIDateTimeFormat> dateTime;
rv = nsComponentManager::CreateInstance(kDateTimeFormatCID,
NULL,
NS_GET_IID(nsIDateTimeFormat),
(void**) getter_AddRefs(dateTime));
if (NS_SUCCEEDED(rv)) {
nsAutoString dateString;
time_t ltime;
time( &ltime );
rv = dateTime->FormatTime(locale, kDateFormatShort, kTimeFormatNoSeconds, ltime, dateString);
if (NS_SUCCEEDED(rv)) {
DrawHeaderFooter(aRenderingContext, this, eFooter, nsIPrintOptions::kJustRight, dateString, rect, visibleHeight);
}
}
}
}
}
PRBool usingHalfThePage = (printOptBits & nsIPrintOptions::kOptPrintDocTitle) &&
(printOptBits & nsIPrintOptions::kOptPrintDocLoc);
// print document title
PRUnichar * title;
mPrintOptions->GetTitle(&title); // creates memory
if (title != nsnull && (printOptBits & nsIPrintOptions::kOptPrintDocTitle)) {
DrawHeaderFooter(aRenderingContext, this, eHeader, nsIPrintOptions::kJustLeft, nsAutoString(title), rect, visibleHeight, usingHalfThePage);
nsMemory::Free(title);
}
// print document URL
PRUnichar * url;
mPrintOptions->GetDocURL(&url);
if ((nsnull != url) && (printOptBits & nsIPrintOptions::kOptPrintDocLoc)) {
DrawHeaderFooter(aRenderingContext, this, eHeader, nsIPrintOptions::kJustRight, nsAutoString(url), rect, visibleHeight, usingHalfThePage);
nsMemory::Free(url);
}
PRUnichar * footers[3];
mPrintOptions->GetFooterStrLeft(&footers[0]); // creates memory
mPrintOptions->GetFooterStrCenter(&footers[1]); // creates memory
mPrintOptions->GetFooterStrRight(&footers[2]); // creates memory
DrawHeaderFooter(aRenderingContext, this, eFooter, nsIPrintOptions::kJustRight,
nsAutoString(footers[0]), nsAutoString(footers[1]), nsAutoString(footers[2]),
rect, visibleHeight);
for (i=0;i<3;i++) nsMemory::Free(footers[i]);
}
@ -521,12 +649,31 @@ nsPageFrame::SetPageNumInfo(PRInt32 aPageNumber, PRInt32 aTotalPages)
//------------------------------------------------------------------------------
void
nsPageFrame::SetPageNumberFormat(PRUnichar * aFormatStr)
nsPageFrame::SetPageNumberFormat(PRUnichar * aFormatStr, PRBool aForPageNumOnly)
{
NS_ASSERTION(aFormatStr != nsnull, "Format string cannot be null!");
if (mPageNumFormat != nsnull) {
nsMemory::Free(mPageNumFormat);
if (aForPageNumOnly) {
if (mPageNumFormat != nsnull) {
nsMemory::Free(mPageNumFormat);
}
mPageNumFormat = aFormatStr;
} else {
if (mPageNumAndTotalsFormat != nsnull) {
nsMemory::Free(mPageNumAndTotalsFormat);
}
mPageNumAndTotalsFormat = aFormatStr;
}
mPageNumFormat = aFormatStr;
}
//------------------------------------------------------------------------------
void
nsPageFrame::SetDateTimeStr(PRUnichar * aDateTimeStr)
{
NS_ASSERTION(aDateTimeStr != nsnull, "DateTime string cannot be null!");
if (mDateTimeStr != nsnull) {
nsMemory::Free(mDateTimeStr);
}
mDateTimeStr = aDateTimeStr;
}

View File

@ -71,8 +71,10 @@ public:
virtual void SuppressHeadersAndFooters(PRBool aDoSup) { mSupressHF = aDoSup; }
virtual void SetClipRect(nsRect* aClipRect) { mClipRect = *aClipRect; }
static void SetDateTimeStr(PRUnichar * aDateTimeStr);
// This is class is now responsible for freeing the memory
static void SetPageNumberFormat(PRUnichar * aFormatStr);
static void SetPageNumberFormat(PRUnichar * aFormatStr, PRBool aForPageNumOnly);
protected:
nsPageFrame();
@ -95,19 +97,32 @@ protected:
const nsString& sStr,
const nsRect& aRect,
nscoord aHeight,
PRBool aUseHalfThePage = PR_TRUE);
nscoord aWidth);
void DrawHeaderFooter(nsIRenderingContext& aRenderingContext,
nsIFrame * aFrame,
nsHeaderFooterEnum aHeaderFooter,
PRInt32 aJust,
const nsString& aStr1,
const nsString& aStr2,
const nsString& aStr3,
const nsRect& aRect,
nscoord aHeight);
void ProcessSpecialCodes(const nsString& aStr, nsString& aNewStr);
nsCOMPtr<nsIPrintOptions> mPrintOptions;
PRInt32 mPageNum;
PRInt32 mTotNumPages;
nsMargin mMargin;
nsFont * mHeadFootFont;
PRPackedBool mSupressHF;
nsRect mClipRect;
static PRUnichar * mDateTimeStr;
static nsFont * mHeadFootFont;
static PRUnichar * mPageNumFormat;
static PRUnichar * mPageNumAndTotalsFormat;
};

View File

@ -35,6 +35,16 @@
#include "nsIPrintOptions.h"
#include "nsPageFrame.h"
// DateTime Includes
#include "nsDateTimeFormatCID.h"
#include "nsIDateTimeFormat.h"
#include "nsIServiceManager.h"
#include "nsILocale.h"
#include "nsLocaleCID.h"
#include "nsILocaleService.h"
static NS_DEFINE_CID(kDateTimeFormatCID, NS_DATETIMEFORMAT_CID);
static NS_DEFINE_CID(kLocaleServiceCID, NS_LOCALESERVICE_CID);
#define OFFSET_NOT_SET -1
// This is for localization of the "x of n" pages string
@ -364,6 +374,7 @@ nsSimplePageSequenceFrame::Reflow(nsIPresContext* aPresContext,
kidReflowState.mComputedWidth = kidReflowState.availableWidth;
//kidReflowState.mComputedHeight = kidReflowState.availableHeight;
PRINT_DEBUG_MSG3("AV W: %d H: %d\n", kidReflowState.availableWidth, kidReflowState.availableHeight);
// Place and size the page. If the page is narrower than our
// max width then center it horizontally
@ -403,6 +414,49 @@ nsSimplePageSequenceFrame::Reflow(nsIPresContext* aPresContext,
// Get the next page
kidFrame->GetNextSibling(&kidFrame);
}
// Get Total Page Count
nsIFrame* page;
PRInt32 pageTot = 0;
for (page = mFrames.FirstChild(); nsnull != page; page->GetNextSibling(&page)) {
pageTot++;
}
// Set Page Number Info
PRInt32 pageNum = 1;
for (page = mFrames.FirstChild(); nsnull != page; page->GetNextSibling(&page)) {
nsPageFrame * pf = NS_STATIC_CAST(nsPageFrame*, page);
if (pf != nsnull) {
//pf->SetPrintOptions(aPrintOptions);
pf->SetPageNumInfo(pageNum, pageTot);
}
pageNum++;
}
// Create current Date/Time String
nsresult rv;
nsCOMPtr<nsILocale> locale;
nsCOMPtr<nsILocaleService> localeSvc = do_GetService(kLocaleServiceCID, &rv);
if (NS_SUCCEEDED(rv)) {
rv = localeSvc->GetApplicationLocale(getter_AddRefs(locale));
if (NS_SUCCEEDED(rv) && locale) {
nsCOMPtr<nsIDateTimeFormat> dateTime;
rv = nsComponentManager::CreateInstance(kDateTimeFormatCID,
NULL,
NS_GET_IID(nsIDateTimeFormat),
(void**) getter_AddRefs(dateTime));
if (NS_SUCCEEDED(rv)) {
nsAutoString dateString;
time_t ltime;
time( &ltime );
if (NS_SUCCEEDED(dateTime->FormatTime(locale, kDateFormatShort, kTimeFormatNoSeconds, ltime, dateString))) {
PRUnichar * uStr = dateString.ToNewUnicode();
nsPageFrame::SetDateTimeStr(uStr); // nsPageFrame will own memory
}
}
}
}
}
// Return our desired size
@ -501,6 +555,30 @@ nsSimplePageSequenceFrame::GetPrintRange(PRInt32* aFromPage, PRInt32* aToPage)
return NS_OK;
}
// Helper Function
void
nsSimplePageSequenceFrame::SetPageNumberFormat(const char* aPropName, const char* aDefPropVal, PRBool aPageNumOnly)
{
// Doing this here so we only have to go get these formats once
nsAutoString pageNumberFormat;
// Now go get the Localized Page Formating String
nsAutoString propName;
propName.AssignWithConversion(aPropName);
PRUnichar* uPropName = propName.ToNewUnicode();
if (uPropName != nsnull) {
nsresult rv = nsFormControlHelper::GetLocalizedString(PRINTING_PROPERTIES, uPropName, pageNumberFormat);
if (NS_FAILED(rv)) { // back stop formatting
pageNumberFormat.AssignWithConversion(aDefPropVal);
}
nsMemory::Free(uPropName);
}
// Sets the format into a static data memeber which will own the memory and free it
PRUnichar* uStr = pageNumberFormat.ToNewUnicode();
if (uStr != nsnull) {
nsPageFrame::SetPageNumberFormat(uStr, aPageNumOnly); // nsPageFrame will own the memory
}
}
NS_IMETHODIMP
nsSimplePageSequenceFrame::StartPrint(nsIPresContext* aPresContext,
@ -649,19 +727,9 @@ nsSimplePageSequenceFrame::StartPrint(nsIPresContext* aPresContext,
}
aPrintOptions->SetFontNamePointSize(fontName, pointSize);
// Now go get the Localized Page Formating String
PRBool doingPageTotals = PR_TRUE;
aPrintOptions->GetPrintOptions(nsIPrintOptions::kOptPrintPageTotal, &doingPageTotals);
nsAutoString pageFormatStr;
rv = nsFormControlHelper::GetLocalizedString(PRINTING_PROPERTIES,
doingPageTotals? NS_LITERAL_STRING("pageofpages").get():NS_LITERAL_STRING("pagenumber").get(),
pageFormatStr);
if (NS_FAILED(rv)) { // back stop formatting
pageFormatStr.AssignWithConversion(doingPageTotals?"%ld of %ld":"%ld");
}
// Sets the format into a static data memeber which will own the memory and free it
nsPageFrame::SetPageNumberFormat(pageFormatStr.ToNewUnicode());
// Doing this here so we only have to go get these formats once
SetPageNumberFormat("pagenumber", "%1$d", PR_TRUE);
SetPageNumberFormat("pageofpages", "%1$d of %2$d", PR_FALSE);
mPageNum = 1;
mPrintedPageNum = 1;
@ -870,3 +938,29 @@ nsSimplePageSequenceFrame::SetDebugFD(FILE* aFD)
return NS_OK;
}
#endif
//------------------------------------------------------------------------------
NS_IMETHODIMP
nsSimplePageSequenceFrame::Paint(nsIPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
const nsRect& aDirtyRect,
nsFramePaintLayer aWhichLayer)
{
aRenderingContext.PushState();
aRenderingContext.SetColor(NS_RGB(255,255,255));
if (NS_FRAME_PAINT_LAYER_BACKGROUND == aWhichLayer) {
nsRect rect = mRect;
aRenderingContext.SetColor(NS_RGB(255,255,255));
rect.x = 0;
rect.y = 0;
aRenderingContext.FillRect(rect);
}
nsresult rv = nsContainerFrame::Paint(aPresContext, aRenderingContext, aDirtyRect, aWhichLayer);
PRBool clipEmpty;
aRenderingContext.PopState(clipEmpty);
return rv;
}

View File

@ -41,6 +41,11 @@ public:
const nsHTMLReflowState& aMaxSize,
nsReflowStatus& aStatus);
NS_IMETHOD Paint(nsIPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
const nsRect& aDirtyRect,
nsFramePaintLayer aWhichLayer);
// nsIPageSequenceFrame
NS_IMETHOD Print(nsIPresContext* aPresContext,
nsIPrintOptions* aPrintOptions,
@ -85,6 +90,9 @@ protected:
nsresult CreateContinuingPageFrame(nsIPresContext* aPresContext,
nsIFrame* aPageFrame,
nsIFrame** aContinuingFrame);
void SetPageNumberFormat(const char* aPropName, const char* aDefPropVal, PRBool aPageNumOnly);
NS_IMETHOD_(nsrefcnt) AddRef(void) {return nsContainerFrame::AddRef();}
NS_IMETHOD_(nsrefcnt) Release(void) {return nsContainerFrame::Release();}