commonuisupport/grid/src/GRDLAY.CPP
changeset 0 2f259fa3e83a
equal deleted inserted replaced
-1:000000000000 0:2f259fa3e83a
       
     1 // Copyright (c) 1997-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 // The data members of the class CGridLay are as follows:-
       
    15 // iGridRange - the range of cells that define the grid boundary.
       
    16 // iVisibleRange - the range of cells within the grid that are visible
       
    17 // in the active window. iVisibleRange.iFrom is the cell reference
       
    18 // of the top left cell in the window with respect to iGridRange
       
    19 // (i.e not necessarily (1, 1)). iVisibleRange.iTo is the cell that is
       
    20 // partially visible at the bottom right of the window.
       
    21 // *iGridTable, *iGridImg - allows access to the data in these classes.
       
    22 // *iColumnWidthMap,*iRowHeightMap - pointers to an array of column/row heights/widths
       
    23 // 
       
    24 //
       
    25 
       
    26 #include <s32strm.h>
       
    27 #include "GRDSTD.H"
       
    28 #include "GRDMAP.H"
       
    29 #include "GRDPANIC.H"
       
    30 
       
    31 
       
    32 #define KRgbGridForeground			TRgb(0,0,0)			// Black
       
    33 #define KRgbGridBackground			TRgb(255,255,255)	// White
       
    34 #define KRgbGridLines				TRgb(170,170,170)	// Light Gray
       
    35 #define KRgbGridLabelSeparators		TRgb(0,0,0)
       
    36 
       
    37 
       
    38 RWriteStream& operator<<(RWriteStream& aStream,const TInt& aInt)
       
    39 	{
       
    40 	aStream.WriteInt32L(aInt);
       
    41 	return aStream;
       
    42 	}
       
    43 
       
    44 RReadStream& operator>>(RReadStream &aStream,TInt& aInt)
       
    45 	{
       
    46 	aInt = aStream.ReadInt32L();
       
    47 	return aStream;
       
    48 	}
       
    49 
       
    50 
       
    51 //
       
    52 // TGridColors class
       
    53 //
       
    54 EXPORT_C TGridColors::TGridColors() :
       
    55 	iForeground(KRgbGridForeground),
       
    56 	iBackground(KRgbGridBackground),
       
    57 	iLines(KRgbGridLines),
       
    58 	iLabelSeparators(KRgbGridLabelSeparators)
       
    59 /** Default constructor.
       
    60 
       
    61 Sets the colours to their default values: foreground colour to the RGB value 
       
    62 TRgb(0,0,0), background colour to the RGB value TRgb(255,255,255), the colour 
       
    63 of lines to the RGB value TRgb(170,170,170), and the colour of label separators 
       
    64 to the RGB value TRgb(0,0,0). */
       
    65 	{
       
    66 	}
       
    67 
       
    68 EXPORT_C TGridColors::TGridColors(TRgb aForeground, TRgb aBackground, TRgb aLines, TRgb aLabelSeparators) :
       
    69 	iForeground(aForeground),
       
    70 	iBackground(aBackground),
       
    71 	iLines(aLines),
       
    72 	iLabelSeparators(aLabelSeparators)
       
    73 /** Constructor setting the colour values.
       
    74 
       
    75 @param aForeground The foreground colour value.
       
    76 @param aBackground The background colour value.
       
    77 @param aLines The colour of lines.
       
    78 @param aLabelSeparators The colour of label separators. */
       
    79 	{
       
    80 	}
       
    81 
       
    82 
       
    83 // CGridLay stuff
       
    84 
       
    85 EXPORT_C CGridLay::CGridLay(MGraphicsDeviceMap* aGraphicsDeviceMap)
       
    86 	: iGraphicsDeviceMap(aGraphicsDeviceMap)
       
    87 /** Constructor taking an object that implements mapping between twips and device-specific 
       
    88 units.
       
    89 
       
    90 @param aGraphicsDeviceMap An object that implements the interface for mapping 
       
    91 between twips and device-specific units. Typically, this is a TZoomFactor 
       
    92 object. */
       
    93 	{
       
    94 	}
       
    95 
       
    96 LOCAL_C void CopyIntArrayL(const CArrayFix<TInt>* aSource,CArrayFix<TInt>*& aDest)
       
    97 	{
       
    98 	TInt count=aSource->Count();
       
    99 	aDest = new(ELeave) CArrayFixFlat<TInt>(Max(count,1));
       
   100 	for (TInt ii=0;ii<count;ii++)
       
   101 		aDest->AppendL((*aSource)[ii]);
       
   102 	}
       
   103 
       
   104 EXPORT_C void CGridLay::ConstructL(CGridLay* aGridLay,CGridImg* aGridImg)
       
   105 //
       
   106 // Constructs a partial gridLay object for printing with the same data as the passed object.
       
   107 // - Assumes the zoom factor has already been set
       
   108 // - New Sparse maps are created
       
   109 /** A second-phase constructor, taking an existing grid layout object, that constructs 
       
   110 a partial layout object for printing.
       
   111 
       
   112 The function assumes that the zoom factor has already been set.
       
   113 
       
   114 @param aGridLay Pointer to an existing grid layout object.
       
   115 @param aGridImg Pointer to an existing grid image object. */
       
   116 	{
       
   117 	iGridImg=aGridImg;
       
   118 	iGridTable=aGridLay->iGridTable;
       
   119 	iGridRange=aGridLay->iGridRange;
       
   120 	iColumnWidthMap = CSparseMap::NewL(aGridLay->iColumnWidthMap);
       
   121 	CopyIntArrayL(aGridLay->iHardRowPageBreaks,iHardRowPageBreaks);
       
   122 	CopyIntArrayL(aGridLay->iHardColumnPageBreaks,iHardColumnPageBreaks);
       
   123 	iPageSizeInTwips=aGridLay->iPageSizeInTwips;
       
   124 	iRowHeightMap = CSparseMap::NewL(aGridLay->iRowHeightMap);
       
   125 	RecalcPixelSparseMaps();
       
   126 	iFlags=aGridLay->iFlags;
       
   127 	if (IsPaginated())
       
   128 		{
       
   129 		ClearPagination();
       
   130 		PaginateL();
       
   131 		}
       
   132 	}
       
   133 
       
   134 EXPORT_C void CGridLay::ConstructL(const MGridTable *aGridTable,CGridImg *aGridImg,TInt aNoOfRows,TInt aNoOfCols)
       
   135 /** A second-phase constructor for constructing the object with definite row boundaries.
       
   136 
       
   137 @param aGridTable A pointer to the grid table.
       
   138 @param aGridImg Pointer to a grid image object.
       
   139 @param aNoOfRows The number of rows in the grid.
       
   140 @param aNoOfCols The number of columns in the grid. */
       
   141 	{
       
   142 	TRangeRef gridRange(0,0,aNoOfRows-1,aNoOfCols-1);
       
   143 	ConstructL(aGridTable,aGridImg,gridRange);
       
   144 	}
       
   145 
       
   146 EXPORT_C void CGridLay::ConstructL(const MGridTable *aGridTable,CGridImg *aGridImg,TInt aNoOfCols)
       
   147 /** A second-phase constructor for constructing the object with indefinite row 
       
   148 boundaries.
       
   149 
       
   150 @param aGridTable A pointer to the grid table.
       
   151 @param aGridImg Pointer to a grid image object.
       
   152 @param aNoOfCols The number of columns in the grid. */
       
   153 	{
       
   154 	SetIndefiniteRowBoundaries(ETrue);
       
   155 	TRangeRef gridRange(-KMaxTInt,0,KMaxTInt,aNoOfCols-1);
       
   156 	ConstructL(aGridTable,aGridImg,gridRange);
       
   157 	}
       
   158 
       
   159 void CGridLay::ConstructL(const MGridTable *aGridTable,CGridImg *aGridImg,const TRangeRef& aGridRange)
       
   160 // Initialization of member data in CGridLay
       
   161 	{
       
   162 	iGridTable = aGridTable;
       
   163 	iGridImg = aGridImg;
       
   164 	iGridRange = aGridRange;
       
   165 
       
   166 	iColumnWidthMap = CSparseMap::NewL();
       
   167 	iRowHeightMap = CSparseMap::NewL();
       
   168 	iHardRowPageBreaks = new(ELeave) CArrayFixFlat<TInt>(1);
       
   169 	iHardColumnPageBreaks = new(ELeave) CArrayFixFlat<TInt>(1);
       
   170 
       
   171 	SetGridToDefault();
       
   172 	if (iGridImg)
       
   173 		iGridImg->ConstructSelectedL(iGridRange);
       
   174 	iHasChanged=EFalse;
       
   175 	}
       
   176 
       
   177 EXPORT_C void CGridLay::SetGridImgL(CGridImg* aGridImg)
       
   178 /** Sets the specified grid image object.
       
   179 
       
   180 @param aGridImg The grid image object that draws the contents of the grid. */
       
   181 	{
       
   182 	__ASSERT_DEBUG(aGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
   183 	iGridImg=aGridImg;
       
   184 	iGridImg->ResetReferencePoints();
       
   185 	ResetVisibleToCell();
       
   186 	iGridImg->CheckSideLabelWidth();
       
   187 	iGridImg->ConstructSelectedL(iGridRange);
       
   188 	if (IsPaginated())	// Internalize will fail to paginate if NULL gridimg
       
   189 		{
       
   190 		ClearPagination();
       
   191 		PaginateL();
       
   192 		}
       
   193 	}
       
   194 
       
   195 EXPORT_C CGridLay::~CGridLay()
       
   196 /** Destructor.
       
   197 
       
   198 Frees resources prior to destruction of the object. */
       
   199 	{
       
   200 	delete iColumnWidthMap;
       
   201 	delete iRowHeightMap;
       
   202 	delete iColumnPageMap;
       
   203 	delete iRowPageMap;
       
   204 	delete iHardRowPageBreaks;
       
   205 	delete iHardColumnPageBreaks;
       
   206 	}
       
   207 
       
   208 EXPORT_C void CGridLay::SetGraphicsDeviceMap(MGraphicsDeviceMap* aGraphicsDeviceMap)
       
   209 /** Sets the graphics device map to be used.
       
   210 
       
   211 @param aGraphicsDeviceMap The graphics device map: an interface for mapping 
       
   212 between twips and device-specific units. */
       
   213 	{
       
   214 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
   215 	iGraphicsDeviceMap=aGraphicsDeviceMap;
       
   216 	RecalcPixelSparseMaps();
       
   217 	iGridImg->ResetReferencePoints();
       
   218 	ResetVisibleToCell();
       
   219 	}
       
   220 
       
   221 EXPORT_C void CGridLay::SetGridToDefault()
       
   222 /** Resets the grid to its default layout. */
       
   223 	{
       
   224 	iRowHeightMap->ResetArray();
       
   225 	iColumnWidthMap->ResetArray();
       
   226 	iRowHeightMap->SetDefaultValueInTwips(EInitialDefaultRowHeightInTwips);
       
   227 	iColumnWidthMap->SetDefaultValueInTwips(EInitialDefaultColumnWidthInTwips);
       
   228 	RecalcPixelSparseMaps();
       
   229 	ClearPagination();
       
   230 	iHardRowPageBreaks->Reset();
       
   231 	iHardColumnPageBreaks->Reset();
       
   232 	iMinRowHeightInPixels=0;
       
   233 	iMinColumnWidthInPixels=0;
       
   234 	TBool isIndefiniteRowBoundaries=IsIndefiniteRowBoundaries();
       
   235 	iFlags=EIsTopLabels|EIsSideLabels|EIsHorizontalGridLines|EIsVerticalGridLines|EIsGridLabelSeparators
       
   236 		|EIsCursorVisible|EIsHighlightVisible|EIsPrintedGridLines|EIsAutoClearGridCells;
       
   237 	if (iGridImg)
       
   238 		{
       
   239 		iGridImg->SetGridLay(this);
       
   240 		iGridImg->ResetReferencePoints();
       
   241 		}
       
   242 	if (isIndefiniteRowBoundaries)
       
   243 		{
       
   244 		iFlags|=EIsIndefiniteRowBoundaries;
       
   245 		iVisibleRange.iFrom.iRow=0;
       
   246 		}
       
   247 	else
       
   248 		iVisibleRange.iFrom.iRow=iGridRange.iFrom.iRow;
       
   249 	iVisibleRange.iFrom.iCol=iGridRange.iFrom.iCol;
       
   250 	if (iGridImg)
       
   251 		{
       
   252 		ResetVisibleToCell();
       
   253 		iGridImg->CheckSideLabelWidth();
       
   254 		}
       
   255 	}
       
   256 
       
   257 EXPORT_C void CGridLay::SetVisibleRange(const TCellRef& aTopLeftCell)
       
   258 /** Scrolls the grid so that the specified cell is visible in the top left corner 
       
   259 of the grid.
       
   260 
       
   261 @param aTopLeftCell The cell to be made visible in the top left corner of 
       
   262 the visible grid. */
       
   263 	{
       
   264 	iVisibleRange.iFrom = aTopLeftCell;
       
   265 	ResetVisibleToCell();
       
   266 	}
       
   267 
       
   268 EXPORT_C TPoint CGridLay::ExposeCell(const TCellRef &aCell)
       
   269 /** Scrolls the grid by the minimum necessary to allow the specified cell to become 
       
   270 visible.
       
   271 
       
   272 @param aCell The cell to be made visible.
       
   273 @return The number of pixels scrolled, in the x and y directions. */
       
   274 	{
       
   275 	TCellRef cell=aCell;
       
   276 	LimitCellToVisible(cell);
       
   277 	TCellRef newVisFromCell=iVisibleRange.iFrom;
       
   278 	TInt visibilityCorr = (IsVisibleToRowFullyVisible()) ? 0 : 1;
       
   279 	if (iVisibleRange.iTo.iRow>=iVisibleRange.iFrom.iRow)
       
   280 		{
       
   281 	    if (cell.iRow+visibilityCorr>iVisibleRange.iTo.iRow)
       
   282 		    {
       
   283 		    if (iVisibleRange.iFrom.iRow!=iVisibleRange.iTo.iRow)
       
   284 			    CalcVisibleFromRow(cell.iRow+1,newVisFromCell.iRow);
       
   285 		    else
       
   286 			    newVisFromCell.iRow=cell.iRow;
       
   287 		    }
       
   288 	    else if (cell.iRow<iVisibleRange.iFrom.iRow)
       
   289 		    newVisFromCell.iRow=cell.iRow;
       
   290         }
       
   291 	visibilityCorr = (IsVisibleToColumnFullyVisible()) ? 0 : 1;
       
   292 	if (iVisibleRange.iTo.iCol>=iVisibleRange.iFrom.iCol)
       
   293 		{
       
   294 	    if (cell.iCol+visibilityCorr>iVisibleRange.iTo.iCol)
       
   295 		    {
       
   296 		    if (iVisibleRange.iFrom.iCol!=iVisibleRange.iTo.iCol)
       
   297 			    CalcVisibleFromColumn(cell.iCol+1,newVisFromCell.iCol);
       
   298 		    else
       
   299 			    newVisFromCell.iCol=cell.iCol;
       
   300 		    }
       
   301 	    else if (cell.iCol<iVisibleRange.iFrom.iCol)
       
   302 		    newVisFromCell.iCol=cell.iCol;
       
   303         }
       
   304 	TPoint offset=CalcOffsetBetweenCells(iVisibleRange.iFrom,newVisFromCell);
       
   305 	SetVisibleRange(newVisFromCell);
       
   306 	return (offset);
       
   307 	}
       
   308 
       
   309 EXPORT_C TPoint CGridLay::ExposeCellToTopLeft(const TCellRef &aCell)
       
   310 /** Scrolls the grid by the minimum necessary so that the specified cell is in 
       
   311 the top left corner of the visible grid.
       
   312 
       
   313 @param aCell The cell to be made visible in the top left corner of the visible 
       
   314 grid.
       
   315 @return The number of pixels scrolled, in the x and y directions. */
       
   316 	{
       
   317 	TCellRef cell=aCell;
       
   318 	LimitCellToVisible(cell);
       
   319 	TPoint offset=CalcOffsetBetweenCells(iVisibleRange.iFrom,cell);
       
   320 	SetVisibleRange(cell);
       
   321 	return offset;
       
   322 	}
       
   323 
       
   324 EXPORT_C TPoint CGridLay::PageScroll(TMoveDirectionAndAmount aPageScroll)
       
   325 // Same as CalcScroll but updates iVisibleRange to the new value.
       
   326 /** Scrolls the grid by one page.
       
   327 
       
   328 @param aPageScroll The direction and amount by which to scroll.
       
   329 @return The number of pixels scrolled, in the x and y directions. This represents 
       
   330 the amount of scrolling required to move from the start of the old visible 
       
   331 range to the start of the new visible range. */
       
   332 	{
       
   333 	TRangeRef newVisRange;
       
   334 	newVisRange.iFrom=CalcVisibleFromCellAfterPageScroll(aPageScroll);
       
   335 	TPoint offset=CalcOffsetBetweenCells(iVisibleRange.iFrom,newVisRange.iFrom);
       
   336 	SetVisibleRange(newVisRange.iFrom);
       
   337 	return offset;
       
   338 	}
       
   339 
       
   340 TInt CGridLay::ColumnWidthInPixels(TInt aCol) const
       
   341 	{
       
   342 	return iColumnWidthMap->ValueInPixels(aCol);
       
   343 	}
       
   344 
       
   345 EXPORT_C TInt CGridLay::ColumnWidthInTwips(TInt aCol) const
       
   346 /** Gets the width of the specified column.
       
   347 
       
   348 @param aCol The column number.
       
   349 @return The width of the column, in twips. */
       
   350 	{
       
   351 	return iColumnWidthMap->ValueInTwips(aCol);
       
   352 	}
       
   353 
       
   354 void CGridLay::SetColumnWidthInPixelsL(TInt aCol,TInt aWidthInPixels)
       
   355 //
       
   356 // Set the given column to the given width. Ensures that the visible range is
       
   357 // left with sensible values
       
   358 //	
       
   359 	{
       
   360 	__ASSERT_DEBUG(iGraphicsDeviceMap!=NULL,Panic(EGridNullGraphicsDeviceMap));
       
   361 	aWidthInPixels=Max(aWidthInPixels,iMinColumnWidthInPixels);
       
   362 	PreCheckColumnWidthChange(aCol,aWidthInPixels);
       
   363 	iColumnWidthMap->SetL(aCol,iGraphicsDeviceMap->HorizontalPixelsToTwips(aWidthInPixels),aWidthInPixels);
       
   364 	PostCheckColumnWidthChange(aCol,aWidthInPixels);
       
   365 	}
       
   366 
       
   367 void CGridLay::PreCheckColumnWidthChange(TInt aCol,TBool aNonZeroWidth)
       
   368 	{
       
   369 	if (aNonZeroWidth)
       
   370 		{
       
   371 		TInt col=aCol;
       
   372 		StepColumnForward(col);
       
   373 		if (IsVerticalTitleLine() && col==iTitleRange.iFrom.iCol)
       
   374 			iTitleRange.iFrom.iCol=aCol;
       
   375 		else if ((!IsVerticalTitleLine() || col>iTitleRange.iTo.iCol) && col==iVisibleRange.iFrom.iCol)
       
   376 			iVisibleRange.iFrom.iCol=aCol;
       
   377 		}
       
   378 	}
       
   379 
       
   380 void CGridLay::PostCheckColumnWidthChange(TInt aCol,TBool aNonZeroWidth)
       
   381 	{
       
   382 	if (!aNonZeroWidth)
       
   383 		{
       
   384 		if (IsVerticalTitleLine() && aCol==iTitleRange.iFrom.iCol)
       
   385 			StepColumnForward(iTitleRange.iFrom.iCol);
       
   386 		if (aCol==iVisibleRange.iFrom.iCol)
       
   387 			StepColumnForward(iVisibleRange.iFrom.iCol);
       
   388 		}
       
   389 	if (iGridImg)
       
   390 		iGridImg->ResetReferencePoints();
       
   391 	ResetVisibleToColumn();
       
   392 	iHasChanged=ETrue;
       
   393 	}
       
   394 
       
   395 EXPORT_C void CGridLay::SetColumnWidthInTwipsL(TInt aCol,TInt aWidthInTwips)
       
   396 //
       
   397 // Set the given column to the given width. Ensures that the visible range is
       
   398 // left with sensible values
       
   399 //	
       
   400 /** Sets the width of the specified column.
       
   401 
       
   402 Note that the width cannot be set smaller than the minimum defined column 
       
   403 width.
       
   404 
       
   405 @param aCol The number of the column whose width is to be set.
       
   406 @param aWidthInTwips The width of the column, in twips.
       
   407 @panic GRIDIMG 9 In debug mode, if no MGraphicsDeviceMap object has been set.
       
   408 @see MinColumnWidthInPixels() */
       
   409 	{
       
   410 	TInt widthInPixels=0;
       
   411 	if (iGraphicsDeviceMap)
       
   412 		{
       
   413 		widthInPixels=iGraphicsDeviceMap->HorizontalTwipsToPixels(aWidthInTwips);
       
   414 		if (widthInPixels<iMinColumnWidthInPixels)
       
   415 			{
       
   416 			widthInPixels=iMinColumnWidthInPixels;
       
   417 			aWidthInTwips=iGraphicsDeviceMap->HorizontalPixelsToTwips(widthInPixels);
       
   418 			}
       
   419 		}
       
   420 	PreCheckColumnWidthChange(aCol,aWidthInTwips);
       
   421 	iColumnWidthMap->SetL(aCol,aWidthInTwips,widthInPixels);
       
   422 	PostCheckColumnWidthChange(aCol,aWidthInTwips);
       
   423 	}
       
   424 
       
   425 EXPORT_C TInt CGridLay::SetColumnWidthInTwipsL(TInt aStartCol,TInt aEndCol,TInt aWidthInTwips)
       
   426 /** Sets the widths of all specified columns to the specified value.
       
   427 
       
   428 @param aStartCol The first column whose width is to be set.
       
   429 @param aEndCol The last column whose width is to be set.
       
   430 @param aWidthInTwips The width of the columns, in twips. Note that if the specified 
       
   431 columns span the whole grid, then the function sets this value as the default 
       
   432 width of all columns through a call to SetDefaultColumnWidthInTwips().
       
   433 @return KErrNone if successful; KErrTooBig if the difference between the two 
       
   434 column numbers is greater than EMaxArrayChanges. */
       
   435 	{
       
   436 	if (aStartCol==iGridRange.iFrom.iCol && aEndCol==iGridRange.iTo.iCol)
       
   437 		{
       
   438 		SetColumnWidthsToDefault();
       
   439 		SetDefaultColumnWidthInTwips(aWidthInTwips);
       
   440 		}
       
   441 	else if (aEndCol-aStartCol>EMaxArrayChanges)
       
   442 		return KErrTooBig;
       
   443 	else
       
   444 		{
       
   445 		for (;aStartCol<=aEndCol;aStartCol++)
       
   446 			SetColumnWidthInTwipsL(aStartCol,aWidthInTwips);
       
   447 		}
       
   448 	iHasChanged=ETrue;
       
   449 	return KErrNone;
       
   450 	}
       
   451 
       
   452 TInt CGridLay::DefaultColumnWidthInPixels() const
       
   453 	{
       
   454 	return iColumnWidthMap->DefaultValueInPixels();
       
   455 	}
       
   456 
       
   457 EXPORT_C TInt CGridLay::DefaultColumnWidthInTwips() const
       
   458 /** Gets the default width of columns.
       
   459 
       
   460 @return The default width of columns, in twips. */
       
   461 	{
       
   462 	return iColumnWidthMap->DefaultValueInTwips();
       
   463 	}
       
   464 
       
   465 void CGridLay::SetDefaultColumnWidthInPixels(TInt aWidthInPixels)
       
   466 	{
       
   467 	if (aWidthInPixels==0)
       
   468 		return;
       
   469 	__ASSERT_DEBUG(iGraphicsDeviceMap!=NULL,Panic(EGridNullGraphicsDeviceMap));
       
   470 	aWidthInPixels=Max(aWidthInPixels,iMinColumnWidthInPixels);
       
   471 	iColumnWidthMap->SetDefaultValueInPixels(aWidthInPixels);
       
   472 	iColumnWidthMap->SetDefaultValueInTwips(iGraphicsDeviceMap->HorizontalPixelsToTwips(aWidthInPixels));
       
   473 	if (iGridImg)
       
   474 		iGridImg->ResetReferencePoints();
       
   475 	ResetVisibleToColumn();
       
   476 	iHasChanged=ETrue;
       
   477 	}
       
   478 
       
   479 EXPORT_C void CGridLay::SetDefaultColumnWidthInTwips(TInt aWidthInTwips)
       
   480 /** Sets the column width default value.
       
   481 
       
   482 Note that the width cannot be set smaller than the minimum defined column 
       
   483 width.
       
   484 
       
   485 @param aWidthInTwips The width of columns, in twips.
       
   486 @see SetMinColumnWidthInPixels()
       
   487 @see MinColumnWidthInPixels() */
       
   488 	{
       
   489 	if (aWidthInTwips==0)
       
   490 		return;
       
   491 	if (iGraphicsDeviceMap)
       
   492 		{
       
   493 		TInt widthInPixels=iGraphicsDeviceMap->HorizontalTwipsToPixels(aWidthInTwips);
       
   494 		if (widthInPixels<iMinColumnWidthInPixels)
       
   495 			{
       
   496 			widthInPixels=iMinColumnWidthInPixels;
       
   497 			aWidthInTwips=iGraphicsDeviceMap->HorizontalPixelsToTwips(widthInPixels);
       
   498 			}
       
   499 		iColumnWidthMap->SetDefaultValueInPixels(widthInPixels);
       
   500 		}
       
   501 	iColumnWidthMap->SetDefaultValueInTwips(aWidthInTwips);
       
   502 	if (iGridImg)
       
   503 		iGridImg->ResetReferencePoints();
       
   504 	ResetVisibleToColumn();
       
   505 	iHasChanged=ETrue;
       
   506 	}
       
   507 
       
   508 EXPORT_C void CGridLay::SetColumnWidthsToDefault()
       
   509 /** Sets the widths of all columns to the default value.
       
   510 
       
   511 @see SetDefaultColumnWidthInTwips() */
       
   512 	{
       
   513 	iColumnWidthMap->ResetArray();
       
   514 	if (iGridImg)
       
   515 		iGridImg->ResetReferencePoints();
       
   516 	ResetVisibleToColumn();
       
   517 	iHasChanged=ETrue;
       
   518 	}
       
   519 
       
   520 EXPORT_C TInt CGridLay::MinColumnWidthInPixels() const
       
   521 /** Gets the minimum width of columns.
       
   522 
       
   523 @return The minimum width of columns, in pixels. */
       
   524 	{
       
   525 	return iMinColumnWidthInPixels;
       
   526 	}
       
   527 
       
   528 EXPORT_C void CGridLay::SetMinColumnWidthInPixels(TInt aWidthInPixels)
       
   529 /** Sets the minimum width of columns.
       
   530 
       
   531 @param aWidthInPixels The minimum width of columns, in pixels. */
       
   532 	{
       
   533 	iMinColumnWidthInPixels=aWidthInPixels;
       
   534 	iHasChanged=ETrue;
       
   535 	}
       
   536 
       
   537 EXPORT_C TInt CGridLay::ColumnWidthOfSelectedInTwips() const
       
   538 /** Gets the width of columns in the selected region.
       
   539 
       
   540 @return The column width, in twips, if all columns in the selected region 
       
   541 have the same width; -1, otherwise.
       
   542 @panic GRIDIMG 3 If this grid layout object has no grid image object. */
       
   543 	{
       
   544 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
   545 	if (IsUniformColumnWidth())
       
   546 		return DefaultColumnWidthInTwips();
       
   547 	const CGridCellRegion* selected=iGridImg->Selected();
       
   548 	TInt count=selected->Count();
       
   549 	if (!count)
       
   550 		return ColumnWidthInTwips(iGridImg->CursorPos().iCol);
       
   551 	if (selected->IsAnyRowSelected())
       
   552 		return iColumnWidthMap->Count() ? -1 : DefaultColumnWidthInTwips();
       
   553 
       
   554 	TInt width=ColumnWidthInTwips((*selected)[count-1].iFrom.iCol);
       
   555 	for (TInt ii=0;ii<count;ii++)
       
   556 		{
       
   557 		TRangeRef range=(*selected)[ii];
       
   558 		for (;range.iFrom.iCol<=range.iTo.iCol;range.iFrom.iCol++)
       
   559 			{
       
   560 			if (ColumnWidthInTwips(range.iFrom.iCol)!=width)
       
   561 				return -1; //Inconsistent widths
       
   562 			}
       
   563 		}
       
   564 	return width;
       
   565 	}
       
   566 
       
   567 EXPORT_C void CGridLay::SetColumnWidthOfSelectedInTwipsL(TInt aWidthInTwips)
       
   568 /** Sets the widths of all columns in the selected region to the specified value.
       
   569 
       
   570 @param aWidthInTwips The column width, in twips.
       
   571 @panic GRIDIMG 3 If this grid layout object has no grid image object. */
       
   572 	{
       
   573 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
   574 	const CGridCellRegion* selected=iGridImg->Selected();
       
   575 	if (selected->IsAnyRowSelected() || IsUniformColumnWidth())
       
   576 		{
       
   577 		iColumnWidthMap->ResetArray();
       
   578 		SetDefaultColumnWidthInTwips(aWidthInTwips);
       
   579 		}
       
   580 	else
       
   581 		{
       
   582 		TInt count=selected->Count();
       
   583 		if (!count)
       
   584 			SetColumnWidthInTwipsL(iGridImg->CursorPos().iCol,aWidthInTwips);
       
   585 		for (TInt ii=0;ii<count;ii++)
       
   586 			{
       
   587 			TRangeRef range=(*selected)[ii];
       
   588 			if ((range.iTo.iCol-range.iFrom.iCol)>EMaxArrayChanges)
       
   589 				continue;
       
   590 			for (;range.iFrom.iCol<=range.iTo.iCol;range.iFrom.iCol++)
       
   591 				SetColumnWidthInTwipsL(range.iFrom.iCol,aWidthInTwips);
       
   592 			}
       
   593 		}
       
   594 	NotifyPaginationOutOfDateL();
       
   595 	}
       
   596 
       
   597 TInt CGridLay::RowHeightInPixels(TInt aRow) const
       
   598 	{
       
   599 	return iRowHeightMap->ValueInPixels(aRow);
       
   600 	}
       
   601 
       
   602 EXPORT_C TInt CGridLay::RowHeightInTwips(TInt aRow) const
       
   603 /** Gets the height of the specified row.
       
   604 
       
   605 @param aRow The row number.
       
   606 @return The height of the row, in twips. */
       
   607 	{
       
   608 	return iRowHeightMap->ValueInTwips(aRow);
       
   609 	}
       
   610 
       
   611 void CGridLay::SetRowHeightInPixelsL(TInt aRow,TInt aHeightInPixels)
       
   612 //
       
   613 // Similar to SetColumnWidthInPixelsL (remember this may be limited to the min row height)
       
   614 //
       
   615 	{
       
   616 	__ASSERT_DEBUG(iGraphicsDeviceMap!=NULL,Panic(EGridNullGraphicsDeviceMap));
       
   617 	aHeightInPixels=Max(aHeightInPixels,iMinRowHeightInPixels);
       
   618 	PreCheckRowHeightChange(aRow,aHeightInPixels);
       
   619 	iRowHeightMap->SetL(aRow,iGraphicsDeviceMap->VerticalPixelsToTwips(aHeightInPixels),aHeightInPixels);
       
   620 	PostCheckRowHeightChange(aRow,aHeightInPixels);
       
   621 	}
       
   622 
       
   623 void CGridLay::PreCheckRowHeightChange(TInt aRow,TBool aNonZeroHeight)
       
   624 	{
       
   625 	if (aNonZeroHeight)
       
   626 		{
       
   627 		TInt row=aRow;
       
   628 		StepRowForward(row);
       
   629 		if (IsHorizontalTitleLine() && row==iTitleRange.iFrom.iRow)
       
   630 			iTitleRange.iFrom.iRow=aRow;
       
   631 		else if ((!IsHorizontalTitleLine() || row>iTitleRange.iTo.iRow) && row==iVisibleRange.iFrom.iRow)
       
   632 			iVisibleRange.iFrom.iRow=aRow;
       
   633 		}
       
   634 	}
       
   635 
       
   636 void CGridLay::PostCheckRowHeightChange(TInt aRow,TBool aNonZeroHeight)
       
   637 	{
       
   638 	if (!aNonZeroHeight)
       
   639 		{
       
   640 		if (IsHorizontalTitleLine() && aRow==iTitleRange.iFrom.iRow)
       
   641 			StepRowForward(iTitleRange.iFrom.iRow);
       
   642 		if (aRow==iVisibleRange.iFrom.iRow)
       
   643 			StepRowForward(iVisibleRange.iFrom.iRow);
       
   644 		}
       
   645 	if (iGridImg)
       
   646 		iGridImg->ResetReferencePoints();
       
   647 	ResetVisibleToRow();
       
   648 	iHasChanged=ETrue;
       
   649 	}
       
   650 
       
   651 EXPORT_C void CGridLay::SetRowHeightInTwipsL(TInt aRow,TInt aHeightInTwips)
       
   652 //
       
   653 // Similar to SetColumnWidthInTwipsL (remember this may be limited to the min row height)
       
   654 //
       
   655 /** Sets the height of the specified row.
       
   656 
       
   657 Note that the height cannot be set smaller than the minimum defined row height.
       
   658 
       
   659 @param aRow The number of row whose height is to be set.
       
   660 @param aHeightInTwips The height of the row, in twips.
       
   661 @see MinRowHeightInPixels() */
       
   662 	{
       
   663 	TInt heightInPixels=0;
       
   664 	if (iGraphicsDeviceMap)
       
   665 		{
       
   666 		heightInPixels=iGraphicsDeviceMap->VerticalTwipsToPixels(aHeightInTwips);
       
   667 		if (heightInPixels<iMinRowHeightInPixels)
       
   668 			{
       
   669 			heightInPixels=iMinRowHeightInPixels;
       
   670 			aHeightInTwips=iGraphicsDeviceMap->VerticalPixelsToTwips(heightInPixels);
       
   671 			}
       
   672 		}
       
   673 	PreCheckRowHeightChange(aRow,aHeightInTwips);
       
   674 	iRowHeightMap->SetL(aRow,aHeightInTwips,heightInPixels);
       
   675 	PostCheckRowHeightChange(aRow,aHeightInTwips);
       
   676 	}
       
   677 
       
   678 EXPORT_C TInt CGridLay::SetRowHeightInTwipsL(TInt aStartRow,TInt aEndRow,TInt aHeightInTwips)
       
   679 /** Sets the heights of all specified rows to the specified value.
       
   680 
       
   681 @param aStartRow The first row whose height is to be set.
       
   682 @param aEndRow The last row whose height is to be set.
       
   683 @param aHeightInTwips The height of the rows, in twips. Note that if the specified 
       
   684 rows span the whole grid, then the function sets this value as the default 
       
   685 height of all rows through a call to SetDefaultRowHeightInTwips().
       
   686 @return KErrNone if successful; KErrTooBig if the difference between the two 
       
   687 row numbers is greater than EMaxArrayChanges. */
       
   688 	{
       
   689 	if (aStartRow==iGridRange.iFrom.iRow && aEndRow==iGridRange.iTo.iRow)
       
   690 		{
       
   691 		SetRowHeightsToDefault();
       
   692 		SetDefaultRowHeightInTwips(aHeightInTwips);
       
   693 		}
       
   694 	else if (aEndRow-aStartRow>EMaxArrayChanges)
       
   695 		return KErrTooBig;
       
   696 	else
       
   697 		{
       
   698 		for (;aStartRow<=aEndRow;aStartRow++)
       
   699 			SetRowHeightInTwipsL(aStartRow,aHeightInTwips);
       
   700 		}
       
   701 	iHasChanged=ETrue;
       
   702 	return KErrNone;
       
   703 	}
       
   704 
       
   705 EXPORT_C TInt CGridLay::MinRowHeightInPixels() const
       
   706 /** Gets the minimum height of rows.
       
   707 
       
   708 @return The minimum height of rows, in pixels. */
       
   709 	{
       
   710 	return iMinRowHeightInPixels;
       
   711 	}
       
   712 
       
   713 EXPORT_C void CGridLay::SetMinRowHeightInPixels(TInt aHeightInPixels)
       
   714 /** Sets the minimum height of rows.
       
   715 
       
   716 @param aHeightInPixels The minimum height of rows, in pixels. */
       
   717 	{
       
   718 	iMinRowHeightInPixels=aHeightInPixels;
       
   719 	iHasChanged=ETrue;
       
   720 	}
       
   721 
       
   722 TInt CGridLay::DefaultRowHeightInPixels() const
       
   723 	{
       
   724 	return iRowHeightMap->DefaultValueInPixels();
       
   725 	}
       
   726 
       
   727 EXPORT_C TInt CGridLay::DefaultRowHeightInTwips() const
       
   728 /** Gets the default height of rows.
       
   729 
       
   730 @return The default height of rows, in twips, */
       
   731 	{
       
   732 	return iRowHeightMap->DefaultValueInTwips();
       
   733 	}
       
   734 
       
   735 void CGridLay::SetDefaultRowHeightInPixels(TInt aHeightInPixels)
       
   736 //
       
   737 // Remember this may be limited to the min row height
       
   738 	{
       
   739 	if (aHeightInPixels==0)
       
   740 		return;
       
   741 	__ASSERT_DEBUG(iGraphicsDeviceMap!=NULL,Panic(EGridNullGraphicsDeviceMap));
       
   742 	aHeightInPixels=Max(aHeightInPixels,iMinRowHeightInPixels);
       
   743 	iRowHeightMap->SetDefaultValueInPixels(aHeightInPixels);
       
   744 	iRowHeightMap->SetDefaultValueInTwips(iGraphicsDeviceMap->VerticalPixelsToTwips(aHeightInPixels));
       
   745 	if (iGridImg)
       
   746 		iGridImg->ResetReferencePoints();
       
   747 	ResetVisibleToRow();
       
   748 	iHasChanged=ETrue;
       
   749 	}
       
   750 
       
   751 EXPORT_C void CGridLay::SetDefaultRowHeightInTwips(TInt aHeightInTwips)
       
   752 /** Sets the default height of rows.
       
   753 
       
   754 Note that the height cannot be set smaller than the minimum defined row height.
       
   755 
       
   756 @param aHeightInTwips The height of rows, in twips.
       
   757 @see SetMinRowHeightInPixels()
       
   758 @see MinRowHeightInPixels() */
       
   759 	{
       
   760 	if (aHeightInTwips==0)
       
   761 		return;
       
   762 	if (iGraphicsDeviceMap)
       
   763 		{
       
   764 		TInt heightInPixels=iGraphicsDeviceMap->VerticalTwipsToPixels(aHeightInTwips);
       
   765 		if (heightInPixels<iMinRowHeightInPixels)
       
   766 			{
       
   767 			heightInPixels=iMinRowHeightInPixels;
       
   768 			aHeightInTwips=iGraphicsDeviceMap->VerticalPixelsToTwips(heightInPixels);
       
   769 			}
       
   770 		iRowHeightMap->SetDefaultValueInPixels(heightInPixels);
       
   771 		}
       
   772 	iRowHeightMap->SetDefaultValueInTwips(aHeightInTwips);
       
   773 	if (iGridImg)
       
   774 		iGridImg->ResetReferencePoints();
       
   775 	ResetVisibleToRow();
       
   776 	iHasChanged=ETrue;
       
   777 	}
       
   778 
       
   779 EXPORT_C void CGridLay::SetRowHeightsToDefault()
       
   780 /** Sets the heights of all rows to the default value.
       
   781 
       
   782 @see SetDefaultRowHeightInTwips() */
       
   783 	{
       
   784 	iRowHeightMap->ResetArray();
       
   785 	if (iGridImg)
       
   786 		iGridImg->ResetReferencePoints();
       
   787 	ResetVisibleToRow();
       
   788 	iHasChanged=ETrue;
       
   789 	}
       
   790 
       
   791 EXPORT_C TInt CGridLay::RowHeightOfSelectedInTwips() const
       
   792 /** Gets the height of rows in the selected region.
       
   793 
       
   794 @return The row height, in twips, if all rows in the selected region have 
       
   795 the same width; -1, otherwise.
       
   796 @panic GRIDIMG 3 If this grid layout object has no grid image object. */
       
   797 	{
       
   798 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
   799 	if (IsUniformRowHeight())
       
   800 		return DefaultRowHeightInTwips();
       
   801 	const CGridCellRegion* selected=iGridImg->Selected();
       
   802 	TInt count=selected->Count();
       
   803 	if (!count)
       
   804 		return RowHeightInTwips(iGridImg->CursorPos().iRow);
       
   805 	if (selected->IsAnyColSelected())
       
   806 		return iRowHeightMap->Count() ? -1 : DefaultRowHeightInTwips();
       
   807 
       
   808 	TInt height=RowHeightInTwips((*selected)[count-1].iFrom.iRow);
       
   809 	for (TInt ii=0;ii<count;ii++)
       
   810 		{
       
   811 		TRangeRef range=(*selected)[ii];
       
   812 		for (;range.iFrom.iRow<=range.iTo.iRow;range.iFrom.iRow++)
       
   813 			{
       
   814 			if (RowHeightInTwips(range.iFrom.iRow)!=height)
       
   815 				return -1; //Inconsistent heights
       
   816 			}
       
   817 		}
       
   818 	return height;
       
   819 	}
       
   820 
       
   821 EXPORT_C void CGridLay::SetRowHeightOfSelectedInTwipsL(TInt aHeightInTwips)
       
   822 /** Sets the heights of all rows in the selected region to the specified value.
       
   823 
       
   824 @param aHeightInTwips The row height, in twips.
       
   825 @panic GRIDIMG 3 If this grid layout object has no grid image object. */
       
   826 	{
       
   827 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
   828 	const CGridCellRegion* selected=iGridImg->Selected();
       
   829 	if (selected->IsAnyColSelected() || IsUniformRowHeight())
       
   830 		{
       
   831 		iRowHeightMap->ResetArray();
       
   832 		SetDefaultRowHeightInTwips(aHeightInTwips);
       
   833 		}
       
   834 	else
       
   835 		{
       
   836 		TInt count=selected->Count();
       
   837 		if (!count)
       
   838 			SetRowHeightInTwipsL(iGridImg->CursorPos().iRow,aHeightInTwips);
       
   839 		for (TInt ii=0;ii<count;ii++)
       
   840 			{
       
   841 			TRangeRef range=(*selected)[ii];
       
   842 			if ((range.iTo.iRow-range.iFrom.iRow)>EMaxArrayChanges)
       
   843 				continue;
       
   844 			for (;range.iFrom.iRow<=range.iTo.iRow;range.iFrom.iRow++)
       
   845 				SetRowHeightInTwipsL(range.iFrom.iRow,aHeightInTwips);
       
   846 			}
       
   847 		}
       
   848 	iHasChanged=ETrue;
       
   849 	NotifyPaginationOutOfDateL();
       
   850 	}
       
   851 
       
   852 EXPORT_C void CGridLay::RecalcPixelSparseMaps()
       
   853 /** Recalculates the internal maps that map row and column numbers to heights and 
       
   854 widths respectively.
       
   855 
       
   856 Heights and widths are held as both pixel and twip values. */
       
   857 	{
       
   858 	if (!iGraphicsDeviceMap)
       
   859 		{
       
   860 		const TInt KArbitraryNonZeroValue = 100;
       
   861 		iColumnWidthMap->SetDefaultValueInPixels(KArbitraryNonZeroValue);	// Must be non-zero else get divide by zero errors
       
   862 		iRowHeightMap->SetDefaultValueInPixels(KArbitraryNonZeroValue);
       
   863 		return;
       
   864 		}
       
   865 	TInt defValueInTwips=iColumnWidthMap->DefaultValueInTwips();
       
   866 	TInt defValueInPixels=iGraphicsDeviceMap->HorizontalTwipsToPixels(defValueInTwips);
       
   867 	if (defValueInPixels==0)
       
   868 		defValueInPixels=1;		// cannot be zero
       
   869 	iColumnWidthMap->SetDefaultValueInPixels(defValueInPixels);
       
   870 	TInt end=iColumnWidthMap->Count();
       
   871 	{for (TInt ii=0;ii<end;ii++)
       
   872 		{
       
   873 		TSizeElement& element=(*iColumnWidthMap)[ii];
       
   874 		element.iValueInPixels=iGraphicsDeviceMap->HorizontalTwipsToPixels(element.iValueInTwips);
       
   875 		}}
       
   876 
       
   877 	defValueInTwips=iRowHeightMap->DefaultValueInTwips();
       
   878 	defValueInPixels=iGraphicsDeviceMap->VerticalTwipsToPixels(defValueInTwips);
       
   879 	if (defValueInPixels==0)
       
   880 		defValueInPixels=1;
       
   881 	iRowHeightMap->SetDefaultValueInPixels(defValueInPixels);
       
   882 	end=iRowHeightMap->Count();
       
   883 	for (TInt ii=0;ii<end;ii++)
       
   884 		{
       
   885 		TSizeElement& element=(*iRowHeightMap)[ii];
       
   886 		element.iValueInPixels=iGraphicsDeviceMap->VerticalTwipsToPixels(element.iValueInTwips);
       
   887 		}
       
   888 	}
       
   889 
       
   890 EXPORT_C void CGridLay::InsertDeleteColumns(TInt aStartCol,TInt aNoOfCols,TFixGridRange aFixGridRange)
       
   891 /** Inserts or deletes columns.
       
   892 
       
   893 Insertion causes columns to be inserted in front of the specified start column. 
       
   894 Deletion causes columns in front of the specified columns to be deleted.
       
   895 
       
   896 @param aStartCol The start column.
       
   897 @param aNoOfCols The number of columns to be inserted or deleted. A positive 
       
   898 number means that columns are to be inserted; a negative number means that 
       
   899 columns are to be deleted.
       
   900 @param aFixGridRange Indicates whether the grid boundary is to be adjusted 
       
   901 by the number of columns (increased or decreased). */
       
   902 	{
       
   903 	if (aNoOfCols==0)
       
   904 		return;
       
   905 	if (aFixGridRange==EAdjustGridRange)
       
   906 		iGridRange.iTo.iCol+=aNoOfCols;
       
   907 	iColumnWidthMap->OpenCloseGap(aStartCol,aNoOfCols,iGridRange.iTo.iCol);
       
   908 	if (iGridImg)
       
   909 		{
       
   910 		iGridImg->ResetReferencePoints();
       
   911 		ResetVisibleToColumn();
       
   912 		if (aFixGridRange==EAdjustGridRange)
       
   913 			iGridImg->NotifyGridRangeResize();
       
   914 		}
       
   915 	iHasChanged=ETrue;
       
   916 	}
       
   917 
       
   918 EXPORT_C void CGridLay::InsertDeleteRows(TInt aStartRow,TInt aNoOfRows,TFixGridRange aFixGridRange)
       
   919 /** Inserts or deletes rows.
       
   920 
       
   921 Insertion causes rows to be inserted below the specified start row. Deletion 
       
   922 causes rows below the specified row to be deleted.
       
   923 
       
   924 @param aStartRow The start row.
       
   925 @param aNoOfRows The number of rows to be inserted or deleted. A positive number 
       
   926 means that rows are to be inserted; a negative number means that rows are 
       
   927 to be deleted.
       
   928 @param aFixGridRange Indicates whether the grid boundary is to be adjusted 
       
   929 by the number of rows (increased or decreased). */
       
   930 	{
       
   931 	if (aNoOfRows==0)
       
   932 		return;
       
   933 	if (aFixGridRange==EAdjustGridRange)
       
   934 		iGridRange.iTo.iRow+=aNoOfRows;
       
   935 	iRowHeightMap->OpenCloseGap(aStartRow,aNoOfRows,iGridRange.iTo.iRow);
       
   936 	if (iGridImg)
       
   937 		{
       
   938 		iGridImg->ResetReferencePoints();
       
   939 		ResetVisibleToRow();
       
   940 		if (aFixGridRange==EAdjustGridRange)
       
   941 			iGridImg->NotifyGridRangeResize();
       
   942 		}
       
   943 	iHasChanged=ETrue;
       
   944 	}
       
   945 
       
   946 EXPORT_C void CGridLay::SetHorizontalGridLines(TBool aState)
       
   947 /** Sets whether horizontal grid lines are to be drawn.
       
   948 
       
   949 @param aState ETrue, if horizontal grid lines are to be drawn; EFalse, otherwise. */
       
   950 	{
       
   951 	if (aState)
       
   952 		iFlags|=EIsHorizontalGridLines;
       
   953 	else
       
   954 		iFlags&=~EIsHorizontalGridLines;
       
   955 	iHasChanged=ETrue;
       
   956 	}
       
   957 
       
   958 EXPORT_C void CGridLay::SetVerticalGridLines(TBool aState)
       
   959 /** Sets whether vertical grid lines are to be drawn.
       
   960 
       
   961 @param aState ETrue, if vertical grid lines are to be drawn; EFalse, otherwise. */
       
   962 	{
       
   963 	if (aState)
       
   964 		iFlags|=EIsVerticalGridLines;
       
   965 	else
       
   966 		iFlags&=~EIsVerticalGridLines;
       
   967 	iHasChanged=ETrue;
       
   968 	}
       
   969 
       
   970 EXPORT_C void CGridLay::SetSideLabels(TBool aState)
       
   971 /** Sets whether side labels are printed.
       
   972 
       
   973 @param aState ETrue, if side labels are printed; EFalse, otherwise. */
       
   974 	{
       
   975 	if (aState)
       
   976 		iFlags|=EIsSideLabels;
       
   977 	else
       
   978 		iFlags&=~EIsSideLabels;
       
   979 	if (iGridImg)
       
   980 		{
       
   981 		iGridImg->ResetReferencePoints();
       
   982 		ResetVisibleToColumn();
       
   983 		}
       
   984 	iHasChanged=ETrue;
       
   985 	}
       
   986 
       
   987 EXPORT_C void CGridLay::SetTopLabels(TBool aState)
       
   988 /** Sets whether top labels are printed.
       
   989 
       
   990 @param aState ETrue, if top labels are printed; EFalse, otherwise. */
       
   991 	{
       
   992 	if (aState)
       
   993 		iFlags|=EIsTopLabels;
       
   994 	else
       
   995 		iFlags&=~EIsTopLabels;
       
   996 	if (iGridImg)
       
   997 		{
       
   998 		iGridImg->ResetReferencePoints();
       
   999 		ResetVisibleToRow();
       
  1000 		}
       
  1001 	iHasChanged=ETrue;
       
  1002 	}
       
  1003 
       
  1004 EXPORT_C void CGridLay::SetGridLabelSeparators(TBool aState)
       
  1005 /** Sets whether label separators are to be drawn.
       
  1006 
       
  1007 @param aState ETrue, if label separators are to be drawn; EFalse, otherwise. */
       
  1008 	{
       
  1009 	if (aState)
       
  1010 		iFlags|=EIsGridLabelSeparators;
       
  1011 	else
       
  1012 		iFlags&=~EIsGridLabelSeparators;
       
  1013 	iHasChanged=ETrue;
       
  1014 	}
       
  1015 
       
  1016 EXPORT_C void CGridLay::SetColumnBursting(TBool aState)
       
  1017 /** Sets whether column bursting is to be permitted.
       
  1018 
       
  1019 Column bursting occurs when the contents of a cell are too wide; adjacent 
       
  1020 cells are then overwritten, provided they are empty.
       
  1021 
       
  1022 @param aState ETrue, if column bursting is to be permitted; EFalse, otherwise. */
       
  1023 	{
       
  1024 	if (aState)
       
  1025 		iFlags|=EIsColumnBursting;
       
  1026 	else
       
  1027 		iFlags&=~EIsColumnBursting;
       
  1028 	iHasChanged=ETrue;
       
  1029 	}
       
  1030 
       
  1031 EXPORT_C void CGridLay::SetCursorVisible(TBool aVisible)
       
  1032 /** Sets whether the cursor is to be visible.
       
  1033 
       
  1034 @param aVisible ETrue, if the cursor is to be visible; EFalse, otherwise. */
       
  1035 	{
       
  1036 	if (aVisible)
       
  1037 		iFlags|=EIsCursorVisible;
       
  1038 	else
       
  1039 		iFlags&=~EIsCursorVisible;
       
  1040 	iHasChanged=ETrue;
       
  1041 	}
       
  1042 
       
  1043 EXPORT_C void CGridLay::SetHighlightVisible(TBool aVisible)
       
  1044 /** Sets whether selected cells are to be highlighted.
       
  1045 
       
  1046 @param aVisible ETrue, if selected cells are to be highlighted; EFalse, otherwise. */
       
  1047 	{
       
  1048 	if (aVisible)
       
  1049 		iFlags|=EIsHighlightVisible;
       
  1050 	else
       
  1051 		iFlags&=~EIsHighlightVisible;
       
  1052 	iHasChanged=ETrue;
       
  1053 	}
       
  1054 
       
  1055 EXPORT_C void CGridLay::SetRowPermanentlySelectedL(TBool aState)
       
  1056 /** Sets whether rows are to be permanently selected.
       
  1057 
       
  1058 @param aState ETrue, if rows are to be permanently selected; EFalse, otherwise. */
       
  1059 	{
       
  1060 	if (aState)
       
  1061 		iFlags|=EIsRowPermanentlySelected;
       
  1062 	else
       
  1063 		iFlags&=~EIsRowPermanentlySelected;
       
  1064 	if (aState && iGridImg)
       
  1065 		{
       
  1066 		CGridCellRegion* selected = (CGridCellRegion*)iGridImg->Selected(); //!! Bit naughty
       
  1067 		selected->Reset();
       
  1068 		selected->AddRowL(iGridImg->CursorPos().iRow);
       
  1069 		}
       
  1070 	iHasChanged=ETrue;
       
  1071 	}
       
  1072 
       
  1073 EXPORT_C void CGridLay::SetTitleLinesL(TBool aState)
       
  1074 /** Sets whether the grid is to have both horizontal and vertical title lines.
       
  1075 
       
  1076 @param aState ETrue, if the grid is to have both a horizontal and vertical 
       
  1077 title line; EFalse, otherwise. */
       
  1078 	{
       
  1079 	if (!(aState || IsTitleLines()))
       
  1080 		return;	//No change
       
  1081 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1082 	TCellRef cursorPos=(iGridImg->Selected()->Count()) ? iGridImg->AnchorPos() :
       
  1083 		iGridImg->CursorPos();
       
  1084 	if (aState)
       
  1085 		{
       
  1086 		SetTitleLinesL(cursorPos);
       
  1087 		}
       
  1088 	else
       
  1089 		{
       
  1090 		TCellRef cell=iVisibleRange.iFrom;
       
  1091 		if (IsHorizontalTitleLine())
       
  1092 			cell.iRow=iTitleRange.iTo.iRow;
       
  1093 		if (IsVerticalTitleLine())
       
  1094 			cell.iCol=iTitleRange.iTo.iCol;
       
  1095 		TPoint offset=ExposeCellToTopLeft(cell);
       
  1096 		iGridImg->ScrollL(offset);
       
  1097 		if (IsHorizontalTitleLine())
       
  1098 			iVisibleRange.iFrom.iRow=iTitleRange.iFrom.iRow;
       
  1099 		if (IsVerticalTitleLine())
       
  1100 			iVisibleRange.iFrom.iCol=iTitleRange.iFrom.iCol;
       
  1101 		iFlags&=~(EIsHorizontalTitleLine|EIsVerticalTitleLine);
       
  1102 		offset=iGridImg->MainPoint();	//Just using offset instead of creating a new TPoint
       
  1103 		iGridImg->ResetReferencePoints();
       
  1104 		iGridImg->ClearTitleLineRegionL(offset);
       
  1105 		}
       
  1106 	iHasChanged=ETrue;
       
  1107 	}
       
  1108 
       
  1109 EXPORT_C void CGridLay::SetTitleLinesL(const TCellRef& aCellRef)
       
  1110 /** Sets horizontal and vertical title lines at the specified cell.
       
  1111 
       
  1112 @param aCellRef The cell reference at which title lines are set.
       
  1113 @panic GRIDIMG 3 If this grid layout object has no grid image object. */
       
  1114 	{
       
  1115 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1116 	SetTitleLinesL(EFalse);		// must be cleared first
       
  1117 	if (aCellRef.iRow>iVisibleRange.iFrom.iRow && aCellRef.iRow<=iVisibleRange.iTo.iRow
       
  1118 		&& !IsIndefiniteRowBoundaries())
       
  1119 		{
       
  1120 		iFlags|=EIsHorizontalTitleLine;
       
  1121 		iTitleRange.iFrom.iRow=iVisibleRange.iFrom.iRow;
       
  1122 		iTitleRange.iTo.iRow=iVisibleRange.iFrom.iRow=aCellRef.iRow;
       
  1123 		}
       
  1124 	if (aCellRef.iCol>iVisibleRange.iFrom.iCol && aCellRef.iCol<=iVisibleRange.iTo.iCol)
       
  1125 		{
       
  1126 		iFlags|=EIsVerticalTitleLine;
       
  1127 		iTitleRange.iFrom.iCol=iVisibleRange.iFrom.iCol;
       
  1128 		iTitleRange.iTo.iCol=iVisibleRange.iFrom.iCol=aCellRef.iCol;
       
  1129 		}
       
  1130 	if (IsTitleLines())
       
  1131 		{
       
  1132 		iGridImg->ResetReferencePoints();
       
  1133 		iGridImg->DrawTitleLines();
       
  1134 		}
       
  1135 	iHasChanged=ETrue;
       
  1136 	}
       
  1137 
       
  1138 EXPORT_C void CGridLay::ToggleTitleLinesL()
       
  1139 /** Sets title lines on, if they are off; sets title lines off, if they are on. */
       
  1140 	{
       
  1141 	SetTitleLinesL(!IsTitleLines());
       
  1142 	}
       
  1143 
       
  1144 void CGridLay::SetIndefiniteRowBoundaries(TBool aState)
       
  1145 	{
       
  1146 	if (aState)
       
  1147 		iFlags|=EIsIndefiniteRowBoundaries;
       
  1148 	else
       
  1149 		iFlags&=~EIsIndefiniteRowBoundaries;
       
  1150 	iHasChanged=ETrue;
       
  1151 	}
       
  1152 
       
  1153 EXPORT_C void CGridLay::SetUniformRowHeight(TBool aState)
       
  1154 /** Sets whether all rows are to have the same height.
       
  1155 
       
  1156 @param aState ETrue, if all rows are to have the same height; EFalse, otherwise. */
       
  1157 	{
       
  1158 	if (aState)
       
  1159 		{
       
  1160 		iFlags|=EIsUniformRowHeight;
       
  1161 		SetRowHeightsToDefault();
       
  1162 		}
       
  1163 	else
       
  1164 		iFlags&=~EIsUniformRowHeight;
       
  1165 	iHasChanged=ETrue;
       
  1166 	}
       
  1167 
       
  1168 EXPORT_C void CGridLay::SetUniformColumnWidth(TBool aState)
       
  1169 /** Sets whether all columns are to have the same width.
       
  1170 
       
  1171 @param aState ETrue, if all columns are to have the same width; EFalse, otherwise. */
       
  1172 	{
       
  1173 	if (aState)
       
  1174 		{
       
  1175 		iFlags|=EIsUniformColumnWidth;
       
  1176 		SetColumnWidthsToDefault();
       
  1177 		}
       
  1178 	else
       
  1179 		iFlags&=~EIsUniformColumnWidth;
       
  1180 	iHasChanged=ETrue;
       
  1181 	}
       
  1182 
       
  1183 EXPORT_C void CGridLay::SetTopLabelDragDisabled(TBool aState)
       
  1184 /** Sets whether a drag operation on the boundary between two columns is to be 
       
  1185 permitted.
       
  1186 
       
  1187 @param aState ETrue, if the drag operation is to be permitted; EFalse, otherwise. */
       
  1188 	{
       
  1189 	if (aState)
       
  1190 		iFlags|=EIsTopLabelDragDisabled;
       
  1191 	else
       
  1192 		iFlags&=~EIsTopLabelDragDisabled;
       
  1193 	iHasChanged=ETrue;
       
  1194 	}
       
  1195 
       
  1196 EXPORT_C void CGridLay::SetSideLabelDragDisabled(TBool aState)
       
  1197 /** Sets whether a drag operation on the boundary between two rows is to be permitted.
       
  1198 
       
  1199 @param aState ETrue, if the drag operation is to be permitted; EFalse, otherwise. */
       
  1200 	{
       
  1201 	if (aState)
       
  1202 		iFlags|=EIsSideLabelDragDisabled;
       
  1203 	else
       
  1204 		iFlags&=~EIsSideLabelDragDisabled;
       
  1205 	iHasChanged=ETrue;
       
  1206 	}
       
  1207 
       
  1208 EXPORT_C void CGridLay::SetPrintedLabels(TBool aState)
       
  1209 /** Sets whether labels are printed.
       
  1210 
       
  1211 @param aState ETrue if labels are printed; EFalse, otherwise. */
       
  1212 	{
       
  1213 	if (aState)
       
  1214 		iFlags|=EIsPrintedLabels;
       
  1215 	else
       
  1216 		iFlags&=~EIsPrintedLabels;
       
  1217 	iHasChanged=ETrue;
       
  1218 	}
       
  1219 
       
  1220 EXPORT_C void CGridLay::SetPrintedGridLines(TBool aState)
       
  1221 /** Sets whether grid lines are printed.
       
  1222 
       
  1223 @param aState ETrue if grid lines are printed; EFalse, otherwise. */
       
  1224 	{
       
  1225 	if (aState)
       
  1226 		iFlags|=EIsPrintedGridLines;
       
  1227 	else
       
  1228 		iFlags&=~EIsPrintedGridLines;
       
  1229 	iHasChanged=ETrue;
       
  1230 	}
       
  1231 
       
  1232 void CGridLay::SetVisibleToRowFullyVisible(TBool aState)
       
  1233 	{
       
  1234 	if (aState)
       
  1235 		iFlags|=EIsVisibleToRowFullyVisible;
       
  1236 	else
       
  1237 		iFlags&=~EIsVisibleToRowFullyVisible;
       
  1238 	}
       
  1239 
       
  1240 void CGridLay::SetVisibleToColumnFullyVisible(TBool aState)
       
  1241 	{
       
  1242 	if (aState)
       
  1243 		iFlags|=EIsVisibleToColumnFullyVisible;
       
  1244 	else
       
  1245 		iFlags&=~EIsVisibleToColumnFullyVisible;
       
  1246 	}
       
  1247 
       
  1248 EXPORT_C void CGridLay::SetEncroachingCellBorders(TBool aState)
       
  1249 /** Sets whether encroaching cell borders are permitted.
       
  1250 
       
  1251 Encroaching cell borders are where cell borders wider than one pixel are drawn 
       
  1252 inside the cell, as opposed to outside.
       
  1253 
       
  1254 @param aState ETrue, if encroaching cells borders are to be permitted; EFalse, 
       
  1255 otherwise. */
       
  1256 	{
       
  1257 	if (aState)
       
  1258 		iFlags|=EIsEncroachingCellBorders;
       
  1259 	else 
       
  1260 		iFlags&=~EIsEncroachingCellBorders;
       
  1261 	iHasChanged=ETrue;
       
  1262 	}
       
  1263 
       
  1264 EXPORT_C void CGridLay::SetRowSelectionDisabled(TBool aState)
       
  1265 /** Sets whether row selection is disabled.
       
  1266 
       
  1267 @param aState ETrue, if row selection is disabled; EFalse, otherwise. */
       
  1268 	{
       
  1269 	if (aState)
       
  1270 		iFlags|=EIsRowSelectionDisabled;
       
  1271 	else
       
  1272 		iFlags&=~EIsRowSelectionDisabled;
       
  1273 	iHasChanged=ETrue;
       
  1274 	}
       
  1275 
       
  1276 EXPORT_C void CGridLay::SetColumnSelectionDisabled(TBool aState)
       
  1277 /** Sets whether column selection is disabled.
       
  1278 
       
  1279 @param aState ETrue, if column selection is disabled; EFalse, otherwise. */
       
  1280 	{
       
  1281 	if (aState)
       
  1282 		iFlags|=EIsColumnSelectionDisabled;
       
  1283 	else
       
  1284 		iFlags&=~EIsColumnSelectionDisabled;
       
  1285 	iHasChanged=ETrue;
       
  1286 	}
       
  1287 
       
  1288 EXPORT_C void CGridLay::SetAutoClearGridCells(TBool aState)
       
  1289 /** Sets whether automatic clearing of grid cells is to be done.
       
  1290 
       
  1291 @param aState ETrue, if automatic clearing of grid cells is to be done; EFalse, 
       
  1292 otherwise. */
       
  1293 	{
       
  1294 	if (aState)
       
  1295 		iFlags|=EIsAutoClearGridCells;
       
  1296 	else
       
  1297 		iFlags&=~EIsAutoClearGridCells;
       
  1298 	iHasChanged=ETrue;
       
  1299 	}
       
  1300 
       
  1301 EXPORT_C void CGridLay::SetPageBreakLinesHidden(TBool aState)
       
  1302 /** Sets whether lines marking page breaks are hidden.
       
  1303 
       
  1304 @param aState ETrue, if lines marking page breaks are hidden; EFalse, otherwise. */
       
  1305 	{
       
  1306 	if (aState)
       
  1307 		iFlags|=EIsPageBreakLinesHidden;
       
  1308 	else
       
  1309 		iFlags&=~EIsPageBreakLinesHidden;
       
  1310 	iHasChanged=ETrue;
       
  1311 	}
       
  1312 
       
  1313 EXPORT_C TInt CGridLay::RowToYVal(TInt aRow) const
       
  1314 /** Converts the specified row number to a screen y-coordinate value.
       
  1315 
       
  1316 Note that the resulting value may be outside the current grid window.
       
  1317 
       
  1318 @param aRow The row number.
       
  1319 @return The y-coordinate value. */
       
  1320 	{
       
  1321 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1322 	TInt disp;
       
  1323 	iRowHeightMap->IdToDisplacement(iVisibleRange.iFrom.iRow,aRow,disp);
       
  1324 	return (iGridImg->MainPoint().iY+disp);
       
  1325 	}
       
  1326 
       
  1327 EXPORT_C TInt CGridLay::RowToYVal(TInt aStartRow,TInt aEndRow) const
       
  1328 /** Calculates the relative pixel distance between the two specified rows.
       
  1329 
       
  1330 @param aStartRow The row number of the first row.
       
  1331 @param aEndRow The row number of the second row.
       
  1332 @return The relative pixel distance. */
       
  1333 	{
       
  1334 	TInt disp;
       
  1335 	iRowHeightMap->IdToDisplacement(aStartRow,aEndRow,disp);
       
  1336 	return disp;
       
  1337 	}
       
  1338 
       
  1339 EXPORT_C TInt CGridLay::VisibleRowToYVal(TInt aRow) const
       
  1340 /** Converts the specified visible row number to a screen y-coordinate value.
       
  1341 
       
  1342 Note that the resulting value may be outside the current grid window.
       
  1343 
       
  1344 @param aRow The row number of the visible row.
       
  1345 @return The y-coordinate value. Note that this is -1, if the row is not visible. */
       
  1346 	{
       
  1347 	if (aRow>iVisibleRange.iTo.iRow)
       
  1348 		return -1;
       
  1349 	if (aRow<iVisibleRange.iFrom.iRow)
       
  1350 		{
       
  1351 		if (IsHorizontalTitleLine())
       
  1352 			{
       
  1353 			if (aRow<iTitleRange.iFrom.iRow || aRow>=iTitleRange.iTo.iRow)
       
  1354 				return -1;
       
  1355 			return TitleRowToYVal(aRow);
       
  1356 			}
       
  1357 		return -1;
       
  1358 		}
       
  1359 	return RowToYVal(aRow);
       
  1360 	}
       
  1361 
       
  1362 EXPORT_C TInt CGridLay::TitleRowToYVal(TInt aTitleRow) const
       
  1363 /** Calculates the relative pixel distance between the specified row and the first 
       
  1364 title row.
       
  1365 
       
  1366 @param aTitleRow The row number.
       
  1367 @return The relative pixel distance. */
       
  1368 	{
       
  1369 	__ASSERT_DEBUG(IsHorizontalTitleLine(),Panic(EGridLayNoTitles));
       
  1370 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1371 	TInt disp;
       
  1372 	iRowHeightMap->IdToDisplacement(iTitleRange.iFrom.iRow,aTitleRow,disp);
       
  1373 	return (iGridImg->TitlePoint().iY+disp);
       
  1374 	}
       
  1375 
       
  1376 EXPORT_C TInt CGridLay::ColumnToXVal(TInt aCol) const
       
  1377 /** Converts the specified column number to a screen x-coordinate value.
       
  1378 
       
  1379 Note that the resulting value may be outside the current grid window.
       
  1380 
       
  1381 @param aCol The column number.
       
  1382 @return The column's x-coordinate value.
       
  1383 @panic GRIDIMG 3 In debug mode, if this grid layout object has no grid image. */
       
  1384 	{
       
  1385 	//
       
  1386 	// Converts the passed column to a relative screen 'X' coordinate.
       
  1387 	//
       
  1388 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1389 	TInt disp;
       
  1390 	iColumnWidthMap->IdToDisplacement(iVisibleRange.iFrom.iCol,aCol,disp);
       
  1391 	return (iGridImg->MainPoint().iX+disp);
       
  1392 	}
       
  1393 
       
  1394 EXPORT_C TInt CGridLay::ColumnToXVal(TInt aStartCol,TInt aEndCol) const
       
  1395 /** Gets the distance, in pixels, between the two specified columns.
       
  1396 
       
  1397 @param aStartCol The first (start) column number.
       
  1398 @param aEndCol The second (end) column number.
       
  1399 @return The distance, in pixels. */
       
  1400 	{
       
  1401 	TInt disp;
       
  1402 	iColumnWidthMap->IdToDisplacement(aStartCol,aEndCol,disp);
       
  1403 	return disp;
       
  1404 	}
       
  1405 
       
  1406 EXPORT_C TInt CGridLay::VisibleColumnToXVal(TInt aCol) const
       
  1407 /** Converts the specified visible column number to a screen x-coordinate value.
       
  1408 
       
  1409 Note that the resulting value may be outside the current grid window.
       
  1410 
       
  1411 @param aCol The column number of the visible column.
       
  1412 @return The x-coordinate value. Note that this is -1, if the column is not 
       
  1413 visible. */
       
  1414 	{
       
  1415 	if (aCol>iVisibleRange.iTo.iCol)
       
  1416 		return -1;
       
  1417 	if (aCol<iVisibleRange.iFrom.iCol)
       
  1418 		{
       
  1419 		if (IsVerticalTitleLine())
       
  1420 			{
       
  1421 			if (aCol<iTitleRange.iFrom.iCol || aCol>=iTitleRange.iTo.iCol)
       
  1422 				return -1;
       
  1423 			return TitleColumnToXVal(aCol);
       
  1424 			}
       
  1425 		return -1;
       
  1426 		}
       
  1427 	return ColumnToXVal(aCol);
       
  1428 	}
       
  1429 
       
  1430 EXPORT_C TInt CGridLay::TitleColumnToXVal(TInt aTitleCol) const
       
  1431 /** Calculates the relative pixel distance between the specified column and the 
       
  1432 first title column.
       
  1433 
       
  1434 @param aTitleCol The column number.
       
  1435 @return The relative pixel distance. */
       
  1436 	{
       
  1437 	__ASSERT_DEBUG(IsVerticalTitleLine(),Panic(EGridLayNoTitles));
       
  1438 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1439 	TInt disp;
       
  1440 	iColumnWidthMap->IdToDisplacement(iTitleRange.iFrom.iCol,aTitleCol,disp);
       
  1441 	return (iGridImg->TitlePoint().iX+disp);
       
  1442 	}
       
  1443 
       
  1444 EXPORT_C TPoint CGridLay::CellToPoint(const TCellRef &aCell) const
       
  1445 /** Gets the relative screen coordinates of the top left corner of the specified 
       
  1446 cell.
       
  1447 
       
  1448 @param aCell The cell.
       
  1449 @return The relative screen co-ordinates. */
       
  1450 	{
       
  1451 	return TPoint(ColumnToXVal(aCell.iCol),RowToYVal(aCell.iRow));
       
  1452 	}
       
  1453 
       
  1454 EXPORT_C TPoint CGridLay::CellToPoint(const TCellRef &aStartCell,const TCellRef &aEndCell) const
       
  1455 /** Gets the co-ordinate distance, in pixels, between the specified cells.
       
  1456 
       
  1457 @param aStartCell The start cell of the range.
       
  1458 @param aEndCell The end cell of the range.
       
  1459 @return The x and y values representing the distance, in pixels, between the 
       
  1460 two columns and the two rows, respectively, that are defined by the two cells. */
       
  1461 	{
       
  1462 	return TPoint(ColumnToXVal(aStartCell.iCol,aEndCell.iCol),RowToYVal(aStartCell.iRow,aEndCell.iRow));
       
  1463 	}
       
  1464 
       
  1465 EXPORT_C TPoint CGridLay::TitleCellToPoint(const TCellRef& aTitleCell) const
       
  1466 /** Gets the relative screen coordinates of the top left corner of the specified 
       
  1467 cell, when title lines are displayed.
       
  1468 
       
  1469 @param aTitleCell The cell.
       
  1470 @return The relative screen co-ordinates.
       
  1471 @panic GRIDIMG 3 In debug mode, if this grid layout object has no grid image.
       
  1472 @panic GRIDIMG 4 In debug mode, if there is no horizontal title line and/or 
       
  1473 there is no vertical title line. */
       
  1474 	{
       
  1475 	__ASSERT_DEBUG(IsHorizontalTitleLine(),Panic(EGridLayNoTitles));
       
  1476 	__ASSERT_DEBUG(IsVerticalTitleLine(),Panic(EGridLayNoTitles));
       
  1477 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1478 	TPoint point;
       
  1479 	iColumnWidthMap->IdToDisplacement(iTitleRange.iFrom.iCol,aTitleCell.iCol,point.iX);
       
  1480 	iRowHeightMap->IdToDisplacement(iTitleRange.iFrom.iRow,aTitleCell.iRow,point.iY);
       
  1481 	return point+iGridImg->TitlePoint();
       
  1482 	}
       
  1483 
       
  1484 EXPORT_C TRect CGridLay::CellToRect(const TCellRef& aCell) const
       
  1485 /** Gets the rectangle that is occupied by the specified cell.
       
  1486 
       
  1487 @param aCell The cell.
       
  1488 @return The occupied rectangle. Note that this excludes the cell's bottom and 
       
  1489 right grid lines. */
       
  1490 	{
       
  1491 	TRect rect(CellToPoint(aCell),TSize(0,0));
       
  1492 	rect.iBr.iX+=ColumnWidthInPixels(aCell.iCol)-1;
       
  1493 	rect.iBr.iY+=RowHeightInPixels(aCell.iRow)-1;
       
  1494 	return rect;
       
  1495 	}
       
  1496 
       
  1497 EXPORT_C TInt CGridLay::YValToRow(TInt aYVal) const
       
  1498 /** Gets the number of the row, limited to the grid boundary, that is on or above 
       
  1499 the specified y-coordinate value.
       
  1500 
       
  1501 @param aYVal The y-coordinate value. Note that this may represent a point 
       
  1502 off the visible screen.
       
  1503 @return The row number, limited to the grid boundary. */
       
  1504 	{
       
  1505 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1506 	TInt tempYVal = iGridImg->MainPoint().iY;
       
  1507 	return YValToRow(iVisibleRange.iFrom.iRow,aYVal-tempYVal);
       
  1508 	}
       
  1509 
       
  1510 EXPORT_C TInt CGridLay::YValToRow(TInt aStartRow,TInt aDisp) const
       
  1511 /** Gets the number of the row that is on or above the specified displacement from 
       
  1512 the specified row.
       
  1513 
       
  1514 @param aStartRow The row from which displacement is calculated.
       
  1515 @param aDisp The displacement, in pixels.
       
  1516 @return The row number at the specified displacement. */
       
  1517 	{
       
  1518 	TInt row;
       
  1519 	iRowHeightMap->DisplacementToId(aStartRow,aDisp,row);
       
  1520 	StepRowBackward(row);
       
  1521 	return(row);
       
  1522 	}
       
  1523 
       
  1524 EXPORT_C TInt CGridLay::YValToTitleRow(TInt aYVal) const
       
  1525 /** Gets the number of the row that is on or above the specified y-coordinate value
       
  1526 
       
  1527 @param aYVal The y-coordinate value. Note that this may represent a point 
       
  1528 off the visible screen.
       
  1529 @return The row number. Note that this may include the title row. */
       
  1530 	{
       
  1531 	__ASSERT_DEBUG(IsHorizontalTitleLine(),Panic(EGridLayNoTitles));
       
  1532 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1533 	TInt tempYVal = iGridImg->TitlePoint().iY;
       
  1534 	return YValToRow(iTitleRange.iFrom.iRow,aYVal-tempYVal);
       
  1535 	}
       
  1536 
       
  1537 EXPORT_C TInt CGridLay::XValToColumn(TInt aXVal) const
       
  1538 /** Gets the number of the column, limited to the grid boundary, that is on or 
       
  1539 to the left of the specified x-coordinate value.
       
  1540 
       
  1541 @param aXVal The x-coordinate value. Note that this may represent a point 
       
  1542 off the visible screen.
       
  1543 @return The column number, limited to the grid boundary. */
       
  1544 	{
       
  1545 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1546 	TInt tempXVal=iGridImg->MainPoint().iX;
       
  1547 	return XValToColumn(iVisibleRange.iFrom.iCol,aXVal-tempXVal);
       
  1548 	}
       
  1549 
       
  1550 EXPORT_C TInt CGridLay::XValToColumn(TInt aStartCol,TInt aDisp) const
       
  1551 /** Gets the number of the column that is on or to the left of the specified displacement 
       
  1552 from the specified column.
       
  1553 
       
  1554 @param aStartCol The column from which displacement is calculated.
       
  1555 @param aDisp The displacement, in pixels.
       
  1556 @return The column number at the specified displacement. */
       
  1557 	{
       
  1558 	TInt column;
       
  1559 	iColumnWidthMap->DisplacementToId(aStartCol,aDisp,column);
       
  1560 	StepColumnBackward(column);
       
  1561 	return(column);
       
  1562 	}
       
  1563 
       
  1564 EXPORT_C TInt CGridLay::XValToTitleColumn(TInt aXVal) const
       
  1565 /** Gets the number of the column that is on or to the left of the specified x-coordinate 
       
  1566 value
       
  1567 
       
  1568 @param aXVal The x-coordinate value. Note that this may represent a point 
       
  1569 off the visible screen.
       
  1570 @return The column number. Note that this may include the title column. */
       
  1571 	{
       
  1572 	__ASSERT_DEBUG(IsVerticalTitleLine(),Panic(EGridLayNoTitles));
       
  1573 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1574 	TInt tempXVal=iGridImg->TitlePoint().iX;
       
  1575 	return XValToColumn(iTitleRange.iFrom.iCol,aXVal-tempXVal);
       
  1576 	}
       
  1577 
       
  1578 EXPORT_C TCellRef CGridLay::PointToCell(const TPoint &aPoint) const
       
  1579 /** Gets the cell reference of the cell that contains the specified screen co-ordinates.
       
  1580 
       
  1581 @param aPoint The screen co-ordinates.
       
  1582 @return The cell reference. */
       
  1583 	{
       
  1584 	return TCellRef(YValToRow(aPoint.iY),XValToColumn(aPoint.iX));
       
  1585 	}
       
  1586 
       
  1587 EXPORT_C TCellRef CGridLay::PointToCell(const TCellRef &aStartCell,const TPoint &aPointDisp) const
       
  1588 /** Gets the cell reference of the cell that is displaced from the specified cell 
       
  1589 by the specified pixel co-ordinates.
       
  1590 
       
  1591 @param aStartCell The cell reference from which the displacement is based.
       
  1592 @param aPointDisp The displacement.
       
  1593 @return The cell at the specified displacement. */
       
  1594 	{
       
  1595 	return TCellRef(YValToRow(aStartCell.iRow,aPointDisp.iY),XValToColumn(aStartCell.iCol,aPointDisp.iX));
       
  1596 	}
       
  1597 
       
  1598 EXPORT_C TSize CGridLay::TopLeftTitleRangeSize() const
       
  1599 /** Gets the size of the top left range, if title lines are on.
       
  1600 
       
  1601 The top left range is the range of cells formed by the intersection of the 
       
  1602 rows and columns that form the titles.
       
  1603 
       
  1604 @return The size of the top left range. */
       
  1605 	{
       
  1606 	TSize ret;
       
  1607 	if (IsHorizontalTitleLine())
       
  1608 		iRowHeightMap->IdToDisplacement(iTitleRange.iFrom.iRow,iTitleRange.iTo.iRow,ret.iHeight);
       
  1609 	if (IsVerticalTitleLine())
       
  1610 		iColumnWidthMap->IdToDisplacement(iTitleRange.iFrom.iCol,iTitleRange.iTo.iCol,ret.iWidth);
       
  1611 	return ret;
       
  1612 	}
       
  1613 
       
  1614 EXPORT_C TInt CGridLay::YValToNearestRow(TInt aStartRow,TInt aDisp) const
       
  1615 /** Gets the row that is nearest to the specified displacement from the specified 
       
  1616 row.
       
  1617 
       
  1618 @param aStartRow The row on which the displacement is based.
       
  1619 @param aDisp The displacement value, in pixels.
       
  1620 @return The nearest row. */
       
  1621 	{
       
  1622 	TInt topRow;
       
  1623 	iRowHeightMap->DisplacementToId(aStartRow,aDisp,topRow);
       
  1624 	StepRowForward(topRow);
       
  1625 	TInt topYVal;
       
  1626 	iRowHeightMap->IdToDisplacement(aStartRow,topRow,topYVal);
       
  1627 	TInt bottomYVal = topYVal+RowHeightInPixels(topRow);
       
  1628 	if ((aDisp-topYVal)>=(bottomYVal-aDisp))
       
  1629 		StepRowForward(++topRow);
       
  1630 	return (topRow);
       
  1631 	}
       
  1632 
       
  1633 EXPORT_C TInt CGridLay::XValToNearestColumn(TInt aStartCol,TInt aDisp) const
       
  1634 /** Gets the column that is nearest to the specified displacement from the specified 
       
  1635 column.
       
  1636 
       
  1637 @param aStartCol The column on which the displacement is based.
       
  1638 @param aDisp The displacement value, in pixels.
       
  1639 @return The nearest column. */
       
  1640 	{
       
  1641 	TInt leftCol;
       
  1642 	iColumnWidthMap->DisplacementToId(aStartCol,aDisp,leftCol);
       
  1643 	StepColumnForward(leftCol);
       
  1644 	TInt leftXVal;
       
  1645 	iColumnWidthMap->IdToDisplacement(aStartCol,leftCol,leftXVal);
       
  1646 	TInt rightXVal = leftXVal+ColumnWidthInPixels(leftCol);
       
  1647 	if ((aDisp-leftXVal)>=(rightXVal-aDisp))
       
  1648 		StepColumnForward(++leftCol);
       
  1649 	return (leftCol);
       
  1650 	}
       
  1651 
       
  1652 TPoint CGridLay::CalcOffsetBetweenCells(const TCellRef& aCell1,
       
  1653 	const TCellRef& aCell2) const
       
  1654 //
       
  1655 // Returns the scrolling offset required to get from aCell1 to aCell2
       
  1656 	{
       
  1657 	TPoint offset;
       
  1658 	iColumnWidthMap->IdToDisplacement(aCell2.iCol,aCell1.iCol,offset.iX);
       
  1659 	iRowHeightMap->IdToDisplacement(aCell2.iRow,aCell1.iRow,offset.iY);
       
  1660 	return offset;
       
  1661 	}
       
  1662 
       
  1663 TInt CGridLay::CalcVisibleFromRowAfterPageScroll(TMoveDirectionAndAmount aPageScroll) const
       
  1664 //
       
  1665 // Calculates what iVisibleRange.iFrom.iRow would be after aPageScroll but doesn't actually set it
       
  1666 	{
       
  1667 	TInt newFromRow;
       
  1668 	switch (aPageScroll)
       
  1669 		{
       
  1670 	case EMovePageDown:
       
  1671 		CalcVisibleFromRow(iVisibleRange.iFrom.iRow+1,newFromRow);
       
  1672 		if (newFromRow>iVisibleRange.iFrom.iRow)
       
  1673 			newFromRow=iVisibleRange.iFrom.iRow;
       
  1674 		break;
       
  1675 	case EMovePageUp:
       
  1676 		{
       
  1677 		TInt corr=IsVisibleToRowFullyVisible() ? 0 : 1;
       
  1678 		corr=(CalcVisibleToRow(iVisibleRange.iTo.iRow-corr,newFromRow))	? 1 : 0;	// correct if fully visible
       
  1679 		if (newFromRow == iVisibleRange.iTo.iRow)
       
  1680 			newFromRow = iVisibleRange.iTo.iRow - 1;
       
  1681 		else
       
  1682 			CalcVisibleFromRow(newFromRow+corr,newFromRow);
       
  1683 		if (newFromRow<iVisibleRange.iFrom.iRow)
       
  1684 			newFromRow=iVisibleRange.iFrom.iRow;
       
  1685 		}
       
  1686 		break;
       
  1687 	default:
       
  1688 		newFromRow=iVisibleRange.iFrom.iRow;
       
  1689 		break;
       
  1690 		}
       
  1691 	return newFromRow;
       
  1692 	}
       
  1693 
       
  1694 TInt CGridLay::CalcVisibleFromColumnAfterPageScroll(TMoveDirectionAndAmount aPageScroll) const
       
  1695 	{
       
  1696 	TInt newFromColumn;
       
  1697 	switch (aPageScroll)
       
  1698 		{
       
  1699 	case EMovePageRight:
       
  1700 		CalcVisibleFromColumn(iVisibleRange.iFrom.iCol+1,newFromColumn);
       
  1701 		if (newFromColumn>iVisibleRange.iFrom.iCol)
       
  1702 			newFromColumn=iVisibleRange.iFrom.iCol;
       
  1703 		break;
       
  1704 	case EMovePageLeft:
       
  1705 		{
       
  1706 		TInt corr=IsVisibleToColumnFullyVisible() ? 0 : 1;
       
  1707 		corr=(CalcVisibleToColumn(iVisibleRange.iTo.iCol-corr,newFromColumn)) ? 1 : 0;
       
  1708 		if (newFromColumn == iVisibleRange.iTo.iCol)
       
  1709 			newFromColumn = iVisibleRange.iTo.iCol - 1;
       
  1710 		else
       
  1711 			CalcVisibleFromColumn(newFromColumn+corr,newFromColumn);
       
  1712 		if (newFromColumn<iVisibleRange.iFrom.iCol)
       
  1713 			newFromColumn=iVisibleRange.iFrom.iCol;
       
  1714 		}
       
  1715 		break;
       
  1716 	default:
       
  1717 		newFromColumn=iVisibleRange.iFrom.iCol;
       
  1718 		break;
       
  1719 		}
       
  1720 	return newFromColumn;
       
  1721 	}
       
  1722 
       
  1723 TCellRef CGridLay::CalcVisibleFromCellAfterPageScroll(TMoveDirectionAndAmount aPageScroll) const
       
  1724 	{
       
  1725 	return TCellRef(CalcVisibleFromRowAfterPageScroll(aPageScroll),
       
  1726 		CalcVisibleFromColumnAfterPageScroll(aPageScroll));
       
  1727 	}
       
  1728 
       
  1729 void CGridLay::CalcVisibleFromRow(TInt aVisibleToRow,TInt& aNewVisibleFromRow) const
       
  1730 	{
       
  1731 	//
       
  1732 	// Calculates what the VisibleRange.iFrom.iRow would be for a given
       
  1733 	// VisibleRange.iTo.iRow.
       
  1734 	//
       
  1735 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1736 	TInt disp=-iGridImg->MainRect().Height()-1;
       
  1737 	iRowHeightMap->DisplacementToId(aVisibleToRow,disp,aNewVisibleFromRow);
       
  1738 	aNewVisibleFromRow++;
       
  1739 	if (IsIndefiniteRowBoundaries())
       
  1740 		{
       
  1741 		if (!RequestRow(aNewVisibleFromRow,aNewVisibleFromRow))
       
  1742 			aNewVisibleFromRow=aVisibleToRow;
       
  1743 		}
       
  1744 	else
       
  1745 		aNewVisibleFromRow=Max(aNewVisibleFromRow,MinVisibleFromRow());
       
  1746 	StepRowForward(aNewVisibleFromRow);
       
  1747 	}
       
  1748 
       
  1749 TBool CGridLay::CalcVisibleToRow(TInt aVisibleFromRow,TInt& aNewVisibleToRow) const
       
  1750 	{
       
  1751 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1752 	TInt disp=iGridImg->MainRect().Height()+1;
       
  1753 	TBool isExactDisp=iRowHeightMap->DisplacementToId(aVisibleFromRow,disp,aNewVisibleToRow);
       
  1754 	if (isExactDisp)
       
  1755 		aNewVisibleToRow--;
       
  1756 	if (IsIndefiniteRowBoundaries())
       
  1757 		{
       
  1758 		if (RequestRow(TInt(aNewVisibleToRow-1),aNewVisibleToRow))
       
  1759 			aNewVisibleToRow++;
       
  1760 		else
       
  1761 			aNewVisibleToRow=aVisibleFromRow;
       
  1762 		}
       
  1763 	else
       
  1764 		aNewVisibleToRow=Min(aNewVisibleToRow,iGridRange.iTo.iRow+1);
       
  1765 	return isExactDisp;
       
  1766 	}
       
  1767 
       
  1768 void CGridLay::CalcVisibleFromColumn(TInt aVisibleToCol,TInt& aNewVisibleFromCol) const
       
  1769 	{
       
  1770 	//
       
  1771 	// Calculates what the VisibleRange.iFrom.iCol would be for a given
       
  1772 	// VisibleRange.iTo.iCol.
       
  1773 	//
       
  1774 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1775 	TInt disp=-iGridImg->MainRect().Width()-1;
       
  1776 	iColumnWidthMap->DisplacementToId(aVisibleToCol,disp,aNewVisibleFromCol);
       
  1777 	aNewVisibleFromCol++;
       
  1778 	aNewVisibleFromCol=Max(aNewVisibleFromCol,MinVisibleFromColumn());
       
  1779 	StepColumnForward(aNewVisibleFromCol);	//Guarantees to be on a non-zero width column
       
  1780 	}
       
  1781 
       
  1782 TBool CGridLay::CalcVisibleToColumn(TInt aVisibleFromCol,TInt& aNewVisibleToCol) const
       
  1783 	{
       
  1784 	__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  1785 	TInt disp=iGridImg->MainRect().Width()+1;
       
  1786 	TBool isExactDisp=iColumnWidthMap->DisplacementToId(aVisibleFromCol,disp,aNewVisibleToCol);
       
  1787 	if (isExactDisp)
       
  1788 		aNewVisibleToCol--;
       
  1789 	aNewVisibleToCol=Min(aNewVisibleToCol,iGridRange.iTo.iCol+1);
       
  1790 	return isExactDisp;
       
  1791 	}
       
  1792 
       
  1793 EXPORT_C void CGridLay::ResetVisibleToRow()
       
  1794 //
       
  1795 // Resets iVisibleRange.iTo.iRow given iVisibleRange.iFrom.iRow.
       
  1796 /** Resets the row number of the row that should be visible at the bottom of the 
       
  1797 visible area of the grid. */
       
  1798 	{
       
  1799 	if (!iGridImg)
       
  1800 		return;
       
  1801 	TBool isExactDisp=CalcVisibleToRow(iVisibleRange.iFrom.iRow,iVisibleRange.iTo.iRow);
       
  1802 	SetVisibleToRowFullyVisible(isExactDisp);
       
  1803 	}
       
  1804 
       
  1805 EXPORT_C void CGridLay::ResetVisibleToColumn()
       
  1806 /** Resets the column number of the column visible at the right of the visible 
       
  1807 area of the grid. */
       
  1808 	{
       
  1809 	if (!iGridImg)
       
  1810 		return;
       
  1811 	TBool isExactDisp=CalcVisibleToColumn(iVisibleRange.iFrom.iCol,iVisibleRange.iTo.iCol);
       
  1812 	SetVisibleToColumnFullyVisible(isExactDisp);
       
  1813 	}
       
  1814 
       
  1815 EXPORT_C void CGridLay::ResetVisibleToCell()
       
  1816 /** Resets the row and column numbers visible at the bottom, and to the right, 
       
  1817 of the visible area of the grid. */
       
  1818 	{
       
  1819 	ResetVisibleToRow();
       
  1820 	ResetVisibleToColumn();
       
  1821 	}
       
  1822 
       
  1823 TBool CGridLay::IsCellOutOfVisibleRange(const TCellRef &aCell) const
       
  1824 //
       
  1825 // Return ETrue if aCell is outside the visible grid (including title range)
       
  1826 	{
       
  1827 	if (aCell.iRow>=iVisibleRange.iTo.iRow || aCell.iCol>=iVisibleRange.iTo.iCol)
       
  1828 		return ETrue;
       
  1829 	if (aCell.iRow<iVisibleRange.iFrom.iRow)
       
  1830 		{
       
  1831 		TBool inRange=EFalse;
       
  1832 		if (IsHorizontalTitleLine())
       
  1833 			{
       
  1834 			if (aCell.iRow<iTitleRange.iTo.iRow && aCell.iRow>=iTitleRange.iFrom.iRow)
       
  1835 				inRange=ETrue;
       
  1836 			}
       
  1837 		if (!inRange)
       
  1838 			return ETrue;
       
  1839 		}
       
  1840 	if (aCell.iCol<iVisibleRange.iFrom.iCol)
       
  1841 		{
       
  1842 		TBool inRange=EFalse;
       
  1843 		if (IsVerticalTitleLine())
       
  1844 			{
       
  1845 			if (aCell.iCol<iTitleRange.iTo.iCol && aCell.iCol>=iTitleRange.iFrom.iCol)
       
  1846 				inRange=ETrue;
       
  1847 			}
       
  1848 		if (!inRange)
       
  1849 			return ETrue;
       
  1850 		}
       
  1851 	return EFalse;
       
  1852 	}
       
  1853 
       
  1854 TBool CGridLay::IsCellOutOfGridRange(const TCellRef& aCell) const
       
  1855 // Similar to LimitCell but Doesn't alter aCell
       
  1856 	{
       
  1857 	TCellRef cell=aCell;
       
  1858 	return !LimitCell(cell);
       
  1859 	}
       
  1860 
       
  1861 TBool CGridLay::LimitRow(TInt &aRow) const
       
  1862 	{
       
  1863 	TInt newRow;
       
  1864 	TBool ret=RequestRow(aRow,newRow);
       
  1865 	if (ret)
       
  1866 		{
       
  1867 		if (newRow<aRow)
       
  1868 			StepRowBackward(newRow);
       
  1869 		else if (newRow>aRow)
       
  1870 			StepRowForward(newRow);
       
  1871 		}
       
  1872 	aRow=newRow;
       
  1873 	return ret;
       
  1874 	}
       
  1875 
       
  1876 TBool CGridLay::LimitColumn(TInt &aCol) const
       
  1877 	{
       
  1878 	if (iGridRange.iFrom.iCol>iGridRange.iTo.iCol)
       
  1879 		return EFalse;
       
  1880 	LimitColumn(aCol,iGridRange.iFrom.iCol,iGridRange.iTo.iCol);
       
  1881 	return ETrue;
       
  1882  	}
       
  1883 
       
  1884 void CGridLay::LimitRow(TInt& aRow,TInt aLowerLimit,TInt aUpperLimit) const
       
  1885 	{
       
  1886 	if (aRow>aUpperLimit)
       
  1887 		{
       
  1888 		aRow=aUpperLimit;
       
  1889 		StepRowBackward(aRow);
       
  1890 		}
       
  1891 	else if (aRow<aLowerLimit)
       
  1892 		{
       
  1893 		aRow=aLowerLimit;
       
  1894 		StepRowForward(aRow);
       
  1895 		}
       
  1896 	}
       
  1897 
       
  1898 void CGridLay::LimitColumn(TInt& aCol,TInt aLowerLimit,TInt aUpperLimit) const
       
  1899 	{
       
  1900  	if (aCol>aUpperLimit)
       
  1901 		{
       
  1902 		aCol=aUpperLimit;
       
  1903 		StepColumnBackward(aCol);
       
  1904         if (aCol<aLowerLimit)
       
  1905             aCol=aLowerLimit;
       
  1906 		}
       
  1907 	else if (aCol<aLowerLimit)
       
  1908 		{
       
  1909 		aCol=aLowerLimit;
       
  1910 		StepColumnForward(aCol);
       
  1911         if (aCol>aUpperLimit)
       
  1912             aCol=aUpperLimit;
       
  1913 		}
       
  1914 	}
       
  1915 
       
  1916 TBool CGridLay::LimitCell(TCellRef &aCell) const
       
  1917 // Keeps the cell within the grid boundary. Returns EFalse if unable to do so
       
  1918 	{
       
  1919 	TBool canLimitRow=LimitRow(aCell.iRow);
       
  1920 	return (LimitColumn(aCell.iCol) && canLimitRow);
       
  1921 	}
       
  1922 
       
  1923 /*EXPORT_C void CGridLay::LimitCell(TCellRef &aCell,const TRangeRef &aLimitRange) const
       
  1924 	{
       
  1925 	LimitRow(aCell.iRow,aLimitRange.iFrom.iRow,aLimitRange.iTo.iRow);
       
  1926 	LimitColumn(aCell.iCol,aLimitRange.iFrom.iCol,aLimitRange.iTo.iCol);
       
  1927 	}*/
       
  1928 
       
  1929 void CGridLay::LimitRowToVisible(TInt& aRow) const
       
  1930 	{
       
  1931 	if (IsIndefiniteRowBoundaries())
       
  1932 		LimitRow(aRow);
       
  1933 	else
       
  1934 		{
       
  1935 		TInt minRow=MinVisibleFromRow();
       
  1936 		if (minRow>iGridRange.iTo.iRow)
       
  1937 			{
       
  1938 			aRow=minRow;
       
  1939 			return;
       
  1940 			}
       
  1941 		LimitRow(aRow,minRow,iGridRange.iTo.iRow);
       
  1942 		}
       
  1943 	}
       
  1944 
       
  1945 void CGridLay::LimitColumnToVisible(TInt& aCol) const
       
  1946 	{
       
  1947 	TInt minCol=MinVisibleFromColumn();
       
  1948 	if (minCol>iGridRange.iTo.iCol)
       
  1949 		{
       
  1950 		aCol=minCol;
       
  1951 		return;
       
  1952 		}
       
  1953 	LimitColumn(aCol,minCol,iGridRange.iTo.iCol);
       
  1954 	}
       
  1955 
       
  1956 void CGridLay::LimitCellToVisible(TCellRef& aCell) const
       
  1957 	{
       
  1958 	LimitRowToVisible(aCell.iRow);
       
  1959 	LimitColumnToVisible(aCell.iCol);
       
  1960 	}
       
  1961 
       
  1962 void CGridLay::StepRowForward(TInt& aRow) const
       
  1963 // Steps row forward to the nearest non zero row
       
  1964 	{
       
  1965 	for (;!RowHeightInPixels(aRow);aRow++)
       
  1966 		;
       
  1967 	}
       
  1968 
       
  1969 void CGridLay::StepRowBackward(TInt& aRow) const
       
  1970 	{
       
  1971 	for (;!RowHeightInPixels(aRow);aRow--)
       
  1972 		;
       
  1973 	}
       
  1974 
       
  1975 void CGridLay::StepColumnForward(TInt& aCol) const
       
  1976 	{
       
  1977 	for (;!ColumnWidthInPixels(aCol);aCol++)
       
  1978 		;
       
  1979 	}
       
  1980 
       
  1981 void CGridLay::StepColumnBackward(TInt& aCol) const
       
  1982 	{
       
  1983 	for (;!ColumnWidthInPixels(aCol);aCol--)
       
  1984 		;
       
  1985 	}
       
  1986 
       
  1987 EXPORT_C TInt CGridLay::MinVisibleFromRow() const
       
  1988 /** Gets the number of the topmost row visible in the grid.
       
  1989 
       
  1990 @return The row number if successful else KErrUnknown. */
       
  1991 	{
       
  1992 	TInt minRow;
       
  1993 	if (IsIndefiniteRowBoundaries())
       
  1994 		{
       
  1995 		if(!RequestRow(-KMaxTInt,minRow))	// Result is undefined if request row is false
       
  1996 			{
       
  1997 			return KErrUnknown;
       
  1998 			}
       
  1999 		}
       
  2000 	else
       
  2001 		minRow=(IsHorizontalTitleLine())?iTitleRange.iTo.iRow:iGridRange.iFrom.iRow;
       
  2002 	StepRowForward(minRow);
       
  2003 	return minRow;
       
  2004 	}
       
  2005 
       
  2006 EXPORT_C TInt CGridLay::MinVisibleFromColumn() const
       
  2007 /** Gets the number of the leftmost column visible in the grid.
       
  2008 
       
  2009 @return The column number. */
       
  2010 	{
       
  2011 	TInt minCol=(IsVerticalTitleLine())?iTitleRange.iTo.iCol:iGridRange.iFrom.iCol;
       
  2012 	StepColumnForward(minCol);
       
  2013 	return minCol;
       
  2014 	}
       
  2015 
       
  2016 EXPORT_C void CGridLay::PaginateL()
       
  2017 /** Paginates the grid.
       
  2018 
       
  2019 Note that when preparing the grid for printing using a CGridPrinter object, 
       
  2020 then use that object's CGridPrinter::PaginateL() function instead. */
       
  2021 	{
       
  2022 	if (IsPaginated() || !iGraphicsDeviceMap)
       
  2023 		return;
       
  2024 	__ASSERT_DEBUG(iRowPageMap==NULL && iColumnPageMap==NULL,Panic(EGridLayPageMapAlreadyExists));
       
  2025 	iRowPageMap = CSparseMap::NewL();
       
  2026 	iColumnPageMap = CSparseMap::NewL();
       
  2027 
       
  2028 	__ASSERT_DEBUG(iPageSizeInTwips.iWidth!=0 && iPageSizeInTwips.iHeight!=0,
       
  2029  		Panic(EGridLayNoPageSizeSet));
       
  2030 	TPoint pageSizeInPixels=iGraphicsDeviceMap->TwipsToPixels(iPageSizeInTwips.AsPoint());
       
  2031 	if (IsPrintedLabels())
       
  2032 		{
       
  2033 		__ASSERT_DEBUG(iGridImg!=NULL,Panic(EGridLayInvalidGridImg));
       
  2034 		if (IsSideLabels())
       
  2035 			pageSizeInPixels.iX-=iGridImg->MaxSideLabelWidthInPixels();
       
  2036 		if (IsTopLabels())
       
  2037 			pageSizeInPixels.iY-=iGridImg->TopLabelHeightInPixels();
       
  2038 		}
       
  2039 	DoMainPaginationLoopL(pageSizeInPixels.iX,iColumnWidthMap,iColumnPageMap,
       
  2040 		iHardColumnPageBreaks,iGridRange.iFrom.iCol);
       
  2041 	TInt startRow;
       
  2042 	if (RequestRow(-KMaxTInt,startRow))
       
  2043 		{
       
  2044 		DoMainPaginationLoopL(pageSizeInPixels.iY,iRowHeightMap,iRowPageMap,
       
  2045 			iHardRowPageBreaks,startRow);
       
  2046 		}
       
  2047 	iFlags|=EIsPaginated;
       
  2048 	iHasChanged=ETrue;
       
  2049 	}
       
  2050 
       
  2051 void CGridLay::DoMainPaginationLoopL(TInt aPageSpan,CSparseMap* aCellSpanMap,CSparseMap* aPageMap,
       
  2052 	CArrayFix<TInt>* aHardPageBreaks,TInt aStartId)
       
  2053 	{
       
  2054 	__ASSERT_DEBUG(aCellSpanMap->DefaultValueInPixels(),Panic(EGridMapDefaultValueIsZero));
       
  2055 	TInt defIdsPerPage = aPageSpan/aCellSpanMap->DefaultValueInPixels();
       
  2056 	if (defIdsPerPage==0)
       
  2057 		defIdsPerPage=1;	// Should always print at least 1 row/column per page
       
  2058 	aPageMap->SetDefaultValueInPixels(defIdsPerPage);//!!!Misleading Units
       
  2059 	TInt softCount=aCellSpanMap->Count();
       
  2060 	TInt hardCount=aHardPageBreaks->Count();
       
  2061 	TInt currPage=0;
       
  2062 	TInt softPos=0;
       
  2063 	TInt hardPos=0;
       
  2064 	while (softPos<softCount || hardPos<hardCount)
       
  2065 		{
       
  2066 		TInt nextSoftId=(softPos<softCount) ? (*aCellSpanMap)[softPos].iId : KMaxTInt;
       
  2067 		if (aStartId>nextSoftId)
       
  2068 			{
       
  2069 			softPos++;
       
  2070 			continue;
       
  2071 			}
       
  2072 		TInt nextHardPb=(hardPos<hardCount) ? (*aHardPageBreaks)[hardPos] : KMaxTInt;
       
  2073 		TInt nextId=Min(nextSoftId,nextHardPb);
       
  2074 		TInt pageSteps=(nextId-aStartId)/defIdsPerPage;
       
  2075 		currPage+=pageSteps;
       
  2076 		aStartId+=(pageSteps*defIdsPerPage);
       
  2077 		TInt currIdsPerPage;
       
  2078 		if (nextId==nextHardPb)
       
  2079 			{
       
  2080 			if (nextId==aStartId)
       
  2081 				{
       
  2082 				hardPos++;
       
  2083 				continue;
       
  2084 				}
       
  2085 			currIdsPerPage=nextId-aStartId;
       
  2086 			hardPos++;
       
  2087 			if (nextId==nextSoftId)
       
  2088 				softPos++;
       
  2089 			}
       
  2090 		else
       
  2091 			{
       
  2092 			aCellSpanMap->DisplacementToId(aStartId,aPageSpan,currIdsPerPage);
       
  2093 			currIdsPerPage-=aStartId;
       
  2094 			if ((aStartId+currIdsPerPage)>nextHardPb)
       
  2095 				{
       
  2096 				currIdsPerPage=nextHardPb-aStartId;
       
  2097 				hardPos++;
       
  2098 				}
       
  2099 			if (currIdsPerPage==0)
       
  2100 				currIdsPerPage=1;
       
  2101 //			softPos++;
       
  2102 			}
       
  2103 		if (currIdsPerPage)
       
  2104 			{
       
  2105 			aPageMap->SetL(currPage,0/*NotUsed*/,currIdsPerPage);
       
  2106 			aStartId+=currIdsPerPage;
       
  2107 			currPage++;
       
  2108 			}
       
  2109 		}
       
  2110 	}
       
  2111 
       
  2112 EXPORT_C void CGridLay::ClearPagination()
       
  2113 /** Marks the grid as unpaginated. */
       
  2114 	{
       
  2115 	delete iRowPageMap;
       
  2116 	iRowPageMap=NULL;
       
  2117 	delete iColumnPageMap;
       
  2118 	iColumnPageMap=NULL;
       
  2119 	iFlags&=~EIsPaginated;
       
  2120 	iHasChanged=ETrue;
       
  2121 	}
       
  2122 
       
  2123 EXPORT_C void CGridLay::NotifyPaginationOutOfDateL()
       
  2124 /** Notifies this object that repagination must take place.
       
  2125 
       
  2126 This function is called as a response to changes in the grid, such as a change 
       
  2127 in the page size, a change to the width of selected columns, the setting or 
       
  2128 removal of hard page breaks etc. */
       
  2129 	{
       
  2130 	if (IsPaginated())
       
  2131 		{
       
  2132 		ClearPagination();
       
  2133 		if (IsAutoPagination())
       
  2134 			PaginateL();
       
  2135 		}
       
  2136 	}
       
  2137 
       
  2138 EXPORT_C TRangeRef CGridLay::PageToRange(TInt aPageNo,TPageOrder aPageOrder) const
       
  2139 /** Gets the range of cells that are on the specified page
       
  2140 
       
  2141 @param aPageNo The page number. The first page is assumed to be page zero.
       
  2142 @param aPageOrder The page order.
       
  2143 @return The range of cells.
       
  2144 @panic GRIDIMG 5 In debug mode, if the grid has not been paginated. */
       
  2145 	{
       
  2146 	__ASSERT_DEBUG(IsPaginated(),Panic(EGridLayNotPaginated));
       
  2147 	TCellRef pageRef;
       
  2148 	TInt startRow;
       
  2149 	if (!RequestRow(-KMaxTInt,startRow))
       
  2150 		return TRangeRef();
       
  2151 	TInt rowExtent=RowExtent();
       
  2152 	TInt colExtent=ColumnExtent();
       
  2153 	if (aPageOrder==ERightThenDown)
       
  2154 		{
       
  2155 		TInt noOfHorzPages;
       
  2156 		iColumnPageMap->DisplacementToId(0,colExtent-1,noOfHorzPages);
       
  2157 		noOfHorzPages++;
       
  2158 		pageRef.iRow=aPageNo/noOfHorzPages;
       
  2159 		pageRef.iCol=aPageNo-(pageRef.iRow*noOfHorzPages);
       
  2160 		}
       
  2161 	else
       
  2162 		{
       
  2163 		TInt noOfVertPages;
       
  2164 		iRowPageMap->DisplacementToId(0,rowExtent-1,noOfVertPages);
       
  2165 		noOfVertPages++;
       
  2166 		pageRef.iCol=aPageNo/noOfVertPages;
       
  2167 		pageRef.iRow=aPageNo-(pageRef.iCol*noOfVertPages);
       
  2168 		}
       
  2169 	TRangeRef pageRange;
       
  2170 	iColumnPageMap->IdToDisplacement(0,pageRef.iCol,pageRange.iFrom.iCol);
       
  2171 	pageRange.iFrom.iCol+=iGridRange.iFrom.iCol;
       
  2172 	iRowPageMap->IdToDisplacement(0,pageRef.iRow,pageRange.iFrom.iRow);
       
  2173 	pageRange.iFrom.iRow+=startRow;
       
  2174 	pageRange.iTo.iCol=Min(pageRange.iFrom.iCol+iColumnPageMap->ValueInPixels(pageRef.iCol)-1,
       
  2175 		iGridRange.iFrom.iCol+colExtent-1);
       
  2176 	pageRange.iTo.iRow=Min(pageRange.iFrom.iRow+iRowPageMap->ValueInPixels(pageRef.iRow)-1,
       
  2177 		startRow+rowExtent-1);
       
  2178 	return pageRange;
       
  2179 	}
       
  2180 
       
  2181 EXPORT_C TInt CGridLay::NoOfPages() const
       
  2182 /** Gets the number of pages that the grid would print to.
       
  2183 
       
  2184 @return The number of pages.
       
  2185 @panic GRIDIMG 5 In debug mode, if the grid has not been paginated. */
       
  2186 	{
       
  2187 	__ASSERT_DEBUG(IsPaginated(),Panic(EGridLayNotPaginated));
       
  2188 	TInt noOfHorzPages;
       
  2189 	iColumnPageMap->DisplacementToId(0,ColumnExtent()-1,noOfHorzPages);
       
  2190 	noOfHorzPages++;
       
  2191 	TInt noOfVertPages;
       
  2192 	iRowPageMap->DisplacementToId(0,RowExtent()-1,noOfVertPages);
       
  2193 	noOfVertPages++;
       
  2194 	return noOfHorzPages*noOfVertPages;
       
  2195 	}
       
  2196 
       
  2197 TBool CGridLay::FindNextRowPageBreak(TInt aSearchStart,TInt& aFoundRow) const
       
  2198 //
       
  2199 // Searches from aSearchStart and finds the next row page break (hard or soft). If one is found,
       
  2200 // aFoundRow is amended and ETrue returned. Note that returned value is 1 less than the value
       
  2201 // stored because the physical line break belongs to the row above the stored page break.
       
  2202 	{
       
  2203 	if (IsPaginated())
       
  2204 		{
       
  2205 		TInt startRow;
       
  2206 		if (!RequestRow(-KMaxTInt,startRow))
       
  2207 			return EFalse;
       
  2208 		TInt rowPage;
       
  2209 		iRowPageMap->DisplacementToId(0,aSearchStart-startRow,rowPage);
       
  2210 		iRowPageMap->IdToDisplacement(0,rowPage+1,aFoundRow);
       
  2211 		aFoundRow+=startRow-1;
       
  2212 		return ETrue;
       
  2213 		}
       
  2214 	else
       
  2215 		{
       
  2216 		TKeyArrayFix key(0,ECmpTInt);
       
  2217 		TInt pos;
       
  2218 		aSearchStart++;
       
  2219 		if (iHardRowPageBreaks->FindIsq(aSearchStart,key,pos)==0)
       
  2220 			{
       
  2221 			aFoundRow=aSearchStart-1;
       
  2222 			return ETrue;
       
  2223 			}
       
  2224 		else if (pos<iHardRowPageBreaks->Count())
       
  2225 			{
       
  2226 			aFoundRow=(*iHardRowPageBreaks)[pos]-1;
       
  2227 			return ETrue;
       
  2228 			}
       
  2229 		}
       
  2230 	return EFalse;
       
  2231 	}
       
  2232 
       
  2233 TBool CGridLay::FindNextColumnPageBreak(TInt aSearchStart,TInt& aFoundCol) const
       
  2234 //
       
  2235 // Searches from aSearchStart and finds the next column page break (hard or soft). If one is found,
       
  2236 // aFoundCol is amended and ETrue returned.
       
  2237 	{
       
  2238 	if (IsPaginated())
       
  2239 		{
       
  2240 		TInt colPage;
       
  2241 		iColumnPageMap->DisplacementToId(0,aSearchStart-iGridRange.iFrom.iCol,colPage);
       
  2242 		iColumnPageMap->IdToDisplacement(0,colPage+1,aFoundCol);
       
  2243 		aFoundCol+=iGridRange.iFrom.iCol-1;
       
  2244 		return ETrue;
       
  2245 		}
       
  2246 	else
       
  2247 		{
       
  2248 		TKeyArrayFix key(0,ECmpTInt);
       
  2249 		TInt pos;
       
  2250 		aSearchStart++;
       
  2251 		if (iHardColumnPageBreaks->FindIsq(aSearchStart,key,pos)==0)
       
  2252 			{
       
  2253 			aFoundCol=aSearchStart-1;
       
  2254 			return ETrue;
       
  2255 			}
       
  2256 		else if (pos<iHardColumnPageBreaks->Count())
       
  2257 			{
       
  2258 			aFoundCol=(*iHardColumnPageBreaks)[pos]-1;
       
  2259 			return ETrue;
       
  2260 			}
       
  2261 		}
       
  2262 	return EFalse;
       
  2263 	}
       
  2264 
       
  2265 EXPORT_C void CGridLay::SetPageSizeInTwipsL(const TSize& aPageSize)
       
  2266 /** Sets the size of a page.
       
  2267 
       
  2268 @param aPageSize The size of a page, in twips. */
       
  2269 	{
       
  2270 	iPageSizeInTwips=aPageSize;
       
  2271 	NotifyPaginationOutOfDateL();
       
  2272 	iHasChanged=ETrue;
       
  2273 	}
       
  2274 
       
  2275 EXPORT_C void CGridLay::SetAutoPagination(TBool aState)
       
  2276 /** Sets whether automatic pagination is to be in effect.
       
  2277 
       
  2278 @param aState ETrue, if automatic pagination is to be in effect; EFalse, otherwise. */
       
  2279 	{
       
  2280 	if (aState)
       
  2281 		iFlags|=EIsAutoPagination;
       
  2282 	else
       
  2283 		iFlags&=~EIsAutoPagination;
       
  2284 	iHasChanged=ETrue;
       
  2285 	}
       
  2286 
       
  2287 EXPORT_C void CGridLay::SetHardRowPageBreakL(TInt aRow)
       
  2288 /** Sets a hard page break at the specified row.
       
  2289 
       
  2290 Note that pagination will be flagged as being out of date.
       
  2291 
       
  2292 @param aRow The row, immediately above which the hard page break is to occur. */
       
  2293 	{
       
  2294 	if (IsHardRowPageBreak(aRow))
       
  2295 		return;
       
  2296 	TInt startRow;
       
  2297 	if (!RequestRow(-KMaxTInt,startRow) || aRow==startRow)
       
  2298 		return;
       
  2299 	TKeyArrayFix key(0,ECmpTInt);
       
  2300 	iHardRowPageBreaks->InsertIsqL(aRow,key);
       
  2301 	NotifyPaginationOutOfDateL();
       
  2302 	iHasChanged=ETrue;
       
  2303 	}
       
  2304 
       
  2305 EXPORT_C void CGridLay::ClearHardRowPageBreakL(TInt aRow)
       
  2306 /** Removes the hard page break at the specified row.
       
  2307 
       
  2308 Note that pagination will be flagged as being out of date.
       
  2309 
       
  2310 Note also that there is no harm in calling this function if there is no hard 
       
  2311 page break at the specified row.
       
  2312 
       
  2313 @param aRow The row, immediately above which there is a hard page break. */
       
  2314 	{
       
  2315 	TKeyArrayFix key(0,ECmpTInt);
       
  2316 	TInt pos;
       
  2317 	if (iHardRowPageBreaks->FindIsq(aRow,key,pos)==0)
       
  2318 		{
       
  2319 		iHardRowPageBreaks->Delete(pos);
       
  2320 		NotifyPaginationOutOfDateL();
       
  2321 		iHasChanged=ETrue;
       
  2322 		}
       
  2323 	}
       
  2324 
       
  2325 EXPORT_C TBool CGridLay::IsHardRowPageBreak(TInt aRow) const
       
  2326 /** Tests whether there is a hard page break at the specified row.
       
  2327 
       
  2328 @param aRow The row.
       
  2329 @return True, if there is a hard page break at (i.e. immediately above) the 
       
  2330 specified row; false, otherwise. */
       
  2331 	{
       
  2332 	TKeyArrayFix key(0,ECmpTInt);
       
  2333 	TInt pos;
       
  2334 	if (iHardRowPageBreaks->FindIsq(aRow,key,pos)==0)
       
  2335 		return ETrue;
       
  2336 	return EFalse;
       
  2337 	}
       
  2338 
       
  2339 EXPORT_C void CGridLay::SetHardColumnPageBreakL(TInt aCol)
       
  2340 /** Sets a hard page break at the specified column.
       
  2341 
       
  2342 Note that pagination will be flagged as being out of date.
       
  2343 
       
  2344 @param aCol The column, immediately to the left of which the hard page break 
       
  2345 is to occur. */
       
  2346 	{
       
  2347 	if (IsHardColumnPageBreak(aCol) || aCol==iGridRange.iFrom.iCol)
       
  2348 		return;
       
  2349 	TKeyArrayFix key(0,ECmpTInt);
       
  2350 	iHardColumnPageBreaks->InsertIsqL(aCol,key);
       
  2351 	NotifyPaginationOutOfDateL();
       
  2352 	iHasChanged=ETrue;
       
  2353 	}
       
  2354 
       
  2355 EXPORT_C void CGridLay::ClearHardColumnPageBreakL(TInt aCol)
       
  2356 /** Removes the hard page break at the specified column.
       
  2357 
       
  2358 Note that pagination will be flagged as being out of date.
       
  2359 
       
  2360 Note also that there is no harm in calling this function if there is no hard 
       
  2361 page break at the specified column.
       
  2362 
       
  2363 @param aCol The column, immediately to the left of which there is a hard page 
       
  2364 break. */
       
  2365 	{
       
  2366 	TKeyArrayFix key(0,ECmpTInt);
       
  2367 	TInt pos;
       
  2368 	if (iHardColumnPageBreaks->FindIsq(aCol,key,pos)==0)
       
  2369 		{
       
  2370 		iHardColumnPageBreaks->Delete(pos);
       
  2371 		NotifyPaginationOutOfDateL();
       
  2372 		iHasChanged=ETrue;
       
  2373 		}
       
  2374 	}
       
  2375 
       
  2376 EXPORT_C TBool CGridLay::IsHardColumnPageBreak(TInt aCol) const
       
  2377 /** Tests whether there is a hard page break at the specified column.
       
  2378 
       
  2379 @param aCol The column.
       
  2380 @return True, if there is a hard page break at (i.e. immediately to the left 
       
  2381 of) the specified column; false, otherwise. */
       
  2382 	{
       
  2383 	TKeyArrayFix key(0,ECmpTInt);
       
  2384 	TInt pos;
       
  2385 	if (iHardColumnPageBreaks->FindIsq(aCol,key,pos)==0)
       
  2386 		return ETrue;
       
  2387 	return EFalse;
       
  2388 	}
       
  2389 
       
  2390 EXPORT_C void CGridLay::ClearAllHardPageBreaksL()
       
  2391 /** Removes all hard page breaks; this includes all row and column page breaks.
       
  2392 
       
  2393 Note that pagination will be flagged as being out of date. */
       
  2394 	{
       
  2395 	iHardRowPageBreaks->Reset();
       
  2396 	iHardColumnPageBreaks->Reset();
       
  2397 	NotifyPaginationOutOfDateL();
       
  2398 	iHasChanged=ETrue;
       
  2399 	}
       
  2400 
       
  2401 EXPORT_C void CGridLay::ExternalizeL(RWriteStream &aStream) const
       
  2402 /** Externalises an object of this class to a write stream.
       
  2403 
       
  2404 The presence of this function means that the standard templated operator<<() 
       
  2405 can be used to externalise objects of this class. 
       
  2406 
       
  2407 @param aStream Stream to which the object should be externalised. */
       
  2408 	{
       
  2409 	aStream.WriteUint32L(iFlags);
       
  2410 	aStream << iGridRange;
       
  2411 	aStream << *iRowHeightMap;
       
  2412 	aStream << *iColumnWidthMap;
       
  2413 	aStream << *iHardRowPageBreaks;
       
  2414 	aStream << *iHardColumnPageBreaks;
       
  2415 	aStream.WriteInt32L(iMinRowHeightInPixels);
       
  2416 	aStream.WriteInt32L(iMinColumnWidthInPixels);
       
  2417 	aStream.WriteInt32L(iPageSizeInTwips.iWidth);
       
  2418 	aStream.WriteInt32L(iPageSizeInTwips.iHeight);
       
  2419 	if (IsTitleLines())
       
  2420 		{
       
  2421 		aStream << iTitleRange;
       
  2422 		}
       
  2423 	aStream << iVisibleRange.iFrom;
       
  2424 	aStream << iGridEdgeColor;
       
  2425 	((CGridLay*)this)->iHasChanged=EFalse;
       
  2426 	}
       
  2427 
       
  2428 EXPORT_C void CGridLay::InternalizeL(RReadStream &aStream)
       
  2429 /** Internalises an object of this class from a read stream.
       
  2430 
       
  2431 The presence of this function means that the standard templated operator>>() 
       
  2432 can be used to internalise objects of this class.
       
  2433 
       
  2434 Note that the function has assignment semantics. It replaces the old value 
       
  2435 of the object with a new value read from the read stream. 
       
  2436 
       
  2437 @param aStream Stream from which the object is to be internalised. */
       
  2438 	{
       
  2439 	iFlags = aStream.ReadUint32L();
       
  2440 	aStream >> iGridRange;
       
  2441 	if (iGridImg)
       
  2442 		iGridImg->NotifyGridRangeResize();
       
  2443 	aStream >> *iRowHeightMap;
       
  2444 	aStream >> *iColumnWidthMap;
       
  2445 	aStream >> *iHardRowPageBreaks;
       
  2446 	aStream >> *iHardColumnPageBreaks;
       
  2447 	RecalcPixelSparseMaps();
       
  2448 	iMinRowHeightInPixels=aStream.ReadInt32L();
       
  2449 	iMinColumnWidthInPixels=aStream.ReadInt32L();
       
  2450 	iPageSizeInTwips.iWidth=aStream.ReadInt32L();
       
  2451 	iPageSizeInTwips.iHeight=aStream.ReadInt32L();
       
  2452 	if (IsPaginated() && iGridImg)
       
  2453 		{
       
  2454 		ClearPagination();
       
  2455 		PaginateL();
       
  2456 		}
       
  2457 	if (IsTitleLines())
       
  2458 		{
       
  2459 		aStream >> iTitleRange;
       
  2460 		}
       
  2461 	if (IsRowPermanentlySelected())
       
  2462 		SetRowPermanentlySelectedL(ETrue);	//To add row to selection region
       
  2463 	if (iGridImg)
       
  2464 		iGridImg->ResetReferencePoints();
       
  2465 	aStream >> iVisibleRange.iFrom;
       
  2466 	if (iGridImg)
       
  2467 		{
       
  2468 		ResetVisibleToCell();
       
  2469 		iGridImg->CheckSideLabelWidth();
       
  2470 		}
       
  2471 	aStream >> iGridEdgeColor;
       
  2472 	iHasChanged=EFalse;
       
  2473 	}
       
  2474 
       
  2475 EXPORT_C TStreamId CGridLay::StoreL(CStreamStore& aStore) const
       
  2476 /** Externalises this object to a stream in the specified store.
       
  2477 
       
  2478 @param aStore The store in which the stream is to be created and stored.
       
  2479 @return The Id of the created stream. */
       
  2480 	{
       
  2481 	RStoreWriteStream stream;
       
  2482 	TStreamId streamId = stream.CreateLC(aStore);
       
  2483 	ExternalizeL(stream);
       
  2484 	stream.CommitL();
       
  2485 	CleanupStack::PopAndDestroy();
       
  2486 	return streamId;
       
  2487 	}
       
  2488 
       
  2489 EXPORT_C void CGridLay::RestoreL(const CStreamStore& aStore,TStreamId aStreamId)
       
  2490 /** Internalises this object from the specified stream in the specified store.
       
  2491 
       
  2492 Note that the function has assignment semantics. It replaces the old value 
       
  2493 of this object with a new value read from the specified stream.
       
  2494 
       
  2495 @param aStore The store containing the stream.
       
  2496 @param aStreamId The Id of the stream from which this object is to be internalised. */
       
  2497 	{
       
  2498 	RStoreReadStream stream;
       
  2499 	stream.OpenLC(aStore,aStreamId);
       
  2500 	InternalizeL(stream);
       
  2501 	CleanupStack::PopAndDestroy();
       
  2502 	}
       
  2503 
       
  2504 TBool CGridLay::RequestRow(TInt aRow,TInt& aReturnRow) const
       
  2505 	{
       
  2506 	if (IsIndefiniteRowBoundaries())
       
  2507 		return iGridTable->RequestRow(aRow,aReturnRow);
       
  2508 	if (aRow<iGridRange.iFrom.iRow)
       
  2509 		aReturnRow=iGridRange.iFrom.iRow;
       
  2510 	else if (aRow>iGridRange.iTo.iRow)
       
  2511 		aReturnRow=iGridRange.iTo.iRow;
       
  2512 	else
       
  2513 		aReturnRow=aRow;
       
  2514 	return iGridRange.iFrom.iRow<=iGridRange.iTo.iRow;
       
  2515 	}
       
  2516 
       
  2517 EXPORT_C TInt CGridLay::RowExtent() const
       
  2518 /** Gets the number of rows in the range.
       
  2519 
       
  2520 @return The number of rows. */
       
  2521 	{
       
  2522 	TInt gridRowExtent=iGridRange.iTo.iRow-iGridRange.iFrom.iRow+1;
       
  2523 	if (gridRowExtent<0)
       
  2524 		gridRowExtent=KMaxTInt;	// In case gridrange is v. large (i.e. indefinite row boundaries)
       
  2525 	return Min(iGridTable->RowExtent(),gridRowExtent);
       
  2526 	}
       
  2527 
       
  2528 EXPORT_C TInt CGridLay::ColumnExtent() const
       
  2529 /** Gets the number of columns in the range.
       
  2530 
       
  2531 @return The number of columns. */
       
  2532 	{
       
  2533 	return Min(iGridTable->ColumnExtent(),iGridRange.iTo.iCol-iGridRange.iFrom.iCol+1);
       
  2534 	}
       
  2535 
       
  2536 //
       
  2537 
       
  2538 EXPORT_C TBool MGridTable::RequestRow(TInt /*aRow*/,TInt& /*aReturnRow*/) const
       
  2539 /** Translates a requested row.
       
  2540 
       
  2541 Typically, the function is called by grid before it attempts a redraw in order 
       
  2542 to determine how many rows can be drawn. For example, if a request for row 16 
       
  2543 were to be translated as row 11, then it would imply that there are only 11 
       
  2544 rows in this rowset, and cause grid to draw accordingly.
       
  2545 
       
  2546 An implementation must be provided for grids that have indefinite row boundaries.
       
  2547 
       
  2548 The default implementation raises a panic.
       
  2549 
       
  2550 @param aRow The row to be translated.
       
  2551 @param aReturnRow On return, the row that corresponds to the requested row.
       
  2552 @return True, if a row is returned; false, if no rows can be returned.
       
  2553 @panic GRIDIMG 8 Always raised by the default implementation.*/
       
  2554 	{
       
  2555 	Panic(EGridTableInvalidRequestRow);
       
  2556 	return EFalse;
       
  2557 	}
       
  2558 
       
  2559 EXPORT_C TInt MGridTable::RowExtent() const
       
  2560 /** Gets the number of rows in the grid.
       
  2561 
       
  2562 @return The number of rows in the grid. The default implementation returns 
       
  2563 the value EDefaultRowExtent. */
       
  2564 	{
       
  2565 	return EDefaultRowExtent;
       
  2566 	}
       
  2567 
       
  2568 EXPORT_C TInt MGridTable::ColumnExtent() const
       
  2569 /** Gets the number of columns in the grid.
       
  2570 
       
  2571 @return The number of columns in the grid. The default implementation returns 
       
  2572 the value EDefaultColumnExtent. */
       
  2573 	{
       
  2574 	return EDefaultColumnExtent;
       
  2575 	}
       
  2576 
       
  2577 //	Setting the grid colors
       
  2578 
       
  2579 EXPORT_C void CGridLay::SetGridColors(TGridColors aColors)
       
  2580 /** Sets the collection of colours to be used to draw the grid.
       
  2581 
       
  2582 @param aColors The grid colour definitions. */
       
  2583 	{
       
  2584 	iColors = aColors;
       
  2585 	iGridImg->SetGridColors(aColors);
       
  2586 	}
       
  2587 
       
  2588 //	Getting the grid colors
       
  2589 
       
  2590 EXPORT_C const TGridColors& CGridLay::GridColors() const
       
  2591 /** Gets the collection of colours used to draw the grid.
       
  2592 
       
  2593 @return The grid colour definitions. */
       
  2594 	{
       
  2595 	return iColors;
       
  2596 	}