|
1 // Copyright (c) 2007-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 // |
|
15 |
|
16 #include "directgdicontext.h" |
|
17 #include "directgdipaniccodes.h" |
|
18 #include "directgdifont.h" |
|
19 #include "directgdidriver.h" |
|
20 #include <graphics/directgdidrawablesource.h> |
|
21 #include <graphics/directgdiengine.h> |
|
22 #include <e32cmn.h> |
|
23 #include <s32mem.h> |
|
24 #include <shapeinfo.h> |
|
25 #include <fbs.h> |
|
26 #include <fntstore.h> |
|
27 |
|
28 using namespace DirectGdi; |
|
29 |
|
30 /** |
|
31 CDirectGdiContext InternalizeL/ExternalizeL - version numbers. |
|
32 Add new version numbers here. A reason of adding new version numbers may be adding new |
|
33 CDirectGdiContext data members, which may have to be externalized/internalized. |
|
34 When that happens: |
|
35 1.Put a new enum item (like EDirectGDIContext_Ver01) with a version number, which is greater than |
|
36 the last version number, that was used. |
|
37 2.Document the new enum item. |
|
38 3.Update KDirectGDIContext_VerNo value to be the new enum item value. |
|
39 4.Update InternalizeL/ExternalizeL methods after adding the new version number. |
|
40 For example: If a new member is added to the class - TInt iSmth, when InternalizeL |
|
41 is called to operate on older archive, iSmth member won't be in the archive! |
|
42 So, in InternalizeL, there should be a check, something like: |
|
43 TUint16 archiveVerNo = 0; |
|
44 aReadStream >> archiveVerNo; |
|
45 if(archiveVerNo < EDirectGDIContext_Ver02) //EDirectGDIContext_Ver02 has been added, when iSmth has been added |
|
46 { |
|
47 //Do nothing - iSmth is not in the archive |
|
48 //Initialize it with some default value |
|
49 iSmth = KDefVal; |
|
50 } |
|
51 else |
|
52 { |
|
53 aReadStream >> iSmth; |
|
54 } |
|
55 */ |
|
56 enum |
|
57 { |
|
58 EDirectGDIContext_Ver01 = 1 //Base version number, when InternalizeL/ExternalizeL were added |
|
59 }; |
|
60 |
|
61 LOCAL_D const TUint16 KDirectGDIContext_VerNo = EDirectGDIContext_Ver01; |
|
62 |
|
63 /** |
|
64 Static two-phase factory constuctor. Creates an object of this class. |
|
65 |
|
66 @param aDirectGdiDriver The driver object which provides an abstract factory for creating a concrete drawing engine. |
|
67 |
|
68 @pre CDirectGdiDriver object has been initialised from the calling thread. |
|
69 @post Instances of CDirectGdiContext and MDirectGdiEngine have been created. |
|
70 |
|
71 @leave Leaves if CDirectGdiDriver has not been initialised from the calling thread, or other errors occur during object construction. |
|
72 @return Reference to constructed CDirectGdiContext. |
|
73 */ |
|
74 EXPORT_C CDirectGdiContext* CDirectGdiContext::NewL(CDirectGdiDriver& aDirectGdiDriver) |
|
75 { |
|
76 CDirectGdiContext* result = new(ELeave) CDirectGdiContext(aDirectGdiDriver); |
|
77 CleanupStack::PushL(result); |
|
78 |
|
79 // Cache a reference to the driver locally, so that we do not need to use |
|
80 // the singleton accessor all the time. The singleton accessor utilises TLS |
|
81 // and hence incurs a performance penalty. |
|
82 // |
|
83 result->ConstructL(); |
|
84 |
|
85 CleanupStack::Pop(); |
|
86 return result; |
|
87 } |
|
88 |
|
89 |
|
90 /** |
|
91 Installs a rendering engine instance from the supplied driver, records |
|
92 a reference to the driver (for use by the destructor), and initialises it. |
|
93 |
|
94 @pre Invoked by NewL(). |
|
95 @post Instance of MDirectGdiEngine has been created. |
|
96 |
|
97 @leave If CDirectGdiDriver::CreateEngine() returns an error code. |
|
98 */ |
|
99 void CDirectGdiContext::ConstructL() |
|
100 { |
|
101 User::LeaveIfError(iDriver.CreateEngine(iEngine)); |
|
102 Reset(); // Initialise context and engine to default values. |
|
103 } |
|
104 |
|
105 |
|
106 /** |
|
107 Object constructor. Declared private for better encapsulation. A factory method is |
|
108 provided to instantiate this class. This class is not intended for derivation. Binary |
|
109 compatibility needs to be maintained. |
|
110 |
|
111 @param aDirectGdiDriver The driver that coordinates management of DirectGDI resources. |
|
112 |
|
113 @pre The driver must be initialised. |
|
114 @post None. |
|
115 */ |
|
116 EXPORT_C CDirectGdiContext::CDirectGdiContext(CDirectGdiDriver& aDirectGdiDriver) : |
|
117 iDriver(aDirectGdiDriver) |
|
118 { |
|
119 } |
|
120 |
|
121 |
|
122 /** |
|
123 Unbind current target from drawing context and mark drawing engine for deletion. |
|
124 |
|
125 @pre None. |
|
126 @post Rendering engine has had targets unbound and is marked for deletion. |
|
127 */ |
|
128 EXPORT_C CDirectGdiContext::~CDirectGdiContext() |
|
129 { |
|
130 // If an engine has been bound, destroy it through the driver. |
|
131 if (iEngine) |
|
132 { |
|
133 iDriver.DestroyEngine(iEngine); |
|
134 } |
|
135 |
|
136 CleanUpBrushPattern(); |
|
137 iClippingRegion.Close(); |
|
138 } |
|
139 |
|
140 |
|
141 /** |
|
142 Binds a rendering target to this drawing context. |
|
143 |
|
144 Subsequent rendering operations after calling this method will apply to the new rendering |
|
145 target. The clipping region will be reset to none, in other words drawing will be clipped to the |
|
146 full area of the new target by default, other context states such as pen or brush colour, |
|
147 font, etc. will remain unchanged. |
|
148 |
|
149 This operation could fail, DirectGDI clients should always check the return value when |
|
150 calling this method. The error state is not modified by this function. |
|
151 |
|
152 @param aTarget DirectGDI rendering target. |
|
153 |
|
154 @pre Rendering target has been fully constructed. |
|
155 @post The drawing context is bound to the new rendering target. |
|
156 |
|
157 @return KErrNone if successful, KErrNotSupported if target is incompatible with the drawing context, |
|
158 otherwise one of the system-wide error codes. |
|
159 */ |
|
160 EXPORT_C TInt CDirectGdiContext::Activate(RDirectGdiImageTarget& aTarget) |
|
161 { |
|
162 GRAPHICS_TRACE("CDirectGdiContext::Activate"); |
|
163 TInt err = iEngine->Activate(aTarget); |
|
164 |
|
165 iActivated = EFalse; |
|
166 if (err == KErrNone) |
|
167 { |
|
168 iActivated = ETrue; |
|
169 } |
|
170 return err; |
|
171 } |
|
172 |
|
173 /** |
|
174 Disables AutoUpdateJustification state. |
|
175 |
|
176 @see CDirectGdiContext::SetJustifyAutoUpdate |
|
177 */ |
|
178 EXPORT_C void CDirectGdiContext::NoJustifyAutoUpdate() |
|
179 { |
|
180 GRAPHICS_TRACE("CDirectGdiContext::NoJustifyAutoUpdate"); |
|
181 iAutoUpdateJustification = EFalse; |
|
182 } |
|
183 |
|
184 /** |
|
185 Enables AutoUpdateJustification state. |
|
186 During the text drawing, some text parameters which impact on positioning the text on the screen will be updated and applied |
|
187 */ |
|
188 EXPORT_C void CDirectGdiContext::SetJustifyAutoUpdate() |
|
189 { |
|
190 GRAPHICS_TRACE("CDirectGdiContext::SetJustifyAutoUpdate"); |
|
191 iAutoUpdateJustification = ETrue; |
|
192 } |
|
193 |
|
194 /** |
|
195 Draws the whole of a CFbsBitmap. Calls BitBlt() with a rectangle set to the extents of aBitmap. |
|
196 |
|
197 No scaling or stretching is involved. The current clipping region and drawing mode apply. The |
|
198 source bitmap can reside in system memory or ROM. Bitmaps in system memory may be compressed |
|
199 using RLE or Palette compression, and can be in any supported display mode. Please refer to |
|
200 CFbsBitmap documentation for more details. |
|
201 |
|
202 If the client modifies the content of the bitmap after issuing a BitBlt() command, the method |
|
203 does not guarantee whether the old bitmap content or the new one will be drawn. Clients must call |
|
204 Finish() on the driver before modifying the bitmap content if they want a guaranteed result that |
|
205 the previously issued BitBlt() will draw the old bitmap content. |
|
206 |
|
207 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
208 |
|
209 @see void CDirectGdiContext::BitBlt(const TPoint& aPoint, const CFbsBitmap* aBitmap, const TRect& aSourceRect); |
|
210 @param aDestPos The position to draw the top left corner of the bitmap. |
|
211 @param aSourceBitmap The source bitmap. |
|
212 |
|
213 @pre The rendering target has been activated. |
|
214 @post Request to draw the bitmap content has been accepted. There is no guarantee that the request |
|
215 has been processed when the method returns. |
|
216 |
|
217 @panic DGDI 7, if the rendering context has not been activated. |
|
218 */ |
|
219 EXPORT_C void CDirectGdiContext::BitBlt(const TPoint& aDestPos, const CFbsBitmap& aSourceBitmap) |
|
220 { |
|
221 GRAPHICS_TRACE2("CDirectGdiContext::BitBlt(%d,%d)", aDestPos.iX, aDestPos.iY); |
|
222 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
223 |
|
224 if (ValidateBitmap (aSourceBitmap)) |
|
225 { |
|
226 iEngine->BitBlt(aDestPos, aSourceBitmap, TRect(aSourceBitmap.SizeInPixels())); |
|
227 } |
|
228 } |
|
229 |
|
230 |
|
231 /** |
|
232 Draws a particular rectangle from a CFbsBitmap via bitmap block image transfer. |
|
233 The bitmap content is specified by the given source rectangle. The bitmap content is drawn |
|
234 into the rendering target starting from the given destination position. To draw the content |
|
235 of the entire bitmap, a source rectangle TRect(TPoint(0,0), aBitmap.SizeInPixels()) is used. |
|
236 |
|
237 The source rectangle is intersected with the source bitmap’s full extent, and the intersection |
|
238 will become the effective value of the source rectangle. |
|
239 |
|
240 No scaling or stretching is involved. The current clipping region and drawing mode apply. The |
|
241 source bitmap can reside in system memory or ROM. Bitmaps in system memory may be compressed |
|
242 using RLE or Palette compression, and can be in any supported display mode. Please refer to |
|
243 CFbsBitmap documentation for more details. |
|
244 |
|
245 The bitmap is not guaranteed to continue to exist outside the implementation of this method, for example |
|
246 DirectGDI clients may delete the bitmap immediately after issuing a BitBlt() command. The adaptation |
|
247 must maintain its own copy by duplicating the bitmap if access to the bitmap data is required |
|
248 later on, for example outside this method implementation. Duplicating the bitmap will increase its |
|
249 reference counter and will prevent the object from being destroyed by Fbserv. The adaptation |
|
250 must make sure the bitmap copy is destroyed when it is no longer needed. |
|
251 |
|
252 If the client modifies the content of the bitmap after issuing BitBlt() command, the method |
|
253 does not guarantee whether the old bitmap content or the new one will be drawn. Clients must call |
|
254 Finish() on the driver before modifying the bitmap content if they want a guaranteed result that |
|
255 the previously issued BitBlt() will draw the old bitmap content. |
|
256 |
|
257 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
258 |
|
259 @param aDestPos The position to draw the top left corner of the bitmap (destination position). |
|
260 @param aSourceBitmap The source bitmap. |
|
261 @param aSourceRect A rectangle defining the piece of the source to be drawn. No image data |
|
262 is transferred if no intersection exists with the bitmap. |
|
263 NOTE: The top and left hand edges are inclusive, the bottom and |
|
264 right hand edge are exclusive. |
|
265 |
|
266 @pre The rendering target has been activated. |
|
267 @post Request to draw the bitmap content has been accepted. There is no guarantee that the request |
|
268 has been processed when the method returns. |
|
269 |
|
270 @panic DGDI 7, if the rendering context has not been activated. |
|
271 */ |
|
272 EXPORT_C void CDirectGdiContext::BitBlt( |
|
273 const TPoint& aDestPos, |
|
274 const CFbsBitmap& aSourceBitmap, |
|
275 const TRect& aSourceRect) |
|
276 { |
|
277 GRAPHICS_TRACE2("CDirectGdiContext::BitBlt(%d,%d)", aDestPos.iX, aDestPos.iY); |
|
278 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
279 |
|
280 if (ValidateBitmap(aSourceBitmap)) |
|
281 { |
|
282 TRect sourceRect = IntersectBitmapWithRect(aSourceBitmap, aSourceRect); |
|
283 if (!sourceRect.IsEmpty()) |
|
284 { |
|
285 iEngine->BitBlt(aDestPos, aSourceBitmap, sourceRect); |
|
286 } |
|
287 } |
|
288 } |
|
289 |
|
290 /** |
|
291 Validates a specified bitmap image. |
|
292 The bitmap is deemed invalid if its associated handle equals KNullHandle or it |
|
293 has a width or height of zero. |
|
294 |
|
295 The following errors are set in iDirectGdiDriver if the associated conditions are met: |
|
296 - KErrBadHandle if the handle associated with the bitmap equals KNullHandle. |
|
297 - KErrArgument is the bitmaps width or height is zero. |
|
298 |
|
299 @param aBitmap The bitmap to validate. |
|
300 |
|
301 @return ETrue if the specified bitmap is valid, otherwise EFalse. |
|
302 */ |
|
303 TBool CDirectGdiContext::ValidateBitmap(const CFbsBitmap& aBitmap) |
|
304 { |
|
305 TInt errorCode = KErrNone; |
|
306 TBool result = ETrue; |
|
307 |
|
308 if (aBitmap.Handle() == KNullHandle) |
|
309 { |
|
310 errorCode = KErrBadHandle; |
|
311 } |
|
312 else |
|
313 { |
|
314 // Check that mask and source bitmap have width and height. |
|
315 const TSize bitmapSize = aBitmap.SizeInPixels(); |
|
316 if (!bitmapSize.iWidth || !bitmapSize.iHeight) |
|
317 { |
|
318 errorCode = KErrArgument; |
|
319 } |
|
320 } |
|
321 |
|
322 if (errorCode != KErrNone) |
|
323 { |
|
324 iDriver.SetError(errorCode); |
|
325 result = EFalse; |
|
326 } |
|
327 |
|
328 return result; |
|
329 } |
|
330 |
|
331 /* |
|
332 Returns a TRect that intersects both the CFbsBitmap and the passed-in TRect. |
|
333 |
|
334 @param aBitmap The bitmap to intersect with. |
|
335 @param aRect The TRect object that is overlapping the bitmap. |
|
336 @return A TRect that represents the intersection of the two. If the two do not intersect, |
|
337 it will be an empty TRect object. |
|
338 */ |
|
339 TRect CDirectGdiContext::IntersectBitmapWithRect(const CFbsBitmap& aBitmap, const TRect& aRect) const |
|
340 { |
|
341 TRect result = TRect(aBitmap.SizeInPixels()); |
|
342 |
|
343 if (aRect == result) |
|
344 return result; |
|
345 |
|
346 if (result.Intersects(aRect)) |
|
347 { |
|
348 result.Intersection(aRect); |
|
349 return result; |
|
350 } |
|
351 |
|
352 return TRect(0,0,0,0); |
|
353 } |
|
354 |
|
355 /** |
|
356 |
|
357 Validates the specified source bitmap and mask pair. |
|
358 First validates the source and mask bitmaps individually, and then checks for valid |
|
359 bitmap pairings. The only pairing not supported is: EGray256 masks and sources with |
|
360 an alpha-channel when using EDrawModeWriteAlpha. |
|
361 |
|
362 @see CDirectGdiContext::ValidateBitmap() |
|
363 |
|
364 The following errors are set in iDirectGdiDriver if the associated conditions are met: |
|
365 - KErrBadHandle if the handle associated with either bitmap equals KNullHandle. |
|
366 - KErrArgument if either bitmaps width or height is zero. |
|
367 - KErrArgument if the mask format is EGray256 and the source contains an alpha-channel and draw mode is EDrawModeWriteAlpha. |
|
368 |
|
369 @param aSourceBitmap The source bitmap to validate. |
|
370 @param aMaskBitmap The mask to validate. |
|
371 |
|
372 @return ETrue if the specified bitmaps is valid, otherwise EFalse. |
|
373 */ |
|
374 TBool CDirectGdiContext::ValidateSourceAndMaskBitmaps(const CFbsBitmap& aSourceBitmap, const CFbsBitmap& aMaskBitmap) |
|
375 { |
|
376 TInt errorCode = KErrNone; |
|
377 TBool result = ETrue; |
|
378 |
|
379 if (ValidateBitmap (aSourceBitmap) && ValidateBitmap (aMaskBitmap)) |
|
380 { |
|
381 TDisplayMode sourceBitmapDisplayMode = aSourceBitmap.DisplayMode(); |
|
382 |
|
383 // We do not currently support EGray256 masks and sources with an alpha-channel |
|
384 // with EDrawModeWriteAlpha. |
|
385 if ((iDrawMode == DirectGdi::EDrawModeWriteAlpha) && |
|
386 (aMaskBitmap.DisplayMode() == EGray256) && |
|
387 ((sourceBitmapDisplayMode == EColor16MA) || (sourceBitmapDisplayMode == EColor16MAP))) |
|
388 { |
|
389 errorCode = KErrArgument; |
|
390 } |
|
391 } |
|
392 else |
|
393 { |
|
394 result = EFalse; |
|
395 } |
|
396 |
|
397 if (errorCode != KErrNone) |
|
398 { |
|
399 iDriver.SetError(errorCode); |
|
400 result = EFalse; |
|
401 } |
|
402 |
|
403 return result; |
|
404 } |
|
405 |
|
406 /** |
|
407 Helper method for performing BitBltMasked. |
|
408 Note that aInvertMask is ignored if aMaskPos is not at 0,0. |
|
409 |
|
410 @see CDirectGdiContext::BitBlt(const TPoint& aPoint, const CFbsBitmap& aBitmap, const TRect& aSourceRect); |
|
411 @see CDirectGdiContext::BitBltMasked(const TPoint&, const CFbsBitmap&,const TRect&, const CFbsBitmap&, const TPoint&); |
|
412 |
|
413 @param aDestPos The destination for the top left corner of the transferred bitmap. |
|
414 It is relative to the top left corner of the destination bitmap, which may be the screen. |
|
415 @param aSourceBitmap A memory-resident source bitmap. |
|
416 @param aSourceRect A rectangle defining the piece of the bitmap to be drawn, |
|
417 with co-ordinates relative to the top left corner of the bitmap. |
|
418 @param aMaskBitmap Mask bitmap. |
|
419 @param aInvertMask If EFalse, a source pixel that is masked by a black pixel is not transferred to |
|
420 the destination rectangle. If ETrue, then a source pixel that is masked by a |
|
421 white pixel is not transferred to the destination rectangle. If alpha blending |
|
422 is used instead of masking, this flag is ignored and no inversion takes place. |
|
423 Note that this parameter is ignored if aMaskPos does not equal TPoint(0,0). |
|
424 @param aMaskPos The point on the mask bitmap to use as the top left corner |
|
425 */ |
|
426 void CDirectGdiContext::DoBitBltMasked( |
|
427 const TPoint& aDestPos, |
|
428 const CFbsBitmap& aSourceBitmap, |
|
429 const TRect& aSourceRect, |
|
430 const CFbsBitmap& aMaskBitmap, |
|
431 TBool aInvertMask, |
|
432 const TPoint& aMaskPos) |
|
433 { |
|
434 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
435 |
|
436 if (ValidateSourceAndMaskBitmaps(aSourceBitmap, aMaskBitmap)) |
|
437 { |
|
438 // If the source rectangle does not intersect aBitmap, do nothing. |
|
439 TRect sourceRect = IntersectBitmapWithRect(aSourceBitmap, aSourceRect); |
|
440 if (!sourceRect.IsEmpty()) |
|
441 { |
|
442 if (aMaskPos == TPoint(0, 0)) |
|
443 { |
|
444 iEngine->BitBltMasked(aDestPos, aSourceBitmap, sourceRect, aMaskBitmap, aInvertMask); |
|
445 } |
|
446 else |
|
447 { |
|
448 TSize maskSize = aMaskBitmap.SizeInPixels(); |
|
449 // Convert negative or large mask offsets into sensible positive ones for tiling. |
|
450 TPoint maskOffset(aMaskPos.iX % maskSize.iWidth, aMaskPos.iY % maskSize.iHeight); |
|
451 if (maskOffset.iX < 0) |
|
452 maskOffset.iX += maskSize.iWidth; |
|
453 if (maskOffset.iY < 0) |
|
454 maskOffset.iY += maskSize.iHeight; |
|
455 |
|
456 iEngine->BitBltMasked(aDestPos, aSourceBitmap, sourceRect, aMaskBitmap, maskOffset); |
|
457 } |
|
458 } |
|
459 } |
|
460 } |
|
461 |
|
462 |
|
463 /** |
|
464 Performs a masked bitmap block transfer. Source rectangle operates in a similar way to BitBlt(). |
|
465 |
|
466 This function uses either a black and white (binary) mask bitmap, or if the mask's display mode is |
|
467 EGray256, alpha blending is used. The result is undefined if the mask pixel value is neither black nor |
|
468 white and the mask display mode is other than EGray256. |
|
469 |
|
470 The mask is aligned with the source bitmap by aligning the first pixel of the mask and source bitmaps within |
|
471 the source rectangle. Tiling in both directions applies if the mask size is smaller than the source rectangle. |
|
472 Note that the mask is applied before the piece of the bitmap is defined - the mask is tiled relative to the |
|
473 top left of the original source bitmap rather than the top left of the bitmap piece. If the mask has zero |
|
474 width or height, the error state is set to KErrArgument and no drawing is performed. |
|
475 |
|
476 The mask bitmap can be used as either a positive or negative mask. Masked pixels are not mapped to the |
|
477 destination rectangle. |
|
478 |
|
479 If the client modifies the contents of the bitmap or the mask after issuing the BitBltMasked() command, the |
|
480 method does not guarantee whether the old bitmap or mask contents, or the new ones will be used. |
|
481 Clients must call Finish() on the driver before modifying the bitmap or mask contents if they want a |
|
482 guaranteed result that the previously issued BitBltMasked() will be using the old bitmap or mask contents. |
|
483 |
|
484 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
485 |
|
486 @see CDirectGdiContext::BitBlt(const TPoint& aPoint, const CFbsBitmap& aBitmap, const TRect& aSourceRect); |
|
487 @see CDirectGdiContext::BitBltMasked(const TPoint&, const CFbsBitmap&,const TRect&, const CFbsBitmap&, const TPoint&); |
|
488 |
|
489 @param aDestPos The destination for the top left corner of the transferred bitmap. |
|
490 It is relative to the top left corner of the destination bitmap, which may be the screen. |
|
491 @param aSourceBitmap A memory-resident source bitmap. |
|
492 @param aSourceRect A rectangle defining the piece of the bitmap to be drawn, |
|
493 with co-ordinates relative to the top left corner of the bitmap. |
|
494 @param aMaskBitmap Mask bitmap. |
|
495 @param aInvertMask If EFalse, a source pixel that is masked by a black pixel is not transferred to |
|
496 the destination rectangle. If ETrue, then a source pixel that is masked by a |
|
497 white pixel is not transferred to the destination rectangle. If alpha blending |
|
498 is used instead of masking, this flag is ignored and no inversion takes place. |
|
499 |
|
500 @pre The rendering target has been activated. aBitmap and aMask hold valid handles. |
|
501 @post Request to draw the masked bitmap content has been accepted. |
|
502 There is no guarantee that the request has been processed when the method returns. |
|
503 |
|
504 @panic DGDI 7, if the rendering context has not been activated. |
|
505 */ |
|
506 EXPORT_C void CDirectGdiContext::BitBltMasked( |
|
507 const TPoint& aDestPos, |
|
508 const CFbsBitmap& aSourceBitmap, |
|
509 const TRect& aSourceRect, |
|
510 const CFbsBitmap& aMaskBitmap, |
|
511 TBool aInvertMask) |
|
512 { |
|
513 GRAPHICS_TRACE2("CDirectGdiContext::BitBltMasked(%d,%d)", aDestPos.iX, aDestPos.iY); |
|
514 DoBitBltMasked (aDestPos, aSourceBitmap, aSourceRect, aMaskBitmap, aInvertMask, TPoint(0, 0)); |
|
515 } |
|
516 |
|
517 |
|
518 /** |
|
519 Performs a masked bitmap block transfer. Source rectangle operates in a similar way to BitBlt(). |
|
520 |
|
521 This function uses either a black and white (binary) mask bitmap, or if aMaskBitmap's display mode is |
|
522 EGray256, alpha blending is used. The result is undefined if the mask pixel value is neither black nor |
|
523 white and the mask display mode is other than EGray256. |
|
524 |
|
525 The source rectangle is intersected with the source bitmap’s full extent and the intersection |
|
526 will become the effective value. The mask bitmap is aligned with the source bitmap by aligning |
|
527 its pixel at the position specified in aMaskPt with the first pixel of the source bitmap |
|
528 within the source rectangle. The mask bitmap will be tiled if it is smaller than the source |
|
529 rectangle. If the mask has zero width or height, the error state is set to KErrArgument and |
|
530 no drawing is performed. |
|
531 |
|
532 If the client modifies the contents of the bitmap or the mask after issuing the BitBltMasked() command, the |
|
533 method does not guarantee whether the old bitmap or mask contents, or the new ones will be used. |
|
534 Clients must call Finish() on the driver before modifying the bitmap or mask contents if they want a |
|
535 guaranteed result that the previously issued BitBltMasked() will be using the old bitmap or mask contents. |
|
536 |
|
537 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
538 |
|
539 @see CDirectGdiContext::BitBlt(const TPoint& aPoint, const CFbsBitmap& aBitmap, const TRect& aSourceRect); |
|
540 @see CDirectGdiContext::BitBltMasked(const TPoint&, const CFbsBitmap&,const TRect&, const CFbsBitmap&, TBool); |
|
541 |
|
542 @param aDestPos The destination for the top left corner of the transferred bitmap. |
|
543 It is relative to the top left corner of the destination bitmap, which may be the screen. |
|
544 @param aSourceBitmap A memory-resident source bitmap. |
|
545 @param aSourceRect A rectangle defining the piece of the bitmap to be drawn, |
|
546 with co-ordinates relative to the top left corner of the bitmap. |
|
547 @param aMaskBitmap Mask bitmap. |
|
548 @param aMaskPos The point on the mask bitmap to use as the top left corner |
|
549 |
|
550 @pre The rendering target has been activated. aBitmap and aMask hold valid handles. |
|
551 @post Request to draw the masked bitmap content has been accepted. |
|
552 There is no guarantee that the request has been processed when the method returns. |
|
553 |
|
554 @panic DGDI 7, if no context is activated |
|
555 */ |
|
556 EXPORT_C void CDirectGdiContext::BitBltMasked( |
|
557 const TPoint& aDestPos, |
|
558 const CFbsBitmap& aSourceBitmap, |
|
559 const TRect& aSourceRect, |
|
560 const CFbsBitmap& aMaskBitmap, |
|
561 const TPoint& aMaskPos) |
|
562 { |
|
563 GRAPHICS_TRACE2("CDirectGdiContext::BitBltMasked(%d,%d)", aDestPos.iX, aDestPos.iY); |
|
564 DoBitBltMasked (aDestPos, aSourceBitmap, aSourceRect, aMaskBitmap, EFalse, aMaskPos); |
|
565 } |
|
566 |
|
567 |
|
568 /** |
|
569 Resets the current clipping region to none. |
|
570 |
|
571 @see CDirectGdiContext::SetClippingRegion(const TRegion&) |
|
572 |
|
573 @pre The rendering target has been activated. |
|
574 @post Clipping region is reset to none. Subsequent rendering operations on current target will be clipped to the |
|
575 full area of the target. |
|
576 |
|
577 @panic DGDI 7, if the rendering context has not been activated. |
|
578 */ |
|
579 EXPORT_C void CDirectGdiContext::ResetClippingRegion() |
|
580 { |
|
581 GRAPHICS_TRACE("CDirectGdiContext::ResetClippingRegion"); |
|
582 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
583 iClippingRegion.Clear(); |
|
584 iEngine->ResetClippingRegion(); |
|
585 } |
|
586 |
|
587 |
|
588 /** |
|
589 Clears the entire target area with the current brush colour. The area is filled |
|
590 as if ESolidBrush is used. Current clipping region and drawing mode apply. |
|
591 |
|
592 @see CDirectGdiContext::Clear(const TRect&) |
|
593 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
594 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
595 @see CDirectGdiContext::SetClippingRegion(const TRegion& aRegion) |
|
596 |
|
597 @pre The rendering target has been activated. |
|
598 @post Request to clear given rectangular area (clipped to current clipping region) |
|
599 has been accepted. There is no guarantee that the request has been processed |
|
600 when the method returns. |
|
601 |
|
602 @panic DGDI 7, if the rendering context has not been activated. |
|
603 */ |
|
604 EXPORT_C void CDirectGdiContext::Clear() |
|
605 { |
|
606 GRAPHICS_TRACE("CDirectGdiContext::Clear"); |
|
607 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
608 iEngine->Clear(); |
|
609 } |
|
610 |
|
611 |
|
612 /** |
|
613 Clears the given rectangular area with current brush colour. The area is filled |
|
614 as if ESolidBrush is used. Current clipping region and drawing mode apply. |
|
615 |
|
616 @see CDirectGdiContext::Clear() |
|
617 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
618 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
619 @see CDirectGdiContext::SetClippingRegion(const TRegion&) |
|
620 |
|
621 @param aRect Area to be cleared. |
|
622 |
|
623 @pre The rendering target has been activated. |
|
624 @post Request to clear given rectangular area (clipped to current clipping region) has been accepted. |
|
625 There is no guarantee that the request has been processed when the method returns. |
|
626 |
|
627 @panic DGDI 7, if the rendering context has not been activated. |
|
628 */ |
|
629 EXPORT_C void CDirectGdiContext::Clear(const TRect& aRect) |
|
630 { |
|
631 GRAPHICS_TRACE2("CDirectGdiContext::Clear(%d,%d)", aRect.Width(), aRect.Height()); |
|
632 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
633 if(aRect.Width() <= 0 || aRect.Height() <= 0) |
|
634 { |
|
635 return; |
|
636 } |
|
637 iEngine->Clear(aRect); |
|
638 } |
|
639 |
|
640 |
|
641 /** |
|
642 Resets the bitmap brush pattern to none. If the current brush style is EPatternedBrush, the brush |
|
643 style will be set to ENullBrush. |
|
644 |
|
645 @see CDirectGdiContext::SetBrushPattern(const CFbsBitmap&) |
|
646 |
|
647 @pre None. |
|
648 @post The bitmap brush pattern is no longer used. |
|
649 */ |
|
650 EXPORT_C void CDirectGdiContext::ResetBrushPattern() |
|
651 { |
|
652 GRAPHICS_TRACE("CDirectGdiContext::ResetBrushPattern"); |
|
653 CleanUpBrushPattern(); |
|
654 if (iBrushStyle == DirectGdi::EPatternedBrush) |
|
655 { |
|
656 iBrushStyle = DirectGdi::ENullBrush; |
|
657 iEngine->SetBrushStyle(iBrushStyle); |
|
658 } |
|
659 iEngine->ResetBrushPattern(); |
|
660 } |
|
661 |
|
662 |
|
663 /** |
|
664 Releases the selected font for this context. |
|
665 |
|
666 @pre None. |
|
667 @post Internal resources previously allocated during SetFont() are released. |
|
668 |
|
669 @see CDirectGdiContext::SetFont() |
|
670 @see CGraphicsContext::DiscardFont() |
|
671 */ |
|
672 EXPORT_C void CDirectGdiContext::ResetFont() |
|
673 { |
|
674 GRAPHICS_TRACE("CDirectGdiContext::ResetFont"); |
|
675 iEngine->ResetFont(); |
|
676 iFont.Reset(); |
|
677 } |
|
678 |
|
679 |
|
680 /** |
|
681 Draws an arc. An arc is a segment of an ellipse which is defined by a given rectangle. The arc is drawn |
|
682 anti-clockwise from the arc start point to the arc end point. The arc start point is the intersection |
|
683 between vectors from the centre of the ellipse to the given start position and the ellipse. |
|
684 Arc end point is defined in the same way. |
|
685 |
|
686 @param aRect The rectangle which defines where to draw the ellipse. |
|
687 @param aStart Position to be used in defining the arc start point. |
|
688 @param aEnd Position to be used in defining the arc end point. |
|
689 |
|
690 @pre The rendering target has been activated. |
|
691 @post Request to draw an arc has been accepted. There is no guarantee that the request |
|
692 has been processed when the method returns. |
|
693 |
|
694 @panic DGDI 7, if the rendering context has not been activated. |
|
695 |
|
696 @see CDirectGdiContext::DrawPie(const TRect&, const TPoint&, const TPoint&) |
|
697 */ |
|
698 EXPORT_C void CDirectGdiContext::DrawArc(const TRect& aRect, const TPoint& aStart, const TPoint& aEnd) |
|
699 { |
|
700 GRAPHICS_TRACE("CDirectGdiContext::DrawArc"); |
|
701 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
702 if (aRect.IsEmpty() || iPenStyle == DirectGdi::ENullPen || (iPenSize.iWidth == 0) || (iPenSize.iHeight == 0)) |
|
703 { |
|
704 return; |
|
705 } |
|
706 iEngine->DrawArc(aRect, aStart, aEnd); |
|
707 } |
|
708 |
|
709 |
|
710 /** |
|
711 Draws and fills a pie. A pie is a shape defined by an arc from the ellipse and straight lines |
|
712 from the centre of the ellipse to the arc start and end position. |
|
713 |
|
714 @param aRect The rectangle which defines where to draw the ellipse |
|
715 @param aStart Position to be used in defining the arc start point |
|
716 @param aEnd Position to be used in defining the arc end point |
|
717 |
|
718 @pre The rendering target has been activated. |
|
719 @post Request to draw a pie has been accepted. There is no guarantee that the request |
|
720 has been processed when the method returns. |
|
721 |
|
722 @panic DGDI 7, if the rendering context has not been activated. |
|
723 @panic DGDI 9, if the brush style is EPatternedBrush but no pattern has been set. |
|
724 |
|
725 @see CDirectGdiContext::DrawArc(const TRect&, const TPoint&, const TPoint&) |
|
726 */ |
|
727 EXPORT_C void CDirectGdiContext::DrawPie(const TRect& aRect, const TPoint& aStart, const TPoint& aEnd) |
|
728 { |
|
729 GRAPHICS_TRACE("CDirectGdiContext::DrawPie"); |
|
730 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
731 GRAPHICS_ASSERT_ALWAYS(iBrushStyle != DirectGdi::EPatternedBrush || iBrushPatternUsed, EDirectGdiPanicBrushPatternNotSet); |
|
732 |
|
733 if (aRect.IsEmpty()) |
|
734 { |
|
735 return; |
|
736 } |
|
737 iEngine->DrawPie(aRect, aStart, aEnd); |
|
738 } |
|
739 |
|
740 /** |
|
741 Draws the bitmap contents into the destination rectangle. Scaling applies when |
|
742 the extents of the source bitmap and the destination rectangle do not match. |
|
743 If the source rectangle is not completely contained within the source |
|
744 bitmap's extents, no drawing will take place. |
|
745 |
|
746 If the client modifies the content of the bitmap after issuing a DrawBitmap() command, |
|
747 the method does not guarantee that the old bitmap content or the new one |
|
748 will be drawn. Clients must call Finish() on the driver before modifying the bitmap |
|
749 content if they want a guarantee that the previously issued DrawBitmap() will draw the |
|
750 old bitmap content. |
|
751 |
|
752 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
753 |
|
754 @see CDirectGdiContext::DrawBitmap(const TRect&, const CFbsBitmap&, const TRect&) |
|
755 |
|
756 @param aDestRect Destination rectangle. |
|
757 @param aSourceBitmap Source bitmap. |
|
758 |
|
759 @pre The rendering target has been activated. |
|
760 @post Request to draw the bitmap content has been accepted. |
|
761 There is no guarantee that the request has been processed when the method returns. |
|
762 |
|
763 @panic DGDI 7, if the rendering context has not been activated. |
|
764 */ |
|
765 EXPORT_C void CDirectGdiContext::DrawBitmap(const TRect& aDestRect, const CFbsBitmap& aSourceBitmap) |
|
766 { |
|
767 GRAPHICS_TRACE2("CDirectGdiContext::DrawBitmap(%d,%d)", aDestRect.iTl.iX, aDestRect.iTl.iY); |
|
768 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
769 if (ValidateBitmap (aSourceBitmap)) |
|
770 { |
|
771 DrawBitmap(aDestRect, aSourceBitmap,TRect(TPoint(0, 0), aSourceBitmap.SizeInPixels())); |
|
772 } |
|
773 } |
|
774 |
|
775 /** |
|
776 Draws the bitmap contents into the destination rectangle. Scaling applies when |
|
777 the destination and source rectangles do not match. The source bitmap may be |
|
778 compressed. The destination rectangle will be clipped with the current clipping |
|
779 region. If the source rectangle is not completely contained within the source |
|
780 bitmap's extents, no drawing will take place. |
|
781 |
|
782 If the client modifies the content of the bitmap after issuing a DrawBitmap() command, |
|
783 the method does not guarantee that the old bitmap content or the new one |
|
784 will be drawn. Clients must call Finish() on the driver before modifying the bitmap |
|
785 content if they want a guarantee that the previously issued DrawBitmap() will draw the |
|
786 old bitmap content. |
|
787 |
|
788 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
789 |
|
790 @see CDirectGdiContext::DrawBitmap(const TRect&, const CFbsBitmap&) |
|
791 |
|
792 @param aDestRect Destination rectangle. |
|
793 @param aSourceBitmap Source bitmap. |
|
794 @param aSourceRect Rectangle specifying the area of the source bitmap to be drawn. |
|
795 |
|
796 @pre The rendering target has been activated. |
|
797 @post Request to draw the bitmap content has been accepted. |
|
798 There is no guarantee that the request has been processed when the method returns. |
|
799 |
|
800 @panic DGDI 7, if the rendering context has not been activated. |
|
801 */ |
|
802 EXPORT_C void CDirectGdiContext::DrawBitmap(const TRect& aDestRect, const CFbsBitmap& aSourceBitmap, const TRect& aSourceRect) |
|
803 { |
|
804 GRAPHICS_TRACE2("CDirectGdiContext::DrawBitmap(%d,%d)", aDestRect.iTl.iX, aDestRect.iTl.iY); |
|
805 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
806 |
|
807 if (ValidateBitmap(aSourceBitmap)) |
|
808 { |
|
809 TSize sourceSize = aSourceBitmap.SizeInPixels(); |
|
810 // If source rectangle is not fully contained by the extents of the source bitmap, |
|
811 // or the size of the source bitmap is zero, do nothing. |
|
812 if (aSourceRect.iTl.iX >= 0 && |
|
813 aSourceRect.iTl.iY >= 0 && |
|
814 aSourceRect.iBr.iX <= sourceSize.iWidth && |
|
815 aSourceRect.iBr.iY <= sourceSize.iHeight && |
|
816 !aDestRect.IsEmpty() && !aSourceRect.IsEmpty()) |
|
817 { |
|
818 iEngine->DrawBitmap(aDestRect, aSourceBitmap, aSourceRect); |
|
819 } |
|
820 } |
|
821 } |
|
822 |
|
823 |
|
824 /** |
|
825 Draws bitmap content with masking. Scaling applies to both the source bitmap and the mask. |
|
826 Both the source and the mask bitmap may be compressed. The destination and source rectangles |
|
827 operate in a similar way to DrawBitmap(). |
|
828 |
|
829 This function uses either a black and white (binary) mask bitmap, or if the mask's display mode is |
|
830 EGray256, alpha blending is used. The result is undefined if the mask pixel value is neither black nor |
|
831 white and the mask display mode is other than EGray256. |
|
832 |
|
833 The mask is aligned with the source bitmap by aligning their first pixels within the source |
|
834 rectangle. If the mask size is greater than or equal to the source bitmap size, it will be |
|
835 scaled to fit the destination rectangle in the same way the source bitmap is scaled. |
|
836 If the mask has zero width or height, the error state is set to KErrArgument and no drawing is performed. |
|
837 |
|
838 If the mask is smaller than the source bitmap, it will be tiled to fit the source bitmap size, |
|
839 and then scaled to fit the destination rectangle. |
|
840 |
|
841 If the client modifies the content of the bitmap or mask after issuing a DrawBitmapMasked() command, |
|
842 the method does not guarantee whether the old bitmap or mask contents, or the new ones |
|
843 will be used. Clients must call Finish() on the driver before modifying the bitmap or mask contents |
|
844 if they want a guaranteed result that the previously issued DrawBitmapMasked() will be using the old |
|
845 bitmap or mask contents. |
|
846 |
|
847 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
848 |
|
849 @param aDestRect Destination rectangle. |
|
850 @param aSourceBitmap Source bitmap. |
|
851 @param aSourceRect Rectangle specifying the area of the source bitmap to be drawn. |
|
852 @param aMaskBitmap Mask bitmap. |
|
853 @param aInvertMask If EFalse, a source pixel that is masked by a black pixel is not transferred to |
|
854 the destination rectangle. If ETrue, then a source pixel that is masked by a |
|
855 white pixel is not transferred to the destination rectangle. If alpha blending |
|
856 is used instead of masking, this flag is ignored and no inversion takes place. |
|
857 |
|
858 @pre The rendering target has been activated. |
|
859 @post Request to draw the bitmap content with masking has been accepted. |
|
860 There is no guarantee that the request has been processed when the method returns. |
|
861 |
|
862 @panic DGDI 7, if the rendering context has not been activated. |
|
863 */ |
|
864 EXPORT_C void CDirectGdiContext::DrawBitmapMasked( |
|
865 const TRect& aDestRect, |
|
866 const CFbsBitmap& aSourceBitmap, |
|
867 const TRect& aSourceRect, |
|
868 const CFbsBitmap& aMaskBitmap, |
|
869 TBool aInvertMask) |
|
870 { |
|
871 GRAPHICS_TRACE2("CDirectGdiContext::DrawBitmapMasked(%d,%d)", aDestRect.iTl.iX, aDestRect.iTl.iY); |
|
872 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
873 |
|
874 if (ValidateSourceAndMaskBitmaps(aSourceBitmap, aMaskBitmap)) |
|
875 { |
|
876 TSize sourceSize = aSourceBitmap.SizeInPixels(); |
|
877 // Ensure source rect is fully within bounds of bitmap extents and |
|
878 // dest and source rect are not empty. |
|
879 if (aSourceRect.iTl.iX >= 0 && |
|
880 aSourceRect.iTl.iY >= 0 && |
|
881 aSourceRect.iBr.iX <= sourceSize.iWidth && |
|
882 aSourceRect.iBr.iY <= sourceSize.iHeight && |
|
883 !aDestRect.IsEmpty() && !aSourceRect.IsEmpty()) |
|
884 { |
|
885 iEngine->DrawBitmapMasked(aDestRect, aSourceBitmap, aSourceRect, aMaskBitmap, aInvertMask); |
|
886 } |
|
887 } |
|
888 } |
|
889 |
|
890 /** |
|
891 Draws and fills a rectangle with rounded corners. The corner is constructed as an arc of |
|
892 an ellipse. The outline is drawn in the current pen colour, size and style if the pen |
|
893 colour is not ENullPen. The area inside the rectangle is filled according to the current |
|
894 brush colour and style. |
|
895 |
|
896 If the corner size has zero width or height, a square-cornered rectangle is drawn. If the corner |
|
897 size is greater than half the extents of the rectangle, an ellipse is drawn. |
|
898 |
|
899 @param aRect The rectangle. |
|
900 @param aCornerSize The corner size. |
|
901 |
|
902 @see CDirectGdiContext::SetPenSize() |
|
903 @see CDirectGdiContext::SetPenStyle() |
|
904 @see CDirectGdiContext::SetPenColor() |
|
905 @see CDirectGdiContext::SetBrushColor() |
|
906 @see CDirectGdiContext::SetBrushStyle() |
|
907 @see CDirectGdiContext::SetBrushPattern() |
|
908 |
|
909 @pre The rendering target has been activated. |
|
910 @post Request to draw a rectangle with rounded corners has been accepted. There is no guarantee |
|
911 that the request has been processed when the method returns. |
|
912 |
|
913 @panic DGDI 7, if the rendering context has not been activated. |
|
914 @panic DGDI 9, if the brush style is EPatternedBrush but no pattern has been set. |
|
915 */ |
|
916 EXPORT_C void CDirectGdiContext::DrawRoundRect(const TRect& aRect, const TSize& aCornerSize) |
|
917 { |
|
918 GRAPHICS_TRACE("CDirectGdiContext::DrawRoundRect"); |
|
919 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
920 GRAPHICS_ASSERT_ALWAYS(iBrushStyle != DirectGdi::EPatternedBrush || iBrushPatternUsed, EDirectGdiPanicBrushPatternNotSet); |
|
921 |
|
922 TSize ellsize(aCornerSize); |
|
923 ellsize.iWidth <<= 1; |
|
924 ellsize.iHeight <<= 1; |
|
925 |
|
926 if (aRect.Width() > 0 && aRect.Height() > 0) |
|
927 { |
|
928 if (ellsize.iWidth < 3 || ellsize.iHeight < 3) |
|
929 { |
|
930 DrawRect(aRect); |
|
931 return; |
|
932 } |
|
933 if (aRect.Width() < ellsize.iWidth && aRect.Height() < ellsize.iHeight) |
|
934 { |
|
935 DrawEllipse(aRect); |
|
936 return; |
|
937 } |
|
938 iEngine->DrawRoundRect(aRect, aCornerSize); |
|
939 } |
|
940 } |
|
941 |
|
942 /** |
|
943 Draws a polyline using the points in an array. A polyline is a series of concatenated straight |
|
944 lines joining a set of points. Current pen settings and drawing mode applies. If @c aPointList |
|
945 has one element, a plot is performed. |
|
946 |
|
947 @param aPointList Array of points specifying points on the polyline. |
|
948 |
|
949 @pre The rendering target has been activated. |
|
950 @post Request to draw a polyline has been accepted. |
|
951 There is no guarantee that the request has been processed when the method returns. |
|
952 The internal drawing position is set to the last point in the array. |
|
953 |
|
954 @panic DGDI 7, if the rendering context has not been activated. |
|
955 |
|
956 @see CDirectGdiContext::DrawPolyLineNoEndPoint(const TArray<TPoint>&) |
|
957 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
958 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
959 @see CDirectGdiContext::SetPenColor(TRgb) |
|
960 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
961 */ |
|
962 EXPORT_C void CDirectGdiContext::DrawPolyLine(const TArray<TPoint>& aPointList) |
|
963 { |
|
964 GRAPHICS_TRACE("CDirectGdiContext::DrawPolyLine"); |
|
965 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
966 if ((aPointList.Count() < 1) || iPenStyle == DirectGdi::ENullPen || (iPenSize.iWidth == 0) || (iPenSize.iHeight == 0)) |
|
967 { |
|
968 return; |
|
969 } |
|
970 |
|
971 if (aPointList.Count() == 1) |
|
972 { |
|
973 Plot(aPointList[0]); |
|
974 } |
|
975 else |
|
976 { |
|
977 iEngine->DrawPolyLine(aPointList); |
|
978 } |
|
979 } |
|
980 |
|
981 |
|
982 /** |
|
983 Draws a polyline using the points in an array. A polyline is a series of concatenated straight |
|
984 lines joining a set of points. Current pen settings and drawing mode applies. If @c aPointList |
|
985 has less than two elements, no drawing is performed. If @c aPointList has exactly two elements |
|
986 then a DrawLine is performed. |
|
987 |
|
988 @param aPointList Array of points specifying points on the polyline. |
|
989 |
|
990 @pre The rendering target has been activated. |
|
991 @post Request to draw a polyline has been accepted. |
|
992 There is no guarantee that the request has been processed when the method returns. |
|
993 The internal drawing position is set to the last point in the array. |
|
994 |
|
995 @panic DGDI 7, if the rendering context has not been activated. |
|
996 |
|
997 @see CDirectGdiContext::DrawPolyLine(const TArray<TPoint>&) |
|
998 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
999 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1000 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1001 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
1002 */ |
|
1003 EXPORT_C void CDirectGdiContext::DrawPolyLineNoEndPoint(const TArray<TPoint>& aPointList) |
|
1004 { |
|
1005 GRAPHICS_TRACE("CDirectGdiContext::DrawPolyLineNoEndPoint"); |
|
1006 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1007 |
|
1008 const TInt points = aPointList.Count(); |
|
1009 |
|
1010 if (points == 1) |
|
1011 { |
|
1012 Plot(aPointList[0]); |
|
1013 } |
|
1014 else if (points == 2) |
|
1015 { |
|
1016 DrawLine(aPointList[0], aPointList[1]); |
|
1017 } |
|
1018 else if (points > 2 && !(iPenStyle == DirectGdi::ENullPen || (iPenSize.iWidth == 0) || (iPenSize.iHeight == 0))) |
|
1019 { |
|
1020 iEngine->DrawPolyLineNoEndPoint(aPointList); |
|
1021 } |
|
1022 } |
|
1023 |
|
1024 /** |
|
1025 Draws and fills a polygon defined using an array of points. The first point in the array defines the |
|
1026 start of the first side of the polygon. The final side of the polygon is drawn using the last point |
|
1027 from the array, and the line is drawn to the start point of the first side. The outline of the polygon |
|
1028 is drawn using the current pen settings and the area is filled with the current brush settings. |
|
1029 |
|
1030 Self-crossing polygons are filled according to the specified fill rule. |
|
1031 |
|
1032 If @c aPointList is empty, no drawing is performed. If it has one element, the result is the same as Plot(). |
|
1033 If it has two elements, the result is the same as DrawLine(). |
|
1034 |
|
1035 The error state is set to KErrArgument if aFillRule is an invalid fill rule. |
|
1036 |
|
1037 @param aPointList Array of points specifying the vertices of the polygon. |
|
1038 @param aFillRule Polygon filling rule. |
|
1039 |
|
1040 @pre The rendering target has been activated. |
|
1041 @post Request to draw a polygon has been accepted. There is no guarantee that the request has been processed |
|
1042 when the method returns. The internal drawing position is set to the last point in the array. |
|
1043 |
|
1044 @panic DGDI 7, if the rendering context has not been activated. |
|
1045 @panic DGDI 9, if the brush style is EPatternedBrush but no pattern has been set. |
|
1046 |
|
1047 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
1048 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1049 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1050 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1051 @see CDirectGdiContext::SetBrushStyle(DirectGdi::TBrushStyle) |
|
1052 @see CDirectGdiContext::SetBrushPattern(const CFbsBitmap&) |
|
1053 @see CDirectGdiContext::SetBrushOrigin(TPoint) |
|
1054 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
1055 @see DirectGdi::TFillRule |
|
1056 */ |
|
1057 EXPORT_C void CDirectGdiContext::DrawPolygon(const TArray<TPoint>& aPointList, DirectGdi::TFillRule aFillRule) |
|
1058 { |
|
1059 GRAPHICS_TRACE("CDirectGdiContext::DrawPolygon"); |
|
1060 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1061 GRAPHICS_ASSERT_ALWAYS(iBrushStyle != DirectGdi::EPatternedBrush || iBrushPatternUsed, EDirectGdiPanicBrushPatternNotSet); |
|
1062 |
|
1063 if (aFillRule != DirectGdi::EAlternate && aFillRule != DirectGdi::EWinding) |
|
1064 { |
|
1065 iDriver.SetError(KErrArgument); |
|
1066 return; |
|
1067 } |
|
1068 |
|
1069 if (aPointList.Count() == 0) |
|
1070 { |
|
1071 return; |
|
1072 } |
|
1073 |
|
1074 iEngine->DrawPolygon(aPointList, aFillRule); |
|
1075 } |
|
1076 |
|
1077 |
|
1078 /** |
|
1079 Draws and fills an ellipse inside the given rectangle. Current pen and brush settings apply. |
|
1080 |
|
1081 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
1082 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1083 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1084 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1085 @see CDirectGdiContext::SetBrushStyle(DirectGdi::TBrushStyle) |
|
1086 @see CDirectGdiContext::SetBrushPattern(const CFbsBitmap&) |
|
1087 |
|
1088 @param aRect The rectangle in which to draw the ellipse. |
|
1089 |
|
1090 @pre The rendering target has been activated. |
|
1091 @post Request to draw an ellipse has been accepted. |
|
1092 There is no guarantee that the request has been processed when the method returns. |
|
1093 |
|
1094 @panic DGDI 7, if the rendering context has not been activated. |
|
1095 @panic DGDI 9, if the brush style is EPatternedBrush but no pattern has been set. |
|
1096 */ |
|
1097 EXPORT_C void CDirectGdiContext::DrawEllipse(const TRect& aRect) |
|
1098 { |
|
1099 GRAPHICS_TRACE("CDirectGdiContext::DrawEllipse"); |
|
1100 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1101 GRAPHICS_ASSERT_ALWAYS(iBrushStyle != DirectGdi::EPatternedBrush || iBrushPatternUsed, EDirectGdiPanicBrushPatternNotSet); |
|
1102 |
|
1103 if (aRect.IsEmpty()) |
|
1104 { |
|
1105 return; |
|
1106 } |
|
1107 iEngine->DrawEllipse(aRect); |
|
1108 } |
|
1109 |
|
1110 |
|
1111 /** |
|
1112 Draws a straight line from the start to the end position using current pen size, colour and style. |
|
1113 |
|
1114 @param aStart Start position. |
|
1115 @param aEnd End position. |
|
1116 |
|
1117 @pre The rendering target has been activated. |
|
1118 @post Request to draw a straight line with the current pen colour, size and style has been accepted. |
|
1119 There is no guarantee that the request has been processed when the method returns. |
|
1120 The internal drawing position is set to @c aEnd. |
|
1121 |
|
1122 @panic DGDI 7, if the rendering context has not been activated. |
|
1123 |
|
1124 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
1125 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1126 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1127 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
1128 */ |
|
1129 EXPORT_C void CDirectGdiContext::DrawLine(const TPoint& aStart, const TPoint& aEnd) |
|
1130 { |
|
1131 GRAPHICS_TRACE("CDirectGdiContext::DrawLine"); |
|
1132 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1133 |
|
1134 // Do not draw if start/end at the same point or pensize is 0 |
|
1135 if(aStart == aEnd || iPenStyle == DirectGdi::ENullPen || iPenSize.iWidth == 0 || iPenSize.iHeight == 0) |
|
1136 { |
|
1137 return; |
|
1138 } |
|
1139 |
|
1140 iEngine->DrawLine(aStart, aEnd); |
|
1141 } |
|
1142 |
|
1143 |
|
1144 /** |
|
1145 Draws a straight line from the current internal drawing position to a point using the current pen size, colour and style. |
|
1146 |
|
1147 @param aPoint The end-point of the line. |
|
1148 |
|
1149 @pre Rendering target has been activated. |
|
1150 @post Request to draw a straight line to a specified point with the current pen colour, size and style has been accepted. |
|
1151 There is no guarantee that the request has been processed when the method returns. |
|
1152 Internal drawing position is set to @c aPoint. |
|
1153 |
|
1154 @panic DGDI 7, if the rendering context has not been activated. |
|
1155 |
|
1156 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
1157 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1158 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1159 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
1160 @see CDirectGdiContext::MoveTo(TPoint) |
|
1161 @see CDirectGdiContext::MoveBy(TPoint) |
|
1162 */ |
|
1163 EXPORT_C void CDirectGdiContext::DrawLineTo(const TPoint& aPoint) |
|
1164 { |
|
1165 GRAPHICS_TRACE("CDirectGdiContext::DrawLineTo"); |
|
1166 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1167 if(iPenStyle == DirectGdi::ENullPen || iPenSize.iWidth == 0 || iPenSize.iHeight == 0) |
|
1168 { |
|
1169 return; |
|
1170 } |
|
1171 iEngine->DrawLineTo (aPoint); |
|
1172 } |
|
1173 |
|
1174 |
|
1175 /** |
|
1176 Draws a straight line relative to the current internal drawing position, using a vector. |
|
1177 The start point of the line is the current internal drawing position. The vector @c aVector |
|
1178 is added to the internal drawing position to give the end point of the line. |
|
1179 |
|
1180 @param aVector The vector to add to the current internal drawing position, giving the end point of the line. |
|
1181 |
|
1182 @pre The rendering target has been activated. |
|
1183 @post The request to draw a straight line using the vector with current pen colour, size and style has been |
|
1184 accepted. There is no guarantee that the request has been processed when the method returns. |
|
1185 The internal drawing position is set to the end of the line. |
|
1186 |
|
1187 @panic DGDI 7, if the rendering context has not been activated. |
|
1188 |
|
1189 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
1190 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1191 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1192 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
1193 @see CDirectGdiContext::MoveTo(TPoint) |
|
1194 @see CDirectGdiContext::MoveBy(TPoint) |
|
1195 */ |
|
1196 EXPORT_C void CDirectGdiContext::DrawLineBy(const TPoint& aVector) |
|
1197 { |
|
1198 GRAPHICS_TRACE("CDirectGdiContext::DrawLineBy"); |
|
1199 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1200 if(iPenStyle == DirectGdi::ENullPen || iPenSize.iWidth == 0 || iPenSize.iHeight == 0) |
|
1201 { |
|
1202 return; |
|
1203 } |
|
1204 |
|
1205 if (aVector != TPoint(0,0)) |
|
1206 { |
|
1207 iEngine->DrawLineBy(aVector); |
|
1208 } |
|
1209 } |
|
1210 |
|
1211 |
|
1212 /** |
|
1213 Draws and fills a rectangle. The outlines are drawn according to the current pen colour, size and style. |
|
1214 The area inside the rectangle is filled according to the current brush colour and style. |
|
1215 |
|
1216 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
1217 @see CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle) |
|
1218 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1219 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1220 @see CDirectGdiContext::SetBrushStyle(DirectGdi::TBrushStyle) |
|
1221 @see CDirectGdiContext::SetBrushPattern(const CFbsBitmap&) |
|
1222 |
|
1223 @param aRect The rectangle. |
|
1224 |
|
1225 @pre The rendering target has been activated. |
|
1226 @post Request to draw a rectangle according to the current pen and brush settings has been accepted. |
|
1227 There is no guarantee that the request has been processed when the method returns. |
|
1228 |
|
1229 @panic DGDI 7, if the rendering context has not been activated. |
|
1230 @panic DGDI 9, if the brush style is EPatternedBrush but no pattern has been set. |
|
1231 */ |
|
1232 EXPORT_C void CDirectGdiContext::DrawRect(const TRect& aRect) |
|
1233 { |
|
1234 GRAPHICS_TRACE("CDirectGdiContext::DrawRect"); |
|
1235 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1236 GRAPHICS_ASSERT_ALWAYS(iBrushStyle != DirectGdi::EPatternedBrush || iBrushPatternUsed, EDirectGdiPanicBrushPatternNotSet); |
|
1237 |
|
1238 if(aRect.IsEmpty()) |
|
1239 return; |
|
1240 |
|
1241 iEngine->DrawRect(aRect); |
|
1242 } |
|
1243 |
|
1244 |
|
1245 /** |
|
1246 Draws text at the last print position. |
|
1247 |
|
1248 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1249 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1250 @see CDirectGdiContext::SetFont(const CFont*) |
|
1251 |
|
1252 @param aText The text string to be drawn. |
|
1253 @param aParam Parameters used in drawing text. |
|
1254 |
|
1255 @pre The rendering target has been activated. |
|
1256 @post Request to draw the text at the last text position using the current font and pen colour has been accepted. |
|
1257 There is no guarantee that the request has been processed when the method returns. |
|
1258 |
|
1259 @panic DGDI 7, if the rendering context has not been activated. |
|
1260 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush |
|
1261 style is neither ENullBrush nor ESolidBrush. |
|
1262 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1263 */ |
|
1264 EXPORT_C void CDirectGdiContext::DrawText(const TDesC& aText, const DirectGdi::TTextParameters* aParam) |
|
1265 { |
|
1266 GRAPHICS_TRACE("CDirectGdiContext::DrawText"); |
|
1267 DrawText(aText, aParam, iLastPrintPosition, DirectGdi::ELeft, CFont::EHorizontal); |
|
1268 } |
|
1269 |
|
1270 |
|
1271 /** |
|
1272 Draws text at the specified text position. |
|
1273 |
|
1274 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1275 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1276 @see CDirectGdiContext::SetFont(const CFont*) |
|
1277 |
|
1278 @param aText The text string to be drawn. |
|
1279 @param aParam Parameters used in drawing text. |
|
1280 @param aPosition The position to draw at. |
|
1281 |
|
1282 @pre The rendering target has been activated. |
|
1283 @post Request to draw the text at the specified position using the current font and pen colour has been accepted. |
|
1284 There is no guarantee that the request has been processed when the method returns. |
|
1285 @panic DGDI 7, if the rendering context has not been activated. |
|
1286 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush |
|
1287 style is neither ENullBrush nor ESolidBrush. |
|
1288 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1289 */ |
|
1290 EXPORT_C void CDirectGdiContext::DrawText(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TPoint& aPosition) |
|
1291 { |
|
1292 GRAPHICS_TRACE("CDirectGdiContext::DrawText"); |
|
1293 DrawText(aText, aParam, aPosition, DirectGdi::ELeft, CFont::EHorizontal); |
|
1294 } |
|
1295 |
|
1296 |
|
1297 /** |
|
1298 Draws text clipped to the specified rectangle. |
|
1299 |
|
1300 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1301 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1302 @see CDirectGdiContext::SetFont(const CFont*) |
|
1303 |
|
1304 @param aText The text string to be drawn. |
|
1305 @param aParam Parameters used in drawing text. |
|
1306 @param aClipRect The clipping rectangle. |
|
1307 |
|
1308 @pre The rendering target has been activated. |
|
1309 @post Request to draw the text at the last text position using the current font and pen colour, clipped to the specified rectangle has been accepted. |
|
1310 There is no guarantee that the request has been processed when the method returns. |
|
1311 @panic DGDI 7, if the rendering context has not been activated. |
|
1312 @panic DGDI 10, if the active font is an outline and/or shadow font and |
|
1313 the brush style is neither ENullBrush nor ESolidBrush. |
|
1314 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1315 */ |
|
1316 EXPORT_C void CDirectGdiContext::DrawText(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TRect& aClipRect) |
|
1317 { |
|
1318 GRAPHICS_TRACE("CDirectGdiContext::DrawText"); |
|
1319 DrawText(aText, aParam, iLastPrintPosition, DirectGdi::ELeft, CFont::EHorizontal, &aClipRect); |
|
1320 } |
|
1321 |
|
1322 |
|
1323 /** |
|
1324 Draws text clipped to the specified filled rectangle using a baseline offset, |
|
1325 horizontal alignment and a margin. |
|
1326 |
|
1327 @see CDirectGdiContext::SetPenColor(TRgb) |
|
1328 @see CDirectGdiContext::SetBrushColor(TRgb) |
|
1329 @see CDirectGdiContext::SetFont(const CFont*) |
|
1330 |
|
1331 @param aText The text string to be drawn. |
|
1332 @param aParam Parameters used in drawing text. |
|
1333 @param aClipFillRect The clipping rectangle (this rect will also be filled before text is plotted). |
|
1334 @param aBaselineOffset An offset in pixels for the baseline from the normal position (bottom of the rectangle minus the descent of the font). |
|
1335 @param aAlignment Horizontal alignment option relative to the specified rectangle. |
|
1336 @param aMargin Offset to add to the position as calculated using specified rectangle. |
|
1337 |
|
1338 @pre The rendering target has been activated. |
|
1339 @post Request to draw the text within the filled rectangle using the current font and pen colour, offset and clipped to the specified rectangle has been accepted. |
|
1340 There is no guarantee that the request has been processed when the method returns. |
|
1341 @panic DGDI 7, if the rendering context has not been activated. |
|
1342 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush |
|
1343 style is neither ENullBrush nor ESolidBrush. |
|
1344 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1345 */ |
|
1346 EXPORT_C void CDirectGdiContext::DrawText(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TRect& aClipFillRect, TInt aBaselineOffset, DirectGdi::TTextAlign aAlignment, TInt aMargin) |
|
1347 { |
|
1348 GRAPHICS_TRACE("CDirectGdiContext::DrawText"); |
|
1349 TPoint p(aClipFillRect.iTl); |
|
1350 p.iY += aBaselineOffset; |
|
1351 switch (aAlignment) |
|
1352 { |
|
1353 case DirectGdi::ELeft: |
|
1354 { |
|
1355 p.iX += aMargin; |
|
1356 break; |
|
1357 } |
|
1358 case DirectGdi::ERight: |
|
1359 { |
|
1360 p.iX = aClipFillRect.iBr.iX - aMargin; |
|
1361 break; |
|
1362 } |
|
1363 case DirectGdi::ECenter: |
|
1364 { |
|
1365 p.iX += (aClipFillRect.Width() >> 1) + aMargin; |
|
1366 break; |
|
1367 } |
|
1368 default: |
|
1369 { |
|
1370 iDriver.SetError(KErrArgument); |
|
1371 return; |
|
1372 } |
|
1373 } |
|
1374 DrawText(aText, aParam, p, aAlignment, CFont::EHorizontal, &aClipFillRect, &aClipFillRect); |
|
1375 } |
|
1376 |
|
1377 |
|
1378 /** |
|
1379 The private general DrawText routine that implements all the others. |
|
1380 |
|
1381 @param aText The text to be drawn. |
|
1382 @param aParam Parameters used in drawing text. |
|
1383 @param aPosition The origin of the text. |
|
1384 @param aAlignment Left, centred or right, around aPosition; not used if drawing vertically. |
|
1385 @param aDirection Direction: left to right, right to left, or top to bottom. |
|
1386 @param aClipRect If non-null, used as a clippingrect when the text is drawn. |
|
1387 @param aFillRect If non-null, filled before the text is drawn. |
|
1388 |
|
1389 @panic DGDI 7, if the rendering context has not been activated. |
|
1390 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush |
|
1391 style is neither ENullBrush nor ESolidBrush. |
|
1392 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1393 */ |
|
1394 void CDirectGdiContext::DrawText(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TPoint& aPosition, DirectGdi::TTextAlign aAlignment, |
|
1395 CFont::TTextDirection aDirection, const TRect* aClipRect, const TRect* aFillRect) |
|
1396 { |
|
1397 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1398 // anything to do? |
|
1399 if (aClipRect && aClipRect->IsEmpty()) |
|
1400 { |
|
1401 iDriver.SetError(KErrArgument); |
|
1402 return; |
|
1403 } |
|
1404 |
|
1405 GRAPHICS_ASSERT_ALWAYS(iFont.Handle() != 0, EDirectGdiPanicNoFontSelected); |
|
1406 // This next check actually covers both bitmap and open fonts |
|
1407 const CBitmapFont* bitmap_font = iFont.Address(); |
|
1408 GRAPHICS_ASSERT_ALWAYS(bitmap_font != 0, EDirectGdiPanicNoFontSelected); |
|
1409 |
|
1410 // measure the text |
|
1411 CFont::TMeasureTextInput measure_text_input; |
|
1412 measure_text_input.iCharJustNum = iCharJustNum; |
|
1413 measure_text_input.iCharJustExcess = iCharJustExcess; |
|
1414 measure_text_input.iWordJustNum = iWordJustNum; |
|
1415 measure_text_input.iWordJustExcess = iWordJustExcess; |
|
1416 measure_text_input.iFlags |= CFont::TMeasureTextInput::EFVisualOrder; |
|
1417 if (aParam) |
|
1418 { |
|
1419 GRAPHICS_ASSERT_ALWAYS(aParam->iStart < aParam->iEnd ,EDirectGdiPanicBadParameter); |
|
1420 measure_text_input.iStartInputChar = aParam->iStart; |
|
1421 measure_text_input.iEndInputChar = Min(aText.Length(),aParam->iEnd); |
|
1422 } |
|
1423 CFont::TMeasureTextOutput measure_text_output; |
|
1424 const TInt advance = iFont.MeasureText(aText, &measure_text_input, &measure_text_output); |
|
1425 TRect text_bounds = measure_text_output.iBounds; |
|
1426 |
|
1427 //for linked fonts need an adjustment to the underline postion |
|
1428 TInt underlineStrikeoutOffset = BaselineCorrection(); |
|
1429 |
|
1430 if (iUnderline == DirectGdi::EUnderlineOn) |
|
1431 { |
|
1432 TInt underline_top = 0; |
|
1433 TInt underline_bottom = 0; |
|
1434 GetUnderlineMetrics(underline_top, underline_bottom); |
|
1435 underline_top+=underlineStrikeoutOffset; |
|
1436 underline_bottom+=underlineStrikeoutOffset; |
|
1437 text_bounds.iTl.iY = Min(text_bounds.iTl.iY, underline_top); |
|
1438 text_bounds.iBr.iY = Max(text_bounds.iBr.iY, underline_bottom); |
|
1439 } |
|
1440 if (iStrikethrough == DirectGdi::EStrikethroughOn) |
|
1441 { |
|
1442 TInt strike_top = 0; |
|
1443 TInt strike_bottom = 0; |
|
1444 GetStrikethroughMetrics(strike_top, strike_bottom); |
|
1445 strike_top+=underlineStrikeoutOffset; |
|
1446 strike_bottom+=underlineStrikeoutOffset; |
|
1447 text_bounds.iTl.iY = Min(text_bounds.iTl.iY, strike_top); |
|
1448 text_bounds.iBr.iY = Max(text_bounds.iBr.iY, strike_bottom); |
|
1449 } |
|
1450 if (iUnderline == DirectGdi::EUnderlineOn || iStrikethrough == DirectGdi::EStrikethroughOn) |
|
1451 { |
|
1452 if (aDirection == CFont::EHorizontal) |
|
1453 { |
|
1454 text_bounds.iTl.iX = Min(text_bounds.iTl.iX, 0); |
|
1455 text_bounds.iBr.iX = Max(text_bounds.iBr.iX, advance); |
|
1456 } |
|
1457 else |
|
1458 { |
|
1459 text_bounds.iTl.iY = Min(text_bounds.iTl.iY, 0); |
|
1460 text_bounds.iBr.iY = Max(text_bounds.iBr.iY, advance); |
|
1461 } |
|
1462 } |
|
1463 |
|
1464 // work out the text origin and new drawing position |
|
1465 TPoint text_origin = aPosition; |
|
1466 if (aDirection != CFont::EVertical) |
|
1467 { |
|
1468 const TInt leftSideBearing = Min(text_bounds.iTl.iX, 0); |
|
1469 const TInt rightSideBearing = Max(text_bounds.iBr.iX, advance); |
|
1470 switch (aAlignment) |
|
1471 { |
|
1472 // We are forbidding side-bearings to leak over the sides here, |
|
1473 // but still keeping the start and end pen positions within bounds. |
|
1474 case DirectGdi::ELeft: |
|
1475 text_origin.iX -= leftSideBearing; |
|
1476 break; |
|
1477 case DirectGdi::ERight: |
|
1478 text_origin.iX -= rightSideBearing; |
|
1479 break; |
|
1480 case DirectGdi::ECenter: |
|
1481 // Centre is the average of left and right |
|
1482 text_origin.iX -= (leftSideBearing + rightSideBearing) >> 1; |
|
1483 break; |
|
1484 default: |
|
1485 iDriver.SetError(KErrArgument); |
|
1486 return; |
|
1487 } |
|
1488 } |
|
1489 iLastPrintPosition = text_origin; |
|
1490 if (aDirection == CFont::EHorizontal) |
|
1491 { |
|
1492 iLastPrintPosition.iX += advance; |
|
1493 } |
|
1494 else |
|
1495 { |
|
1496 iLastPrintPosition.iY += advance; |
|
1497 } |
|
1498 text_origin.iY += bitmap_font->iAlgStyle.iBaselineOffsetInPixels; |
|
1499 text_bounds.Move(text_origin); |
|
1500 text_origin += iOrigin; |
|
1501 |
|
1502 // determine clipping rectangle |
|
1503 TRect clipRect = aClipRect ? *aClipRect : text_bounds; |
|
1504 |
|
1505 // fill the box if necessary |
|
1506 if (aFillRect && (iBrushStyle != DirectGdi::ENullBrush)) |
|
1507 { |
|
1508 TRect fillBox = *aFillRect; |
|
1509 if (fillBox.Intersects(clipRect)) |
|
1510 { |
|
1511 fillBox.Intersection(clipRect); |
|
1512 iEngine->SetPenStyle(DirectGdi::ENullPen); // Fill box, don't outline it |
|
1513 iEngine->DrawRect(fillBox); |
|
1514 iEngine->SetPenStyle(iPenStyle); // Put the pen style back |
|
1515 } |
|
1516 } |
|
1517 if (!aText.Length()) |
|
1518 { |
|
1519 return; |
|
1520 } |
|
1521 |
|
1522 clipRect.Move(iOrigin); |
|
1523 |
|
1524 // decide which drawing routine to call |
|
1525 |
|
1526 TOpenFontMetrics metrics; |
|
1527 iFont.GetFontMetrics(metrics); |
|
1528 const TInt maxwidth = metrics.MaxWidth(); |
|
1529 // extext will be TRUE, if font is underline/strikethrough/anti-aliased or it has shadow/outline effects ON. |
|
1530 // Depending on these properties it will call the proper draw routine. |
|
1531 TBool extext = EFalse; |
|
1532 TBool normaltext = EFalse; |
|
1533 const TBool antiAliased = (bitmap_font->GlyphBitmapType() == EAntiAliasedGlyphBitmap); |
|
1534 const TBool outlineAndShadow = (bitmap_font->GlyphBitmapType() == EFourColourBlendGlyphBitmap); |
|
1535 if (antiAliased || outlineAndShadow ) |
|
1536 { |
|
1537 if ((outlineAndShadow) && !((iBrushStyle == DirectGdi::ENullBrush) || (iBrushStyle == DirectGdi::ESolidBrush))) |
|
1538 { |
|
1539 //For future compatibility it is better if brush style of ENullBrush or ESolidBrush is used |
|
1540 //when drawing outline and shadow fonts. |
|
1541 GRAPHICS_PANIC_ALWAYS(EDirectGdiPanicInvalidBrushStyle); |
|
1542 } |
|
1543 extext = ETrue; |
|
1544 } |
|
1545 else if ((iUnderline == DirectGdi::EUnderlineOn) || (iStrikethrough == DirectGdi::EStrikethroughOn) || (iCharJustNum > 0) || (iWordJustNum > 0)) |
|
1546 extext = ETrue; |
|
1547 else |
|
1548 normaltext = ETrue; |
|
1549 |
|
1550 const TInt charjustexcess = iCharJustExcess; |
|
1551 const TInt charjustnum = iCharJustNum; |
|
1552 const TInt wordjustexcess = iWordJustExcess; |
|
1553 const TInt wordjustnum = iWordJustNum; |
|
1554 |
|
1555 // Set up the parameter block for character positioning. |
|
1556 CFont::TPositionParam param; |
|
1557 param.iDirection = static_cast<TInt16>(aDirection); |
|
1558 param.iText.Set(aText); |
|
1559 TInt endDraw = aText.Length(); |
|
1560 if (aParam) |
|
1561 { |
|
1562 param.iPosInText = aParam->iStart; |
|
1563 endDraw = Min(aText.Length(),aParam->iEnd); |
|
1564 } |
|
1565 else |
|
1566 { |
|
1567 param.iPosInText = 0; |
|
1568 } |
|
1569 param.iPen = text_origin; |
|
1570 |
|
1571 // Draw the text. |
|
1572 if (normaltext) |
|
1573 { |
|
1574 DoDrawText(param, endDraw, clipRect); |
|
1575 } |
|
1576 else if (extext) |
|
1577 { |
|
1578 DoDrawTextEx(param, endDraw, clipRect,underlineStrikeoutOffset); |
|
1579 } |
|
1580 |
|
1581 // Reset the justification parameters to their original values. |
|
1582 // These will be updated as required later in code. |
|
1583 iCharJustExcess = charjustexcess; |
|
1584 iCharJustNum = charjustnum; |
|
1585 iWordJustExcess = wordjustexcess; |
|
1586 iWordJustNum = wordjustnum; |
|
1587 |
|
1588 if (iAutoUpdateJustification) |
|
1589 UpdateJustification(aText, aParam); |
|
1590 } |
|
1591 |
|
1592 /** |
|
1593 Overridden function which draws monochrome text within the given clip rectangle. No rotation applied. |
|
1594 @param aParam Defines glyph code, ligature creation and diacritic placement. |
|
1595 @param aEnd The end position within the text descriptor to draw. |
|
1596 @param aClipRect If not-empty, used as a clippingrect when the text is drawn. |
|
1597 */ |
|
1598 void CDirectGdiContext::DoDrawText(CFont::TPositionParam& aParam, const TInt aEnd, const TRect& aClipRect) |
|
1599 { |
|
1600 iEngine->BeginDrawGlyph(); |
|
1601 RShapeInfo shapeInfo; |
|
1602 while (aParam.iPosInText < aEnd) |
|
1603 { |
|
1604 if (iFont.GetCharacterPosition2(aParam, shapeInfo)) |
|
1605 { |
|
1606 const CFont::TPositionParam::TOutput* output = aParam.iOutput; |
|
1607 for (TInt i = 0; i < aParam.iOutputGlyphs; ++i, ++output) |
|
1608 iEngine->DrawGlyph(output->iBounds.iTl, output->iCode, output->iBitmap, EMonochromeGlyphBitmap, output->iBitmapSize, aClipRect); // All other parameters are default |
|
1609 } |
|
1610 } |
|
1611 iEngine->EndDrawGlyph(); |
|
1612 |
|
1613 if (shapeInfo.IsOpen()) |
|
1614 shapeInfo.Close(); |
|
1615 } |
|
1616 |
|
1617 |
|
1618 /** |
|
1619 Overridden function which draws monochrome text within the given clip rectangle. |
|
1620 The current rotation and font style (strikethrough, underline) are applied. |
|
1621 |
|
1622 @param aParam Defines glyph code, ligature creation and diacritic placement. |
|
1623 @param aEnd The end position within the text descriptor to draw. |
|
1624 @param aClipRect If not-empty, used as a clipping rect when the text is drawn. |
|
1625 @param aUnderlineStrikethroughOffset the offset for the underline, passed to save calculating this value again |
|
1626 */ |
|
1627 void CDirectGdiContext::DoDrawTextEx(CFont::TPositionParam& aParam, const TInt aEnd, const TRect& aClipRect, const TInt aUnderlineStrikethroughOffset) |
|
1628 { |
|
1629 TPoint startPen = aParam.iPen; |
|
1630 const CBitmapFont* bitmap_font = iFont.Address(); |
|
1631 TInt underlineTop = 0; |
|
1632 TInt underlineBottom = 0; |
|
1633 if (iUnderline == DirectGdi::EUnderlineOn) |
|
1634 { |
|
1635 GetUnderlineMetrics(underlineTop, underlineBottom); |
|
1636 underlineTop+=aUnderlineStrikethroughOffset; |
|
1637 underlineBottom+=aUnderlineStrikethroughOffset; |
|
1638 } |
|
1639 TInt strikeTop = 0; |
|
1640 TInt strikeBottom = 0; |
|
1641 if (iStrikethrough == DirectGdi::EStrikethroughOn) |
|
1642 { |
|
1643 GetStrikethroughMetrics(strikeTop, strikeBottom); |
|
1644 strikeTop+=aUnderlineStrikethroughOffset; |
|
1645 strikeBottom+=aUnderlineStrikethroughOffset; |
|
1646 } |
|
1647 |
|
1648 iEngine->BeginDrawGlyph(); |
|
1649 RShapeInfo shapeInfo; |
|
1650 while (aParam.iPosInText < aEnd) |
|
1651 { |
|
1652 if (!iFont.GetCharacterPosition2(aParam, shapeInfo)) |
|
1653 { |
|
1654 continue; |
|
1655 } |
|
1656 |
|
1657 TInt adjustment = 0; |
|
1658 if ((iCharJustExcess > 0) && (iCharJustNum > 0)) // character clipping/justification |
|
1659 { |
|
1660 adjustment = CGraphicsContext::JustificationInPixels(iCharJustExcess, iCharJustNum); |
|
1661 } |
|
1662 |
|
1663 const CFont::TPositionParam::TOutput* output = aParam.iOutput; |
|
1664 for (TInt i = 0; i < aParam.iOutputGlyphs; ++i, ++output) |
|
1665 { |
|
1666 //get the character metrics for the glyph type |
|
1667 TOpenFontCharMetrics characterParams; |
|
1668 const TUint8* bitmap; |
|
1669 TSize size; |
|
1670 //note may now be using a glyph code, and not a character |
|
1671 iFont.GetCharacterData(aParam.iOutput[i].iCode,characterParams,bitmap,size); |
|
1672 TGlyphBitmapType glyphType = characterParams.GlyphType(); |
|
1673 |
|
1674 switch (glyphType) |
|
1675 { |
|
1676 case EAntiAliasedGlyphBitmap: |
|
1677 case EFourColourBlendGlyphBitmap: |
|
1678 case EDefaultGlyphBitmap: |
|
1679 iEngine->DrawGlyph(output->iBounds.iTl, output->iCode, output->iBitmap, glyphType, output->iBitmapSize, aClipRect); |
|
1680 break; |
|
1681 |
|
1682 default: |
|
1683 //if the outline or shadow is not specified for the character, then use the font setting for the glyph bitmap type |
|
1684 iEngine->DrawGlyph(output->iBounds.iTl, output->iCode, output->iBitmap, |
|
1685 bitmap_font->GlyphBitmapType(), output->iBitmapSize, aClipRect); |
|
1686 break; |
|
1687 } |
|
1688 } |
|
1689 |
|
1690 if (adjustment) |
|
1691 { |
|
1692 aParam.iPen.iX += adjustment; |
|
1693 } |
|
1694 if ((iWordJustExcess > 0) && (iWordJustNum > 0) && (aParam.iOutput[0].iCode == 0x0020)) // word justification |
|
1695 { |
|
1696 adjustment = CGraphicsContext::JustificationInPixels(iWordJustExcess, iWordJustNum); |
|
1697 aParam.iPen.iX += adjustment; |
|
1698 } |
|
1699 } |
|
1700 iEngine->EndDrawGlyph(); |
|
1701 if (shapeInfo.IsOpen()) |
|
1702 shapeInfo.Close(); |
|
1703 |
|
1704 if (iUnderline == DirectGdi::EUnderlineOn) |
|
1705 { |
|
1706 TRect underlineRect(startPen.iX, startPen.iY + underlineTop, aParam.iPen.iX, startPen.iY + underlineBottom); |
|
1707 FillRect(underlineRect, iPenColor, aClipRect); |
|
1708 } |
|
1709 |
|
1710 if (iStrikethrough == DirectGdi::EStrikethroughOn) |
|
1711 { |
|
1712 TRect strikethroughRect(startPen.iX, startPen.iY + strikeTop, aParam.iPen.iX, startPen.iY + strikeBottom); |
|
1713 FillRect(strikethroughRect, iPenColor, aClipRect); |
|
1714 } |
|
1715 } |
|
1716 |
|
1717 |
|
1718 /** |
|
1719 Fills the given rectangle with the specified colour (subject to the clip rect). |
|
1720 This function is internal and used by the text drawing routines. |
|
1721 |
|
1722 @param aRect The rectangle to fill. |
|
1723 @param aColor The colour to fill it with. |
|
1724 @param aClipRect The clipping rect. |
|
1725 */ |
|
1726 void CDirectGdiContext::FillRect(const TRect& aRect, const TRgb& aColor, const TRect& aClipRect) |
|
1727 { |
|
1728 TRect fillRect = aRect; |
|
1729 if (fillRect.Intersects(aClipRect)) |
|
1730 { |
|
1731 fillRect.Intersection(aClipRect); |
|
1732 // Override the current settings temporarily |
|
1733 iEngine->SetBrushColor(aColor); |
|
1734 iEngine->SetBrushStyle(DirectGdi::ESolidBrush); |
|
1735 iEngine->SetPenStyle(DirectGdi::ENullPen); // Fill box, don't outline it |
|
1736 fillRect.Move(-iOrigin); |
|
1737 iEngine->DrawRect(fillRect); |
|
1738 // Put things back |
|
1739 iEngine->SetPenStyle(iPenStyle); |
|
1740 iEngine->SetBrushStyle(iBrushStyle); |
|
1741 iEngine->SetBrushColor(iBrushColor); |
|
1742 } |
|
1743 } |
|
1744 |
|
1745 |
|
1746 /** |
|
1747 Draws text at the last print position and then rotates it into a vertical position. |
|
1748 |
|
1749 @param aText The text string to be drawn. |
|
1750 @param aParam Parameters used in drawing text. |
|
1751 @param aUp If ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1752 |
|
1753 @panic DGDI 7, if the rendering context has not been activated. |
|
1754 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush |
|
1755 style is neither ENullBrush nor ESolidBrush. |
|
1756 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1757 */ |
|
1758 EXPORT_C void CDirectGdiContext::DrawTextVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, TBool aUp) |
|
1759 { |
|
1760 GRAPHICS_TRACE("CDirectGdiContext::DrawTextVertical"); |
|
1761 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1762 // This next check covers both bitmap and open fonts |
|
1763 const CBitmapFont* bitmapFont = iFont.Address(); |
|
1764 GRAPHICS_ASSERT_ALWAYS(bitmapFont != 0, EDirectGdiPanicNoFontSelected); |
|
1765 TRect clipRect2(0, 0, 0, 0); |
|
1766 TInt baselineOffset = 0; |
|
1767 TInt margin = 0; |
|
1768 CalculateClipRect2PlusBaselineOffsetAndMargin(aText, aParam, iLastPrintPosition, aUp, clipRect2, baselineOffset, margin); |
|
1769 DrawTextVertical(aText, aParam, NULL, &clipRect2, NULL, baselineOffset, -1, aUp, DirectGdi::ELeft, margin); //-1 signifies that text will not be clipped |
|
1770 } |
|
1771 |
|
1772 |
|
1773 /** |
|
1774 Draws text vertically from the specified position. |
|
1775 |
|
1776 @param aText The text string to be drawn. |
|
1777 @param aParam Parameters used in drawing text. |
|
1778 @param aPosition A point specifying the position of the left end of the text. |
|
1779 @param aUp If ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1780 |
|
1781 @panic DGDI 7, if the rendering context has not been activated. |
|
1782 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush style is neither |
|
1783 ENullBrush nor ESolidBrush. |
|
1784 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1785 */ |
|
1786 EXPORT_C void CDirectGdiContext::DrawTextVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TPoint& aPosition, TBool aUp) |
|
1787 { |
|
1788 GRAPHICS_TRACE("CDirectGdiContext::DrawTextVertical"); |
|
1789 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1790 // This next check covers both bitmap and open fonts |
|
1791 const CBitmapFont* bitmapFont = iFont.Address(); |
|
1792 GRAPHICS_ASSERT_ALWAYS(bitmapFont != 0, EDirectGdiPanicNoFontSelected); |
|
1793 TRect clipRect2(0, 0, 0, 0); |
|
1794 TInt baselineOffset = 0; |
|
1795 TInt margin = 0; |
|
1796 CalculateClipRect2PlusBaselineOffsetAndMargin(aText, aParam, aPosition, aUp, clipRect2, baselineOffset, margin); |
|
1797 DrawTextVertical(aText, aParam, NULL, &clipRect2, NULL, baselineOffset, -1, aUp, DirectGdi::ELeft, margin);//-1 signifies that text will not be clipped |
|
1798 } |
|
1799 |
|
1800 |
|
1801 /** |
|
1802 Draws text clipped to the specified rectangle and then rotates it into a vertical position. |
|
1803 |
|
1804 @param aText The text string to be drawn. |
|
1805 @param aParam Parameters used in drawing text. |
|
1806 @param aClipRect The clipping rectangle. |
|
1807 @param aUp ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1808 |
|
1809 @panic DGDI 7, if the rendering context has not been activated. |
|
1810 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush style is neither ENullBrush |
|
1811 nor ESolidBrush. |
|
1812 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1813 */ |
|
1814 EXPORT_C void CDirectGdiContext::DrawTextVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TRect& aClipRect, TBool aUp) |
|
1815 { |
|
1816 GRAPHICS_TRACE("CDirectGdiContext::DrawTextVertical"); |
|
1817 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1818 // This next check covers both bitmap and open fonts |
|
1819 const CBitmapFont* bitmapFont = iFont.Address(); |
|
1820 GRAPHICS_ASSERT_ALWAYS(bitmapFont != 0, EDirectGdiPanicNoFontSelected); |
|
1821 TRect clipRect2(0, 0, 0, 0); |
|
1822 TInt baselineOffset = 0; |
|
1823 TInt margin = 0; |
|
1824 CalculateClipRect2PlusBaselineOffsetAndMargin(aText, aParam, iLastPrintPosition, aUp, clipRect2, baselineOffset, margin); |
|
1825 DrawTextVertical(aText, aParam, &aClipRect, &clipRect2, NULL, baselineOffset, -1, aUp, DirectGdi::ELeft, margin); |
|
1826 } |
|
1827 |
|
1828 |
|
1829 /** |
|
1830 Private internal function for calculating several parameters needed by these routines. |
|
1831 |
|
1832 @param aText The text string to be drawn. |
|
1833 @param aParam Parameters used in drawing text. |
|
1834 @param aPosition A point specifying the position of the left end of the text. |
|
1835 @param aUp ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1836 @param aClipRect2 On return, contains clipping rectangle. |
|
1837 @param aBaselineOffset On return, contains baseline offset. |
|
1838 @param aMargin On return, contains margin. |
|
1839 */ |
|
1840 void CDirectGdiContext::CalculateClipRect2PlusBaselineOffsetAndMargin(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TPoint& aPosition, TBool aUp, TRect& aClipRect2, TInt& aBaselineOffset, TInt& aMargin) |
|
1841 { |
|
1842 TOpenFontMetrics metrics; |
|
1843 iFont.GetFontMetrics(metrics); |
|
1844 aBaselineOffset = metrics.MaxHeight(); |
|
1845 TInt height = aBaselineOffset + metrics.MaxDepth(); |
|
1846 // The next few lines do much the same as TextWidthInPixels but pass |
|
1847 // the text in visual order instead of logical order and also take |
|
1848 // full account of left and right side bearings on the text |
|
1849 CFont::TMeasureTextOutput output; |
|
1850 CFont::TMeasureTextInput input; |
|
1851 input.iFlags = CFont::TMeasureTextInput::EFVisualOrder; |
|
1852 if (aParam) |
|
1853 { |
|
1854 GRAPHICS_ASSERT_ALWAYS(aParam->iStart < aParam->iEnd ,EDirectGdiPanicBadParameter); |
|
1855 input.iStartInputChar = aParam->iStart; |
|
1856 input.iEndInputChar = Min(aText.Length(),aParam->iEnd); |
|
1857 } |
|
1858 TInt advance = iFont.MeasureText(aText, &input, &output); |
|
1859 TInt leftBearing = output.iBounds.iTl.iX; |
|
1860 TInt rightBearing = advance - output.iBounds.iBr.iX; |
|
1861 aMargin = 0; |
|
1862 if (aUp) |
|
1863 { |
|
1864 aClipRect2.iTl.iX = aPosition.iX - aBaselineOffset; |
|
1865 aClipRect2.iTl.iY = aPosition.iY - advance; |
|
1866 aClipRect2.iBr.iX = aPosition.iX + height - aBaselineOffset + 1; |
|
1867 aClipRect2.iBr.iY = aPosition.iY; |
|
1868 if (leftBearing < 0) |
|
1869 { |
|
1870 aClipRect2.iBr.iY -= leftBearing; |
|
1871 aMargin = -leftBearing; |
|
1872 } |
|
1873 if (rightBearing < 0) |
|
1874 { |
|
1875 aClipRect2.iTl.iY += rightBearing; |
|
1876 } |
|
1877 } |
|
1878 else |
|
1879 { |
|
1880 aClipRect2.iTl.iX = aPosition.iX + aBaselineOffset- height; |
|
1881 aClipRect2.iTl.iY = aPosition.iY; |
|
1882 aClipRect2.iBr.iX = aPosition.iX + aBaselineOffset + 1; |
|
1883 aClipRect2.iBr.iY = aPosition.iY + advance; |
|
1884 if (leftBearing < 0) |
|
1885 { |
|
1886 aClipRect2.iTl.iY += leftBearing; |
|
1887 aMargin = -leftBearing; |
|
1888 } |
|
1889 if (rightBearing < 0) |
|
1890 { |
|
1891 aClipRect2.iBr.iY -= rightBearing; |
|
1892 } |
|
1893 } |
|
1894 } |
|
1895 |
|
1896 |
|
1897 /** |
|
1898 Draws text vertically, clipped to a specified rectangle, using a baseline offset, alignment and margin. |
|
1899 |
|
1900 @param aText The text string to be drawn. |
|
1901 @param aParam Parameters used in drawing text. |
|
1902 @param aClipFillRect The clipping rectangle (this rect will also be filled before text is plotted). |
|
1903 @param aBaselineOffset Number of pixels to offset the baseline by. |
|
1904 @param aUp ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1905 @param aVert Vertical alignment of the text relative to the specified rectangle. |
|
1906 @param aMargin Offset of the text from the position within the rectangle, using the specified alignment. |
|
1907 |
|
1908 @panic DGDI 7, if the rendering context has not been activated. |
|
1909 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush style is neither ENullBrush |
|
1910 nor ESolidBrush. |
|
1911 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1912 */ |
|
1913 EXPORT_C void CDirectGdiContext::DrawTextVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TRect& aClipFillRect, TInt aBaselineOffset, |
|
1914 TBool aUp, DirectGdi::TTextAlign aVert, TInt aMargin) |
|
1915 { |
|
1916 GRAPHICS_TRACE("CDirectGdiContext::DrawTextVertical"); |
|
1917 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1918 // This next check covers both bitmap and open fonts |
|
1919 const CBitmapFont* bitmapFont = iFont.Address(); |
|
1920 GRAPHICS_ASSERT_ALWAYS(bitmapFont != 0, EDirectGdiPanicNoFontSelected); |
|
1921 DrawTextVertical(aText, aParam, NULL, &aClipFillRect, &aClipFillRect, aBaselineOffset, -1, aUp, aVert, aMargin); |
|
1922 } |
|
1923 |
|
1924 |
|
1925 /** |
|
1926 Draws text vertically, clipped to a specified rectangle, using a baseline offset, alignment and margin. |
|
1927 |
|
1928 @param aText The text string to be drawn. |
|
1929 @param aParam Parameters used in drawing text. |
|
1930 @param aClipFillRect The clipping rectangle (this rect will also be filled before text is plotted). |
|
1931 @param aBaselineOffset Number of pixels to offset the baseline by. |
|
1932 @param aTextWidth Number of pixels to clip the text to. |
|
1933 @param aUp ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1934 @param aVert Vertical alignment of the text relative to the specified rectangle. |
|
1935 @param aMargin Offset of the text from the position within the rectangle, using the specified alignment. |
|
1936 |
|
1937 @panic DGDI 7, if the rendering context has not been activated. |
|
1938 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush style is neither ENullBrush |
|
1939 nor ESolidBrush. |
|
1940 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1941 */ |
|
1942 EXPORT_C void CDirectGdiContext::DrawTextVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TRect& aClipFillRect, TInt aBaselineOffset, |
|
1943 TInt aTextWidth, TBool aUp, DirectGdi::TTextAlign aVert, TInt aMargin) |
|
1944 { |
|
1945 GRAPHICS_TRACE("CDirectGdiContext::DrawTextVertical"); |
|
1946 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
1947 // This next check covers both bitmap and open fonts |
|
1948 const CBitmapFont* bitmapFont = iFont.Address(); |
|
1949 GRAPHICS_ASSERT_ALWAYS(bitmapFont != 0, EDirectGdiPanicNoFontSelected); |
|
1950 DrawTextVertical(aText, aParam, NULL, &aClipFillRect, &aClipFillRect, aBaselineOffset, aTextWidth, aUp, aVert, aMargin); |
|
1951 } |
|
1952 |
|
1953 |
|
1954 /** |
|
1955 The private general DrawTextVertical() routine that implements all the others. |
|
1956 Two clipping rectangles received from different routines. The final rectangle will be calculated as intersection |
|
1957 of first and second clipping rectangle. If aClipRect2 is empty, the error state is set to KErrArgument. |
|
1958 |
|
1959 @param aText The text string to be drawn. |
|
1960 @param aParam Parameters used in drawing text. |
|
1961 @param aClipRect1 Pointer to first clipping rectangle. |
|
1962 @param aClipRect2 Pointer to second clipping rectangle. |
|
1963 @param aFillRect Pointer to rectangle to be filled before text plotting. |
|
1964 @param aBaselineOffset Number of pixels to offset the baseline by. |
|
1965 @param aTextWidth Number of pixels to clip the text to. If negative, the text will not be clipped |
|
1966 @param aUp ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
1967 @param aVert Vertical alignment of the text relative to the specified rectangle. |
|
1968 @param aMargin Offset of the text from the position within the rectangle, using the specified alignment. |
|
1969 |
|
1970 @panic DGDI 10, if the active font is an outline and/or shadow font and the brush style is neither ENullBrush |
|
1971 nor ESolidBrush. |
|
1972 @panic DGDI 11, if a font has not been set prior to calling DrawText(). |
|
1973 @panic DGDI 22, if aClipRect2 is NULL. |
|
1974 */ |
|
1975 void CDirectGdiContext::DrawTextVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, const TRect* aClipRect1, const TRect* aClipRect2, const TRect* aFillRect, |
|
1976 TInt aBaselineOffset, TInt aTextWidth, TBool aUp, DirectGdi::TTextAlign aVert, TInt aMargin) |
|
1977 { |
|
1978 GRAPHICS_ASSERT_ALWAYS(aClipRect2, EDirectGdiPanicBadParameter); |
|
1979 |
|
1980 TRect clipRect2 = *aClipRect2; |
|
1981 clipRect2.Move(iOrigin); |
|
1982 |
|
1983 TRect clipRect(clipRect2); |
|
1984 if (aClipRect1 != NULL) |
|
1985 { |
|
1986 if(aClipRect1->IsEmpty()) |
|
1987 { |
|
1988 iDriver.SetError(KErrArgument); |
|
1989 return; |
|
1990 } |
|
1991 TRect clipRect1 = *aClipRect1; |
|
1992 clipRect1.Move(iOrigin); |
|
1993 clipRect.Intersection(clipRect1); |
|
1994 } |
|
1995 |
|
1996 if ((aFillRect != NULL) && (iBrushStyle != ENullBrush)) |
|
1997 { |
|
1998 // fill the box if necessary |
|
1999 TRect fillBox = *aFillRect; |
|
2000 fillBox.Move(iOrigin); |
|
2001 if (fillBox.Intersects(clipRect)) |
|
2002 { |
|
2003 fillBox.Intersection(clipRect); |
|
2004 iEngine->SetPenStyle(DirectGdi::ENullPen); // Fill box, don't outline it |
|
2005 iEngine->DrawRect(*aFillRect); |
|
2006 iEngine->SetPenStyle(iPenStyle); // Put the pen style back |
|
2007 } |
|
2008 } |
|
2009 if (!aText.Length()) |
|
2010 { |
|
2011 return; |
|
2012 } |
|
2013 if (aClipRect2->IsEmpty()) |
|
2014 { |
|
2015 iDriver.SetError(KErrArgument); |
|
2016 return; |
|
2017 } |
|
2018 |
|
2019 const CBitmapFont* bitmapFont = iFont.Address(); |
|
2020 GRAPHICS_ASSERT_ALWAYS(bitmapFont != 0, EDirectGdiPanicNoFontSelected); |
|
2021 |
|
2022 CFont::TMeasureTextInput input; |
|
2023 //CFont::TMeasureTextOutput |
|
2024 if (aParam) |
|
2025 { |
|
2026 GRAPHICS_ASSERT_ALWAYS(aParam->iStart < aParam->iEnd ,EDirectGdiPanicBadParameter); |
|
2027 input.iStartInputChar = aParam->iStart; |
|
2028 input.iEndInputChar = Min(aText.Length(),aParam->iEnd); |
|
2029 } |
|
2030 TInt width = iFont.MeasureText(aText,&input); |
|
2031 TOpenFontMetrics metrics; |
|
2032 iFont.GetFontMetrics(metrics); |
|
2033 |
|
2034 if (aTextWidth < 0) |
|
2035 { |
|
2036 aTextWidth = width; |
|
2037 } |
|
2038 TPoint coords; |
|
2039 coords.iX = clipRect2.iTl.iX; |
|
2040 TInt directionalMultiplier = aUp ? -1 : 1; |
|
2041 coords.iY = aUp ? clipRect2.iBr.iY - 1 : clipRect2.iTl.iY; |
|
2042 // |
|
2043 // iX calculation, for example: ascent(a)=18 descent(d)=2 size=boxwidth=fontheight(h)=20 baseline=ascent |
|
2044 // pre: iX = 0 |
|
2045 // |
|
2046 // hhhhhhhhhhhhhhhhhhhh |
|
2047 // 01234567890123456789 |
|
2048 // aaaaaaaaaaaaaaaaaadd aUp=ETrue |
|
2049 // ^ |
|
2050 // iX = 18 (baseline) |
|
2051 // |
|
2052 // ddaaaaaaaaaaaaaaaaaa aUp=EFalse |
|
2053 // ^ |
|
2054 // iX = 1 (instead of 2 ie 20-18-1 which is boxwidth-baseline-1) |
|
2055 // |
|
2056 coords.iX += aUp ? aBaselineOffset : clipRect2.Width() - aBaselineOffset - 1; |
|
2057 switch (aVert) |
|
2058 { |
|
2059 case DirectGdi::ELeft: |
|
2060 coords.iY += aMargin * directionalMultiplier; |
|
2061 break; |
|
2062 case DirectGdi::ECenter: |
|
2063 coords.iY += (((clipRect2.iBr.iY - clipRect2.iTl.iY - aTextWidth) >> 1) + aMargin) * directionalMultiplier; |
|
2064 break; |
|
2065 case DirectGdi::ERight: |
|
2066 coords.iY += (clipRect2.iBr.iY - clipRect2.iTl.iY - aTextWidth - aMargin) * directionalMultiplier; |
|
2067 break; |
|
2068 default: |
|
2069 iDriver.SetError(KErrArgument); |
|
2070 return; |
|
2071 } |
|
2072 iLastPrintPosition = coords; |
|
2073 coords.iX += bitmapFont->iAlgStyle.iBaselineOffsetInPixels * directionalMultiplier; |
|
2074 TInt prewidth = width + iCharJustExcess + iWordJustExcess; |
|
2075 iLastPrintPosition.iY -= aUp ? prewidth - 1 : -prewidth; |
|
2076 if (clipRect.IsEmpty() || !width) |
|
2077 { |
|
2078 if (iAutoUpdateJustification) |
|
2079 { |
|
2080 UpdateJustificationVertical(aText, aParam, aUp); |
|
2081 } |
|
2082 return; |
|
2083 } |
|
2084 |
|
2085 /* |
|
2086 Set up the parameter block for character positioning. |
|
2087 Draw left to right, because although the text is being drawn vertically, |
|
2088 it is done by rotating the baseline 90 degrees and drawing in the ordinary way, not by drawing |
|
2089 the characters in their normal orientation but in a vertical column. |
|
2090 */ |
|
2091 CFont::TPositionParam param; |
|
2092 param.iText.Set(aText); |
|
2093 param.iPen = coords; |
|
2094 TInt endDraw = aText.Length(); |
|
2095 if (aParam) |
|
2096 { |
|
2097 param.iPosInText = aParam->iStart; |
|
2098 endDraw = Min(aText.Length(),aParam->iEnd); |
|
2099 } |
|
2100 else |
|
2101 { |
|
2102 param.iPosInText = 0; |
|
2103 } |
|
2104 |
|
2105 // Draw the text. |
|
2106 DoDrawTextVertical(param, aUp, endDraw, clipRect); |
|
2107 if(iAutoUpdateJustification) |
|
2108 { |
|
2109 UpdateJustificationVertical(aText, aParam, aUp); |
|
2110 } |
|
2111 } |
|
2112 |
|
2113 |
|
2114 /** |
|
2115 Draws vertical text within the clipping area |
|
2116 |
|
2117 @param aParam Defines glyph code, ligature creation and diacritic placement |
|
2118 @param aUp ETrue, text is rotated 90 degrees anti-clockwise; EFalse, text is rotated 90 degrees clockwise. |
|
2119 @param aEnd The end position within the text descriptor to draw. |
|
2120 @param aClipRect The clipping rectangle. |
|
2121 |
|
2122 @pre iFont is a valid CFont. |
|
2123 |
|
2124 @panic DGDI 13, if the active font is an outline and/or shadow font and the brush style is neither ENullBrush |
|
2125 nor ESolidBrush. |
|
2126 */ |
|
2127 void CDirectGdiContext::DoDrawTextVertical(CFont::TPositionParam& aParam, TBool aUp, const TInt aEnd, TRect& aClipRect) |
|
2128 { |
|
2129 const CBitmapFont* bitmapFont = iFont.Address(); |
|
2130 if ((bitmapFont->GlyphBitmapType() == EFourColourBlendGlyphBitmap) && !((iBrushStyle == DirectGdi::ENullBrush) || (iBrushStyle == DirectGdi::ESolidBrush))) |
|
2131 { |
|
2132 //For future compatibility it is better if brush style of ENullBrush or ESolidBrush is used |
|
2133 //when drawing outline and shadow fonts. |
|
2134 GRAPHICS_PANIC_ALWAYS(EDirectGdiPanicInvalidBrushStyle); |
|
2135 } |
|
2136 |
|
2137 TPoint startPen = aParam.iPen; |
|
2138 TInt charClipping = aClipRect.iTl.iY; |
|
2139 TInt underlineTop = 0; |
|
2140 TInt underlineBottom = 0; |
|
2141 |
|
2142 //for linked fonts need an adjustment to the underline postion |
|
2143 TInt underlineStrikeoutOffset = BaselineCorrection(); |
|
2144 |
|
2145 if (iUnderline == DirectGdi::EUnderlineOn) |
|
2146 { |
|
2147 GetUnderlineMetrics(underlineTop, underlineBottom); |
|
2148 underlineTop+=underlineStrikeoutOffset; |
|
2149 underlineBottom+=underlineStrikeoutOffset; |
|
2150 } |
|
2151 TInt strikeTop = 0; |
|
2152 TInt strikeBottom = 0; |
|
2153 if (iStrikethrough == DirectGdi::EStrikethroughOn) |
|
2154 { |
|
2155 GetStrikethroughMetrics(strikeTop, strikeBottom); |
|
2156 strikeTop+=underlineStrikeoutOffset; |
|
2157 strikeBottom+=underlineStrikeoutOffset; |
|
2158 } |
|
2159 |
|
2160 const DirectGdi::TGraphicsRotation rotation = aUp ? DirectGdi::EGraphicsRotation270 : DirectGdi::EGraphicsRotation90; |
|
2161 iEngine->BeginDrawGlyph(); |
|
2162 RShapeInfo shapeInfo; |
|
2163 while (aParam.iPosInText < aEnd) |
|
2164 { |
|
2165 TPoint startPen2 = aParam.iPen; |
|
2166 if (!iFont.GetCharacterPosition2(aParam, shapeInfo)) |
|
2167 { |
|
2168 continue; |
|
2169 } |
|
2170 Rotate(aParam.iPen, startPen2, aUp); |
|
2171 TInt adjustment = 0; |
|
2172 if(iCharJustExcess && (iCharJustNum > 0)) // character clipping/justification |
|
2173 { |
|
2174 adjustment = CGraphicsContext::JustificationInPixels(iCharJustExcess, iCharJustNum); |
|
2175 if (adjustment < 0) |
|
2176 { |
|
2177 aClipRect.iTl.iY = aParam.iPen.iY + (aUp ? -adjustment : adjustment); |
|
2178 } |
|
2179 } |
|
2180 |
|
2181 CFont::TPositionParam::TOutput* output = aParam.iOutput; |
|
2182 for (TInt i = 0; i < aParam.iOutputGlyphs; i++, output++) |
|
2183 { |
|
2184 Rotate(output->iBounds.iTl, startPen2, aUp); |
|
2185 |
|
2186 //get the character metrics for the glyph type |
|
2187 TOpenFontCharMetrics characterParams; |
|
2188 const TUint8* bitmap; |
|
2189 TSize size; |
|
2190 //note may now be using a glyph code, and not a character |
|
2191 iFont.GetCharacterData(aParam.iOutput[i].iCode,characterParams,bitmap,size); |
|
2192 TGlyphBitmapType glyphType = characterParams.GlyphType(); |
|
2193 |
|
2194 switch (glyphType) |
|
2195 { |
|
2196 case EAntiAliasedGlyphBitmap: |
|
2197 case EFourColourBlendGlyphBitmap: |
|
2198 case EDefaultGlyphBitmap: |
|
2199 iEngine->DrawGlyph(output->iBounds.iTl, output->iCode, output->iBitmap, glyphType, output->iBitmapSize, aClipRect, rotation); |
|
2200 break; |
|
2201 |
|
2202 default: |
|
2203 //if the outline or shadow is not specified for the character, then use the font setting |
|
2204 iEngine->DrawGlyph(output->iBounds.iTl, output->iCode, output->iBitmap, bitmapFont->GlyphBitmapType(), output->iBitmapSize, aClipRect, rotation); |
|
2205 break; |
|
2206 } |
|
2207 } |
|
2208 |
|
2209 aClipRect.iTl.iY = charClipping; |
|
2210 if (adjustment) |
|
2211 { |
|
2212 aParam.iPen.iY += aUp ? -adjustment : adjustment; |
|
2213 } |
|
2214 if ((iWordJustExcess > 0) && (iWordJustNum > 0) && (aParam.iOutput[0].iCode == 0x0020)) // word justification |
|
2215 { |
|
2216 adjustment = CGraphicsContext::JustificationInPixels(iWordJustExcess, iWordJustNum); |
|
2217 aParam.iPen.iY += aUp ? -adjustment : adjustment; |
|
2218 } |
|
2219 } |
|
2220 iEngine->EndDrawGlyph(); |
|
2221 if (shapeInfo.IsOpen()) |
|
2222 { |
|
2223 shapeInfo.Close(); |
|
2224 } |
|
2225 |
|
2226 if (iUnderline == DirectGdi::EUnderlineOn) |
|
2227 { |
|
2228 TRect underlineRect; // underline |
|
2229 if (aUp) |
|
2230 { |
|
2231 underlineRect.SetRect(startPen.iX + underlineTop, aParam.iPen.iY, startPen.iX + underlineBottom, startPen.iY + 1); |
|
2232 underlineRect.iTl.iY = underlineRect.iBr.iY - underlineRect.Height(); |
|
2233 } |
|
2234 else |
|
2235 { |
|
2236 underlineRect.SetRect(startPen.iX - underlineBottom, startPen.iY, startPen.iX - underlineTop, aParam.iPen.iY); |
|
2237 underlineRect.iBr.iY = underlineRect.iTl.iY + underlineRect.Height(); |
|
2238 underlineRect.iTl.iX++; // adjust for rect not including last line |
|
2239 underlineRect.iBr.iX++; |
|
2240 } |
|
2241 FillRect(underlineRect, iPenColor, aClipRect); |
|
2242 } |
|
2243 |
|
2244 if (iStrikethrough == DirectGdi::EStrikethroughOn) |
|
2245 { |
|
2246 TRect strikethroughRect; // strikethrough |
|
2247 if (aUp) |
|
2248 { |
|
2249 strikethroughRect.SetRect(startPen.iX + strikeTop, aParam.iPen.iY, startPen.iX + strikeBottom, startPen.iY + 1); |
|
2250 strikethroughRect.iTl.iY = strikethroughRect.iBr.iY - strikethroughRect.Height(); |
|
2251 } |
|
2252 else |
|
2253 { |
|
2254 strikethroughRect.SetRect(startPen.iX - strikeBottom, startPen.iY, startPen.iX - strikeTop, aParam.iPen.iY); |
|
2255 strikethroughRect.iBr.iY = strikethroughRect.iTl.iY + strikethroughRect.Height(); |
|
2256 strikethroughRect.iTl.iX++; |
|
2257 strikethroughRect.iBr.iX++; |
|
2258 } |
|
2259 FillRect(strikethroughRect, iPenColor, aClipRect); |
|
2260 } |
|
2261 } |
|
2262 |
|
2263 |
|
2264 /** |
|
2265 Transform a vector, defined by a point relative to an origin, from left-to-right to up or down. |
|
2266 |
|
2267 @param aPoint A point relative to the origin aOrigin. |
|
2268 @param aOrigin The origin to use when transforming the point aPoint. |
|
2269 @param aUp If ETrue, then transform the point from left-right to up, otherwise transform from |
|
2270 left-right to down. |
|
2271 */ |
|
2272 void CDirectGdiContext::Rotate(TPoint& aPoint, const TPoint& aOrigin, TBool aUp) |
|
2273 { |
|
2274 TInt dx = aPoint.iX - aOrigin.iX; |
|
2275 TInt dy = aPoint.iY - aOrigin.iY; |
|
2276 if (aUp) |
|
2277 { |
|
2278 aPoint.iX = aOrigin.iX + dy; |
|
2279 aPoint.iY = aOrigin.iY - dx; |
|
2280 } |
|
2281 else |
|
2282 { |
|
2283 aPoint.iX = aOrigin.iX - dy; |
|
2284 aPoint.iY = aOrigin.iY + dx; |
|
2285 } |
|
2286 } |
|
2287 |
|
2288 |
|
2289 /** |
|
2290 Can be used to find out the top and bottom of an underline for the active font. |
|
2291 This allows correct calculation of the area required in which to draw text with underline. |
|
2292 |
|
2293 @param aTop The top of the underline position. |
|
2294 @param aBottom The bottom of the underline position. |
|
2295 */ |
|
2296 void CDirectGdiContext::GetUnderlineMetrics(TInt& aTop, TInt& aBottom) |
|
2297 { |
|
2298 const TInt width = Max((iFont.HeightInPixels() / 10), 1); |
|
2299 aTop = 1 + (width >> 1); |
|
2300 aBottom = aTop + width; |
|
2301 } |
|
2302 |
|
2303 |
|
2304 /** |
|
2305 Get the top and bottom of a strikethrough line for the current font, relative to the baseline. |
|
2306 |
|
2307 @param aTop The top of the strikethrough position. |
|
2308 @param aBottom The bottom of the strikethrough position. |
|
2309 */ |
|
2310 void CDirectGdiContext::GetStrikethroughMetrics(TInt& aTop, TInt& aBottom) |
|
2311 { |
|
2312 aTop = -(iFont.AscentInPixels() * 5/12) - 1; |
|
2313 aBottom = aTop + Max((iFont.HeightInPixels() / 10), 1); |
|
2314 } |
|
2315 |
|
2316 |
|
2317 /** |
|
2318 Moves the internal drawing position relative to the co-ordinate origin, without drawing a line. |
|
2319 A subsequent call to DrawLineTo() or DrawLineBy() will then use the new internal drawing position |
|
2320 as the start point for the line drawn. |
|
2321 |
|
2322 The operations DrawLine(), DrawLineTo(), DrawLineBy() and DrawPolyline() also change the internal drawing |
|
2323 position to the last point of the drawn line(s). The internal drawing position is set to the co-ordinate |
|
2324 origin if no drawing or moving operations have yet taken place. |
|
2325 |
|
2326 @see CDirectGdiContext::MoveBy(const TPoint&) |
|
2327 |
|
2328 @param aPoint The point to move the internal drawing position to. |
|
2329 |
|
2330 @pre The rendering target has been activated. |
|
2331 @post Request to move the internal drawing position to the specified point has been accepted. |
|
2332 There is no guarantee that the request has been processed when the method returns. |
|
2333 |
|
2334 @panic DGDI 7, if the rendering context has not been activated. |
|
2335 */ |
|
2336 EXPORT_C void CDirectGdiContext::MoveTo(const TPoint& aPoint) |
|
2337 { |
|
2338 GRAPHICS_TRACE2("CDirectGdiContext::MoveTo(%d,%d)", aPoint.iX, aPoint.iY); |
|
2339 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
2340 iEngine->MoveTo(aPoint); |
|
2341 } |
|
2342 |
|
2343 |
|
2344 /** |
|
2345 Moves the internal drawing position by a vector, relative to the current position, without drawing a line. |
|
2346 A subsequent call to DrawLineTo() or DrawLineBy() will then use the new internal drawing position |
|
2347 as the start point for the line drawn. |
|
2348 |
|
2349 The operations DrawLine(), DrawLineTo(), DrawLineBy() and DrawPolyline() also change the internal drawing |
|
2350 position to the last point of the drawn line(s). The internal drawing position is set to the co-ordinate |
|
2351 origin if no drawing or moving operations have yet taken place. |
|
2352 |
|
2353 @see CDirectGdiContext::MoveTo(const TPoint&) |
|
2354 |
|
2355 @param aVector The vector to move the internal position by. |
|
2356 |
|
2357 @pre The rendering target has been activated. |
|
2358 @post Request to move the internal drawing position by a vector has been accepted. |
|
2359 There is no guarantee that the request has been processed when the method returns. |
|
2360 @panic DGDI 7, if the rendering context has not been activated. |
|
2361 */ |
|
2362 EXPORT_C void CDirectGdiContext::MoveBy(const TPoint& aVector) |
|
2363 { |
|
2364 GRAPHICS_TRACE2("CDirectGdiContext::MoveBy(%d,%d)", aVector.iX, aVector.iY); |
|
2365 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
2366 if (aVector != TPoint(0,0)) |
|
2367 { |
|
2368 iEngine->MoveBy(aVector); |
|
2369 } |
|
2370 } |
|
2371 |
|
2372 |
|
2373 /** |
|
2374 Draws a point at given location using current pen colour and size. |
|
2375 If the pen size is greater than 1x1 pixel, a filled circle/ellipse with current pen |
|
2376 colour should be drawn with the given position as the centre. |
|
2377 |
|
2378 @param aPoint The position to plot. |
|
2379 |
|
2380 @pre The rendering target has been activated. |
|
2381 @post Request to draw a point or filled circle/ellipse has been accepted. |
|
2382 There is no guarantee that the request has been processed when the method returns. |
|
2383 |
|
2384 @panic DGDI 7, if the rendering context has not been activated. |
|
2385 |
|
2386 @see CDirectGdiContext::SetPenSize(const TSize&) |
|
2387 @see CDirectGdiContext::SetPenColor(TRgb) |
|
2388 @see CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode) |
|
2389 */ |
|
2390 EXPORT_C void CDirectGdiContext::Plot(const TPoint& aPoint) |
|
2391 { |
|
2392 GRAPHICS_TRACE2("CDirectGdiContext::Plot(%d,%d)", aPoint.iX, aPoint.iY); |
|
2393 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
2394 if (iPenStyle == DirectGdi::ENullPen || iPenSize.iWidth == 0 || iPenSize.iHeight == 0) |
|
2395 { |
|
2396 return; |
|
2397 } |
|
2398 iEngine->Plot(aPoint); |
|
2399 } |
|
2400 |
|
2401 |
|
2402 /** |
|
2403 Resets drawing state to its default settings. This operation does not unbind the current target. |
|
2404 @pre None. |
|
2405 @post The drawing state is reset to default values. Subsequent drawing will use the default settings until they are changed to different values. |
|
2406 */ |
|
2407 EXPORT_C void CDirectGdiContext::Reset() |
|
2408 { |
|
2409 GRAPHICS_TRACE("CDirectGdiContext::Reset"); |
|
2410 iEngine->Reset(); |
|
2411 |
|
2412 // Explicit calls are made to the engine to apply the defaults. |
|
2413 // Set() methods should generally not be used as they perform unnecessary checks, and may also |
|
2414 // block the call to the engine if the value being set is the same as the constructor's default. |
|
2415 // Clipping regions. |
|
2416 iClippingRegion.Clear(); |
|
2417 iEngine->ResetClippingRegion(); |
|
2418 // Origin. |
|
2419 iOrigin.SetXY(0,0); |
|
2420 iEngine->SetOrigin(iOrigin); |
|
2421 // Font. |
|
2422 iEngine->ResetFont(); |
|
2423 iFont.Reset(); |
|
2424 // Text. |
|
2425 iLastPrintPosition.SetXY(0,0); |
|
2426 iAutoUpdateJustification = ETrue; |
|
2427 SetCharJustification(0, 0); |
|
2428 SetWordJustification(0, 0); |
|
2429 SetStrikethroughStyle(DirectGdi::EStrikethroughOff); |
|
2430 SetUnderlineStyle(DirectGdi::EUnderlineOff); |
|
2431 // Pen colour. |
|
2432 iPenColor = KRgbBlack; |
|
2433 iEngine->SetPenColor(iPenColor); |
|
2434 // Pen size. |
|
2435 iPenSize = TSize(1,1); |
|
2436 iEngine->SetPenSize(iPenSize); |
|
2437 // Pen style. |
|
2438 iPenStyle = DirectGdi::ESolidPen; |
|
2439 iEngine->SetPenStyle(iPenStyle); |
|
2440 // Draw mode. |
|
2441 iDrawMode = DirectGdi::EDrawModePEN; |
|
2442 iEngine->SetDrawMode(iDrawMode); |
|
2443 // Text shadow colour. |
|
2444 iTextShadowColor = KRgbGray; |
|
2445 iEngine->SetTextShadowColor(iTextShadowColor); |
|
2446 // Brush colour. |
|
2447 iBrushColor = KRgbWhite; |
|
2448 iEngine->SetBrushColor(iBrushColor); |
|
2449 // Brush style. |
|
2450 iBrushStyle = DirectGdi::ENullBrush; |
|
2451 iEngine->SetBrushStyle(iBrushStyle); |
|
2452 // Brush pattern. |
|
2453 CleanUpBrushPattern(); |
|
2454 iEngine->ResetBrushPattern(); |
|
2455 iBrushPatternUsed = EFalse; |
|
2456 // Brush origin. |
|
2457 iBrushOrigin.SetXY(0,0); |
|
2458 iEngine->SetBrushOrigin(iBrushOrigin); |
|
2459 // Internal drawing position. |
|
2460 iEngine->MoveTo(TPoint(0,0)); |
|
2461 } |
|
2462 |
|
2463 |
|
2464 /** |
|
2465 Sets the colour for clearing, filling the area of shapes and the background of text boxes. |
|
2466 |
|
2467 The default brush colour is white. However, the default brush style is ENullBrush, so when drawing |
|
2468 to a target the default appears to be the target's background colour. |
|
2469 |
|
2470 @see CDirectGdiContext::Clear() |
|
2471 @see CDirectGdiContext::Clear(const TRect&) |
|
2472 @see CDirectGdiContext::DrawRect() |
|
2473 @see CDirectGdiContext::DrawRoundRect() |
|
2474 @see CDirectGdiContext::DrawPolygon() |
|
2475 @see CDirectGdiContext::DrawPie() |
|
2476 |
|
2477 @param aColor Brush colour. |
|
2478 |
|
2479 @pre None. |
|
2480 @post The new brush colour will be used on subsequent drawing operations if a brush style making |
|
2481 use of the brush colour is used. The new brush colour remains in effect until another SetBrushColor() |
|
2482 with a different parameter is called. |
|
2483 */ |
|
2484 EXPORT_C void CDirectGdiContext::SetBrushColor(const TRgb& aColor) |
|
2485 { |
|
2486 GRAPHICS_TRACE1("CDirectGdiContext::SetBrushColor(%d)", aColor.Internal()); |
|
2487 if (aColor != iBrushColor) |
|
2488 { |
|
2489 iBrushColor = aColor; |
|
2490 iEngine->SetBrushColor(iBrushColor); |
|
2491 } |
|
2492 } |
|
2493 |
|
2494 |
|
2495 /** |
|
2496 Sets the brush pattern origin which specifies the start of a pattern tile. |
|
2497 Shapes can be considered as a view port into a continuous pattern tile covering the entire |
|
2498 area of rendering target. The default origin is TPoint(0,0). |
|
2499 |
|
2500 @see CDirectGdiContext::SetBrushPattern() |
|
2501 |
|
2502 @param aOrigin An origin point for the brush. The coordinates are relative |
|
2503 to the rectangle to fill, i.e. specify TPoint(0,0) to align the pattern flush with |
|
2504 the top and left hand sides of the rectangle. |
|
2505 |
|
2506 @pre None. |
|
2507 @post New brush origin will be used when filling an area with a pattern is used on |
|
2508 subsequent drawing operations. It remains in effect until another SetBrushOrigin() |
|
2509 with a different parameter is called. |
|
2510 */ |
|
2511 EXPORT_C void CDirectGdiContext::SetBrushOrigin(const TPoint& aOrigin) |
|
2512 { |
|
2513 GRAPHICS_TRACE2("CDirectGdiContext::SetBrushOrigin(%d,%d)", aOrigin.iX, aOrigin.iY); |
|
2514 if (aOrigin != iBrushOrigin) |
|
2515 { |
|
2516 iBrushOrigin = aOrigin; |
|
2517 iEngine->SetBrushOrigin(iBrushOrigin); |
|
2518 } |
|
2519 } |
|
2520 |
|
2521 |
|
2522 /** |
|
2523 Sets the brush style used when filling the area of shapes and the background of text boxes. |
|
2524 Use ENullBrush to draw the outline of a fillable shape on its own, without filling. |
|
2525 |
|
2526 The error state is set to KErrArgument if aBrushStyle is an invalid brush style. |
|
2527 |
|
2528 @see DirectGdi::TBrushStyle |
|
2529 |
|
2530 @param aBrushStyle The brush style to set. |
|
2531 |
|
2532 @pre If aBrushStyle is EPatternedBrush, a pattern must have been set first using SetBrushPattern(). |
|
2533 @post New brush style will be used for subsequent drawing operations, and remains in effect |
|
2534 until another SetBrushStyle() with a different parameter is called. |
|
2535 @panic DGDI 9, if aBrushStyle is EPatternedBrush but no brush pattern has successfully been set. |
|
2536 */ |
|
2537 EXPORT_C void CDirectGdiContext::SetBrushStyle(DirectGdi::TBrushStyle aBrushStyle) |
|
2538 { |
|
2539 GRAPHICS_TRACE1("CDirectGdiContext::SetBrushStyle(%d)", aBrushStyle); |
|
2540 if (aBrushStyle < DirectGdi::ENullBrush || aBrushStyle > DirectGdi::EDiamondCrossHatchBrush) |
|
2541 { |
|
2542 iDriver.SetError(KErrArgument); |
|
2543 return; |
|
2544 } |
|
2545 |
|
2546 if (aBrushStyle != iBrushStyle) |
|
2547 { |
|
2548 GRAPHICS_ASSERT_ALWAYS(aBrushStyle != DirectGdi::EPatternedBrush || iBrushPatternUsed, EDirectGdiPanicBrushPatternNotSet); |
|
2549 iBrushStyle = aBrushStyle; |
|
2550 iEngine->SetBrushStyle(iBrushStyle); |
|
2551 } |
|
2552 } |
|
2553 |
|
2554 |
|
2555 /** |
|
2556 Sets a clipping region which will be used to clip subsequent rendering operations on the current target. |
|
2557 This operation is non-additive, any previous clipping region setting is replaced by the new one. A clipping |
|
2558 region can contain one or more rectangles and is specified in absolute values in the target coordinate system. |
|
2559 By default (when a target is activated for the first time) no clipping region is set and any drawing |
|
2560 operations will be clipped automatically to the full area of the rendering target. |
|
2561 |
|
2562 In the event of a failure, the error state is set to KErrArgument if the given region is invalid or not |
|
2563 fully contained within the area of target, otherwise one of the system-wide error codes. |
|
2564 |
|
2565 @see CDirectGdiContext::ResetClippingRegion() |
|
2566 |
|
2567 @param aRegion The new clipping region. |
|
2568 |
|
2569 @pre Region is not empty and is fully contained within the full area of the target. |
|
2570 @post Subsequent rendering operations will be clipped to the given region if there is no error |
|
2571 while performing the operation, otherwise previous clipping region settings will be retained. |
|
2572 */ |
|
2573 EXPORT_C void CDirectGdiContext::SetClippingRegion(const TRegion& aRegion) |
|
2574 { |
|
2575 GRAPHICS_TRACE("CDirectGdiContext::SetClippingRegion"); |
|
2576 if (aRegion.CheckError()) |
|
2577 { |
|
2578 iDriver.SetError(KErrArgument); |
|
2579 return; |
|
2580 } |
|
2581 iClippingRegion.Copy(aRegion); |
|
2582 if (iClippingRegion.CheckError()) |
|
2583 { |
|
2584 iDriver.SetError(KErrNoMemory); |
|
2585 return; |
|
2586 } |
|
2587 iEngine->SetClippingRegion(iClippingRegion); |
|
2588 } |
|
2589 |
|
2590 |
|
2591 /** |
|
2592 Sets the drawing mode which will affect the way pen and brush colour are used in rendering operations. |
|
2593 The default drawing mode is EDrawModePEN. |
|
2594 |
|
2595 The error state is set to KErrArgument if aDrawMode is an invalid draw mode. |
|
2596 |
|
2597 @see DirectGdi::TDrawMode |
|
2598 |
|
2599 @param aDrawMode The drawing mode. |
|
2600 |
|
2601 @pre None. |
|
2602 @post The new drawing mode will be applied to subsequent rendering operations, and remains in effect |
|
2603 until another SetDrawMode() with a different parameter is called. |
|
2604 */ |
|
2605 EXPORT_C void CDirectGdiContext::SetDrawMode(DirectGdi::TDrawMode aDrawMode) |
|
2606 { |
|
2607 GRAPHICS_TRACE1("CDirectGdiContext::SetDrawMode(%d)", aDrawMode); |
|
2608 if (aDrawMode != DirectGdi::EDrawModePEN && aDrawMode != DirectGdi::EDrawModeWriteAlpha) |
|
2609 { |
|
2610 iDriver.SetError(KErrArgument); |
|
2611 return; |
|
2612 } |
|
2613 |
|
2614 if (iDrawMode != aDrawMode) |
|
2615 { |
|
2616 iDrawMode = aDrawMode; |
|
2617 iEngine->SetDrawMode(iDrawMode); |
|
2618 } |
|
2619 } |
|
2620 |
|
2621 |
|
2622 /** |
|
2623 Sets the origin of the drawing engine coordinate system. By default this is TPoint(0,0) and |
|
2624 coincides with the origin of the target coordinate system which is at the top-left corner of |
|
2625 the full area of target. The X value increases from left to right, and Y value increases from |
|
2626 top to bottom. Integer values are used to represent the position within the coordinate system. |
|
2627 |
|
2628 All drawing operations are done relative to the engine’s origin. However, the clipping region |
|
2629 is always specified in absolute coordinate values (using the target coordinate system) and is |
|
2630 not affected by changes to the drawing engine’s coordinate system origin. |
|
2631 |
|
2632 @param aPoint The new origin for the drawing engine’s coordinate system. |
|
2633 |
|
2634 @pre None. |
|
2635 @post The origin of the drawing engine’s coordinate system is moved to the given position. |
|
2636 All subsequent drawing operations will be done relative to the new origin. The new origin remains |
|
2637 in effect until SetOrigin() is called again with a different parameter. |
|
2638 */ |
|
2639 EXPORT_C void CDirectGdiContext::SetOrigin(const TPoint& aPoint) |
|
2640 { |
|
2641 GRAPHICS_TRACE2("CDirectGdiContext::SetOrigin(%d,%d)", aPoint.iX, aPoint.iY); |
|
2642 if (aPoint != iOrigin) |
|
2643 { |
|
2644 iOrigin = aPoint; |
|
2645 iEngine->SetOrigin(iOrigin); |
|
2646 } |
|
2647 } |
|
2648 |
|
2649 |
|
2650 /** |
|
2651 Sets the colour that will be used for drawing lines, outlines of filled shapes and text. The |
|
2652 default pen colour is black. For outline and shadow fonts the alpha value of the pen colour will be |
|
2653 used for blending the font to the destination. |
|
2654 |
|
2655 @see CDirectGdiContext::Plot() |
|
2656 @see CDirectGdiContext::DrawLine() |
|
2657 @see CDirectGdiContext::DrawRoundRect() |
|
2658 @see CDirectGdiContext::DrawRect() |
|
2659 @see CDirectGdiContext::DrawPolyLine() |
|
2660 @see CDirectGdiContext::DrawPolyLineNoEndPoint() |
|
2661 @see CDirectGdiContext::DrawPolygon() |
|
2662 @see CDirectGdiContext::DrawPie() |
|
2663 @see CDirectGdiContext::DrawArc() |
|
2664 @see CDirectGdiContext::DrawText() |
|
2665 |
|
2666 @param aColor The pen colour. |
|
2667 |
|
2668 @pre None. |
|
2669 @post The new pen colour will be used for subsequent drawing of lines, outlines of filled shapes and text. |
|
2670 The new pen colour remains in effect until another SetPenColor() with a different parameter is called. |
|
2671 */ |
|
2672 EXPORT_C void CDirectGdiContext::SetPenColor(const TRgb& aColor) |
|
2673 { |
|
2674 GRAPHICS_TRACE1("CDirectGdiContext::SetPenColor(%d)", aColor.Internal()); |
|
2675 if (aColor != iPenColor) |
|
2676 { |
|
2677 iPenColor = aColor; |
|
2678 iEngine->SetPenColor(iPenColor); |
|
2679 } |
|
2680 } |
|
2681 |
|
2682 |
|
2683 /** |
|
2684 Sets the pen or line drawing style. |
|
2685 |
|
2686 The pen style is used to draw lines and outlines of shapes. ENullPen can be used if border or |
|
2687 outlines are not required (when drawing a filled shape). The default pen style is ESolidPen. |
|
2688 |
|
2689 The error state is set to KErrArgument if aPenStyle is an invalid pen style. |
|
2690 |
|
2691 @see CDirectGdiContext::Plot() |
|
2692 @see CDirectGdiContext::DrawLine() |
|
2693 @see CDirectGdiContext::DrawRoundRect() |
|
2694 @see CDirectGdiContext::DrawRect() |
|
2695 @see CDirectGdiContext::DrawPolyLine() |
|
2696 @see CDirectGdiContext::DrawPolyLineNoEndPoint() |
|
2697 @see CDirectGdiContext::DrawPolygon() |
|
2698 @see CDirectGdiContext::DrawPie() |
|
2699 @see CDirectGdiContext::DrawArc() |
|
2700 @see DirectGdi::TPenStyle |
|
2701 |
|
2702 @param aPenStyle The pen style. |
|
2703 |
|
2704 @pre None. |
|
2705 @post The new pen style will be applied for subsequent drawing lines and outlines of filled shapes. |
|
2706 The new pen style remains in effect until another SetPenStyle() with a different parameter is called. |
|
2707 */ |
|
2708 EXPORT_C void CDirectGdiContext::SetPenStyle(DirectGdi::TPenStyle aPenStyle) |
|
2709 { |
|
2710 GRAPHICS_TRACE1("CDirectGdiContext::SetPenStyle(%d)", aPenStyle); |
|
2711 if (aPenStyle < DirectGdi::ENullPen || aPenStyle > DirectGdi::EDotDotDashPen) |
|
2712 { |
|
2713 iDriver.SetError(KErrArgument); |
|
2714 return; |
|
2715 } |
|
2716 |
|
2717 if (aPenStyle != iPenStyle) |
|
2718 { |
|
2719 iPenStyle = aPenStyle; |
|
2720 iEngine->SetPenStyle(iPenStyle); |
|
2721 } |
|
2722 } |
|
2723 |
|
2724 |
|
2725 /** |
|
2726 Sets the pen size for drawing lines or the outlines of a filled shape. The default pen size is 1. |
|
2727 Lines with pen size greater than 1 are drawn with rounded ends that extend beyond the end points |
|
2728 and are always drawn using EDrawModePEN for compatibility reasons. |
|
2729 |
|
2730 The error state is set to KErrArgument if the specified width or height is negative. |
|
2731 |
|
2732 @see CDirectGdiContext::Plot() |
|
2733 @see CDirectGdiContext::DrawLine() |
|
2734 @see CDirectGdiContext::DrawRoundRect() |
|
2735 @see CDirectGdiContext::DrawRect() |
|
2736 @see CDirectGdiContext::DrawPolyLine() |
|
2737 @see CDirectGdiContext::DrawPolyLineNoEndPoint() |
|
2738 @see CDirectGdiContext::DrawPolygon() |
|
2739 @see CDirectGdiContext::DrawPie() |
|
2740 @see CDirectGdiContext::DrawArc() |
|
2741 |
|
2742 @param aSize The pen size. |
|
2743 |
|
2744 @pre None. |
|
2745 @post The new pen size is used for subsequent drawing lines and outlines of filled shapes. The new |
|
2746 pen size remains in effect until another SetPenSize() with a different parameter is called. |
|
2747 */ |
|
2748 EXPORT_C void CDirectGdiContext::SetPenSize(const TSize& aSize) |
|
2749 { |
|
2750 GRAPHICS_TRACE2("CDirectGdiContext::SetPenSize(%d,%d)", aSize.iWidth, aSize.iHeight); |
|
2751 if ((aSize.iWidth < 0) || (aSize.iHeight < 0)) |
|
2752 { |
|
2753 iDriver.SetError(KErrArgument); |
|
2754 return; |
|
2755 } |
|
2756 |
|
2757 if (aSize != iPenSize) |
|
2758 { |
|
2759 iPenSize = aSize; |
|
2760 iEngine->SetPenSize(iPenSize); |
|
2761 } |
|
2762 } |
|
2763 |
|
2764 |
|
2765 /** |
|
2766 Sets the colour that will be used for drawing the shadow for shadowed text. |
|
2767 |
|
2768 @param aColor The shadow colour. |
|
2769 |
|
2770 @pre None. |
|
2771 @post The new colour will be used for subsequent drawing of text which has a type EFourColourBlendGlyphBitmap. |
|
2772 The shadow component of the text will be filled with this colour. |
|
2773 The new pen colour remains in effect until another SetTextShadowColor() with a different parameter is called. |
|
2774 */ |
|
2775 EXPORT_C void CDirectGdiContext::SetTextShadowColor(const TRgb& aColor) |
|
2776 { |
|
2777 GRAPHICS_TRACE1("CDirectGdiContext::SetTextShadowColor(%d)", aColor.Internal()); |
|
2778 if (aColor != iTextShadowColor) |
|
2779 { |
|
2780 iTextShadowColor = aColor; |
|
2781 iEngine->SetTextShadowColor(aColor); |
|
2782 } |
|
2783 } |
|
2784 |
|
2785 |
|
2786 /** |
|
2787 Sets the character justification. |
|
2788 The function provides a concrete implementation of the pure virtual function CGraphicsContext::SetCharJustification(). |
|
2789 The function behaviour is the same as documented (in detail) in that class. |
|
2790 |
|
2791 @param aExcessWidth The excess width (in pixels) to be distributed between the specified number of characters. |
|
2792 @param aNumChars The number of characters involved. |
|
2793 |
|
2794 @see CGraphicsContext::SetCharJustification() |
|
2795 */ |
|
2796 EXPORT_C void CDirectGdiContext::SetCharJustification(TInt aExcessWidth, TInt aNumChars) |
|
2797 { |
|
2798 GRAPHICS_TRACE2("CDirectGdiContext::SetCharJustification(%d,%d)", aExcessWidth, aNumChars); |
|
2799 if (aExcessWidth == 0 || aNumChars <= 0) |
|
2800 { |
|
2801 iCharJustExcess = 0; |
|
2802 iCharJustNum = 0; |
|
2803 } |
|
2804 else |
|
2805 { |
|
2806 iCharJustExcess = aExcessWidth; |
|
2807 iCharJustNum = aNumChars; |
|
2808 } |
|
2809 } |
|
2810 |
|
2811 |
|
2812 /** |
|
2813 Sets the word justification. |
|
2814 The function provides a concrete implementation of the pure virtual function CGraphicsContext::SetWordJustification(). |
|
2815 The function behaviour is the same as documented (in detail) in that class. |
|
2816 |
|
2817 @param aExcessWidth The width (in pixels) to be distributed between the specified number of spaces. |
|
2818 It may be positive, in which case the text is stretched, or negative, in which case it is shrunk. |
|
2819 @param aNumGaps The number of word spaces (characters with the code U+0020) over which the change in width is distributed. |
|
2820 |
|
2821 @see CGraphicsContext::SetWordJustification() |
|
2822 */ |
|
2823 EXPORT_C void CDirectGdiContext::SetWordJustification(TInt aExcessWidth, TInt aNumGaps) |
|
2824 { |
|
2825 GRAPHICS_TRACE2("CDirectGdiContext::SetWordJustification(%d,%d)", aExcessWidth, aNumGaps); |
|
2826 if (aExcessWidth <= 0 || aNumGaps <= 0) |
|
2827 { |
|
2828 iWordJustExcess = 0; |
|
2829 iWordJustNum = 0; |
|
2830 } |
|
2831 else |
|
2832 { |
|
2833 iWordJustExcess = aExcessWidth; |
|
2834 iWordJustNum = aNumGaps; |
|
2835 } |
|
2836 } |
|
2837 |
|
2838 |
|
2839 /** |
|
2840 Sets the underline style for all subsequently drawn text. |
|
2841 The function provides a concrete implementation of the pure virtual function CGraphicsContext::SetUnderlineStyle(). |
|
2842 The function behaviour is the same as documented in that class. |
|
2843 |
|
2844 @param aUnderlineStyle The underline style to be used. |
|
2845 |
|
2846 @see CGraphicsContext::SetUnderlineStyle() |
|
2847 */ |
|
2848 EXPORT_C void CDirectGdiContext::SetUnderlineStyle(DirectGdi::TFontUnderline aUnderlineStyle) |
|
2849 { |
|
2850 GRAPHICS_TRACE1("CDirectGdiContext::SetWordJustification(%d)", aUnderlineStyle); |
|
2851 iUnderline = aUnderlineStyle; |
|
2852 } |
|
2853 |
|
2854 |
|
2855 /** |
|
2856 Sets the strikethrough style for all subsequently drawn text. |
|
2857 The function provides a concrete implementation of the pure virtual function CGraphicsContext::SetStrikethroughStyle(). |
|
2858 The function behaviour is the same as documented in that class. |
|
2859 |
|
2860 @param aStrikethroughStyle The strikethrough style to be used. |
|
2861 |
|
2862 @see CGraphicsContext::SetStrikethroughStyle() |
|
2863 */ |
|
2864 EXPORT_C void CDirectGdiContext::SetStrikethroughStyle(DirectGdi::TFontStrikethrough aStrikethroughStyle) |
|
2865 { |
|
2866 GRAPHICS_TRACE1("CDirectGdiContext::SetStrikethroughStyle(%d)", aStrikethroughStyle); |
|
2867 iStrikethrough = aStrikethroughStyle; |
|
2868 } |
|
2869 |
|
2870 |
|
2871 /** |
|
2872 Sets the bitmap to be used as the brush pattern when EPatternedBrush is selected. |
|
2873 The DirectGDI generic layer owns the bitmap and will keep the bitmap until ResetBrushPattern() is called. |
|
2874 |
|
2875 The client may modify the content of the bitmap used as the brush pattern. If this is done after |
|
2876 issuing drawing commands there is no guarantee which bitmap content will be used as brush pattern. |
|
2877 Clients must call Finish() on the driver before modifying the bitmap content if they want a guaranteed |
|
2878 result that the previously issued drawing commands will be drawn using the old bitmap brush pattern. |
|
2879 |
|
2880 In the event of a failure, the error state is set to KErrCouldNotConnect if no connection to the font |
|
2881 and bitmap server could be made, KErrBadHandle if the handle of the bitmap is null, KErrUnknown if |
|
2882 no bitmap could be found with the specified handle number, otherwise one of the system-wide error codes. |
|
2883 |
|
2884 @see CDirectGdiContext::SetBrushStyle() |
|
2885 @see CDirectGdiContext::SetBrushOrigin() |
|
2886 @see CDirectGdiContext::ResetBrushPattern() |
|
2887 |
|
2888 @param aBitmap Bitmap that will be used as the brush pattern. |
|
2889 |
|
2890 @pre Bitmap is fully constructed. |
|
2891 @post Bitmap will be used as the brush pattern for subsequent drawing operations when EPatternedBrush |
|
2892 is selected. It remains in effect until ResetBrushPattern() is called. |
|
2893 */ |
|
2894 EXPORT_C void CDirectGdiContext::SetBrushPattern(const CFbsBitmap& aBitmap) |
|
2895 { |
|
2896 GRAPHICS_TRACE1("CDirectGdiContext::SetBrushPattern(%d)", aBitmap.Handle()); |
|
2897 SetBrushPattern(aBitmap.Handle()); |
|
2898 } |
|
2899 |
|
2900 |
|
2901 /** |
|
2902 Sets the bitmap to be used as the brush pattern when EPatternedBrush is selected. |
|
2903 The DirectGDI generic layer owns the bitmap and will keep the bitmap until ResetBrushPattern() is called. |
|
2904 If the client modifies the content of the bitmap used as the brush pattern after issuing any drawing |
|
2905 commands that uses that brush pattern, the method does not guarantee whether the old bitmap |
|
2906 content or the new one will be used as brush pattern. Clients must call Finish() on the driver |
|
2907 before modifying the bitmap content if they want a guaranteed result that the previously issued |
|
2908 drawing commands will be drawn using the old bitmap brush pattern. |
|
2909 |
|
2910 In the event of a failure, the error state is set to KErrCouldNotConnect if no connection to the font |
|
2911 and bitmap server could be made, KErrBadHandle if the handle is null, KErrUnknown if no bitmap could |
|
2912 be found with the specified handle number, otherwise one of the system-wide error codes. |
|
2913 |
|
2914 @param aFbsBitmapHandle Bitmap handle that will be used as the brush pattern. |
|
2915 |
|
2916 @pre Bitmap belonging to the handle is fully constructed. |
|
2917 @post Bitmap will be used as the brush pattern for subsequent drawing operations when EPatternedBrush |
|
2918 is selected. It remains in effect until ResetBrushPattern() is called. |
|
2919 @panic DGDI 8, if aFbsBitmapHandle is 0. |
|
2920 */ |
|
2921 EXPORT_C void CDirectGdiContext::SetBrushPattern(TInt aFbsBitmapHandle) |
|
2922 { |
|
2923 GRAPHICS_TRACE1("CDirectGdiContext::SetBrushPattern(%d)", aFbsBitmapHandle); |
|
2924 if (aFbsBitmapHandle == KNullHandle) |
|
2925 { |
|
2926 iDriver.SetError(KErrBadHandle); |
|
2927 return; |
|
2928 } |
|
2929 |
|
2930 // Check we're not already using the passed brush pattern |
|
2931 if (iBrushPattern.Handle() == aFbsBitmapHandle) |
|
2932 { |
|
2933 return; |
|
2934 } |
|
2935 |
|
2936 // Delete any previously saved brush pattern |
|
2937 CleanUpBrushPattern(); |
|
2938 |
|
2939 TInt result = iBrushPattern.Duplicate(aFbsBitmapHandle); |
|
2940 if (result == KErrNone) |
|
2941 { |
|
2942 result = iEngine->SetBrushPattern(iBrushPattern); |
|
2943 } |
|
2944 |
|
2945 if (result == KErrNone) |
|
2946 { |
|
2947 iBrushPatternUsed = ETrue; |
|
2948 } |
|
2949 else |
|
2950 { |
|
2951 iDriver.SetError(result); |
|
2952 } |
|
2953 |
|
2954 return; |
|
2955 } |
|
2956 |
|
2957 |
|
2958 /** |
|
2959 Selects the font to be used for text drawing. |
|
2960 Notes: |
|
2961 When the font is no longer required, use ResetFont() to free up the memory used. |
|
2962 If SetFont() is used again without using ResetFont() then the previous font is reset |
|
2963 automatically. If no font has been selected, and an attempt is made to draw text with |
|
2964 DrawText(), then a panic occurs. |
|
2965 |
|
2966 @see CDirectGdiContext::ResetFont() |
|
2967 @see CDirectGdiContext::DrawText() |
|
2968 |
|
2969 @param aFont The font to be used. |
|
2970 |
|
2971 @panic DGDI 12, if aFont has an invalid handle or is not a CFbsFont, or the font cannot be duplicated. |
|
2972 */ |
|
2973 EXPORT_C void CDirectGdiContext::SetFont(const CFont* aFont) |
|
2974 { |
|
2975 GRAPHICS_TRACE("CDirectGdiContext::SetFont"); |
|
2976 // Note: We pass a ptr in, rather than a reference, because otherwise the caller would almost always have to do complex casting |
|
2977 GRAPHICS_ASSERT_ALWAYS(aFont->TypeUid() == KCFbsFontUid, EDirectGdiPanicInvalidFont); |
|
2978 const CDirectGdiFont* font = reinterpret_cast<const CDirectGdiFont*>(aFont); |
|
2979 GRAPHICS_ASSERT_ALWAYS(font->Handle(), EDirectGdiPanicInvalidFont); |
|
2980 |
|
2981 if (iFont.Handle() == font->Handle()) |
|
2982 { |
|
2983 return; |
|
2984 } |
|
2985 ResetFont(); |
|
2986 TInt err = iFont.Duplicate(font->Handle()); |
|
2987 GRAPHICS_ASSERT_ALWAYS(err == KErrNone, EDirectGdiPanicInvalidFont); // This may seem extreme but it is what BitGdi did |
|
2988 iEngine->SetFont(iFont.Address()->UniqueFontId()); |
|
2989 } |
|
2990 |
|
2991 |
|
2992 /** |
|
2993 Copies the content of a rectangular area on the target to another location. |
|
2994 The source rect will be intersected with the target’s full extent. |
|
2995 |
|
2996 @param aOffset Offset from the top left corner of the rectangle to be copied to the top left corner of the copy. |
|
2997 @param aRect Area to be copied. |
|
2998 |
|
2999 @pre The rendering target has been activated. |
|
3000 @post Request to copy an area has been accepted. There is no guarantee that the |
|
3001 request has been processed when this method returns. |
|
3002 |
|
3003 @panic DGDI 7, if the rendering context has not been activated. |
|
3004 */ |
|
3005 EXPORT_C void CDirectGdiContext::CopyRect(const TPoint& aOffset, const TRect& aRect) |
|
3006 { |
|
3007 GRAPHICS_TRACE("CDirectGdiContext::CopyRect"); |
|
3008 if (aRect.IsEmpty() || aOffset == TPoint(0,0)) |
|
3009 { |
|
3010 return; |
|
3011 } |
|
3012 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3013 iEngine->CopyRect(aOffset, aRect); |
|
3014 } |
|
3015 |
|
3016 /** |
|
3017 Copies all settings from the specified DirectGDI context. |
|
3018 |
|
3019 @param aGc The DirectGDI context whose settings are to be copied. |
|
3020 */ |
|
3021 EXPORT_C void CDirectGdiContext::CopySettings(const CDirectGdiContext& aGc) |
|
3022 { |
|
3023 GRAPHICS_TRACE("CDirectGdiContext::CopySettings"); |
|
3024 SetOrigin(aGc.iOrigin); |
|
3025 SetFont(&(aGc.iFont)); |
|
3026 SetCharJustification(aGc.iCharJustExcess, aGc.iCharJustNum); |
|
3027 SetWordJustification(aGc.iWordJustExcess, aGc.iWordJustNum); |
|
3028 iLastPrintPosition = aGc.iLastPrintPosition; |
|
3029 SetStrikethroughStyle(aGc.iStrikethrough); |
|
3030 SetUnderlineStyle(aGc.iUnderline); |
|
3031 SetPenColor(aGc.iPenColor); |
|
3032 SetPenSize(aGc.iPenSize); |
|
3033 SetPenStyle(aGc.iPenStyle); |
|
3034 SetDrawMode(aGc.iDrawMode); |
|
3035 SetTextShadowColor(aGc.iTextShadowColor); |
|
3036 SetBrushColor(aGc.iBrushColor); |
|
3037 SetBrushStyle(aGc.iBrushStyle); |
|
3038 if(aGc.iBrushPattern.Handle()) |
|
3039 { |
|
3040 SetBrushPattern(aGc.iBrushPattern.Handle()); |
|
3041 } |
|
3042 iBrushPatternUsed = aGc.iBrushPatternUsed; |
|
3043 SetBrushOrigin(aGc.iBrushOrigin); |
|
3044 } |
|
3045 |
|
3046 /** |
|
3047 Updates the justification settings. |
|
3048 This function assumes that NoJustifyAutoUpdate() has not been used. |
|
3049 |
|
3050 @param aText The text for which justification is to be adjusted. |
|
3051 @param aParam Parameters used in drawing text. |
|
3052 |
|
3053 @panic DGDI 7, if the rendering context has not been activated. |
|
3054 @panic DGDI 13, if NoJustifyAutoUpdate() had been called prior to this. |
|
3055 */ |
|
3056 EXPORT_C void CDirectGdiContext::UpdateJustification(const TDesC& aText, const DirectGdi::TTextParameters* aParam) |
|
3057 { |
|
3058 GRAPHICS_TRACE("CDirectGdiContext::UpdateJustification"); |
|
3059 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3060 GRAPHICS_ASSERT_ALWAYS(iAutoUpdateJustification, EDirectGdiPanicAutoUpdateJustificationUsed); |
|
3061 if (((iCharJustNum < 1) || (iCharJustExcess == 0)) && ((iWordJustNum < 1) || (iWordJustExcess < 1))) |
|
3062 { |
|
3063 return; |
|
3064 } |
|
3065 |
|
3066 TInt length = aText.Length(); |
|
3067 CFont::TPositionParam param; |
|
3068 param.iText.Set(aText); // Set the start of the string |
|
3069 if (aParam) |
|
3070 { |
|
3071 length = aParam->iEnd; |
|
3072 param.iPosInText = aParam->iStart; |
|
3073 } |
|
3074 TInt excess = 0; |
|
3075 TInt glyphs = 0; |
|
3076 RShapeInfo shapeInfo; |
|
3077 for (TInt count = 0; count < length; count++) |
|
3078 { |
|
3079 if ((iCharJustNum > 0) && (iCharJustExcess != 0)) |
|
3080 { |
|
3081 excess += CGraphicsContext::JustificationInPixels(iCharJustExcess, iCharJustNum); |
|
3082 } |
|
3083 if ((iWordJustNum > 0) && (iWordJustExcess > 0) && (aText[count] == ' ')) |
|
3084 { |
|
3085 excess += CGraphicsContext::JustificationInPixels(iWordJustExcess, iWordJustNum); |
|
3086 } |
|
3087 if (iCharJustNum < (glyphs + length - count)) // there's at least 1 combined glyph to come |
|
3088 { |
|
3089 // otherwise we can skip this slow bit and just increment |
|
3090 if (iFont.GetCharacterPosition2(param, shapeInfo)) |
|
3091 { |
|
3092 count = param.iPosInText - 1; // -1 'cos it gets incremented anyway |
|
3093 } |
|
3094 } |
|
3095 glyphs++; |
|
3096 } |
|
3097 if (shapeInfo.IsOpen()) |
|
3098 { |
|
3099 shapeInfo.Close(); |
|
3100 } |
|
3101 iLastPrintPosition.iX += excess; |
|
3102 } |
|
3103 |
|
3104 |
|
3105 /** |
|
3106 Updates the justification for vertical text. |
|
3107 This function assumes that NoJustifyAutoUpdate() has not been used. |
|
3108 |
|
3109 @param aText The text for which justification is to be adjusted. |
|
3110 @param aParam Parameters used in drawing text. |
|
3111 @param aUp ETrue, if text is to be justified upwards; EFalse, if text is to be justified downwards. |
|
3112 |
|
3113 @panic DGDI 7, if the rendering context has not been activated. |
|
3114 @panic DGDI 13, if NoJustifyAutoUpdate() had been called prior to this. |
|
3115 */ |
|
3116 EXPORT_C void CDirectGdiContext::UpdateJustificationVertical(const TDesC& aText, const DirectGdi::TTextParameters* aParam, TBool aUp) |
|
3117 { |
|
3118 GRAPHICS_TRACE("CDirectGdiContext::UpdateJustificationVertical"); |
|
3119 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3120 GRAPHICS_ASSERT_ALWAYS(iAutoUpdateJustification, EDirectGdiPanicAutoUpdateJustificationUsed); |
|
3121 |
|
3122 if (((iCharJustNum < 1) || (iCharJustExcess == 0)) && ((iWordJustNum < 1) || (iWordJustExcess < 1))) |
|
3123 { |
|
3124 return; |
|
3125 } |
|
3126 |
|
3127 TInt length = aText.Length(); |
|
3128 CFont::TPositionParam param; |
|
3129 param.iText.Set(aText); // Set the start of the string |
|
3130 if (aParam) |
|
3131 { |
|
3132 length = aParam->iEnd; |
|
3133 param.iPosInText = aParam->iStart; |
|
3134 } |
|
3135 TInt excess = 0; |
|
3136 TInt glyphs = 0; |
|
3137 RShapeInfo shapeInfo; |
|
3138 for (TInt count = 0; count < length; count++) |
|
3139 { |
|
3140 if ((iCharJustNum > 0) && (iCharJustExcess != 0)) |
|
3141 { |
|
3142 excess += CGraphicsContext::JustificationInPixels(iCharJustExcess, iCharJustNum); |
|
3143 } |
|
3144 if ((iWordJustNum > 0) && (iWordJustExcess > 0) && (aText[count] == ' ')) |
|
3145 { |
|
3146 excess += CGraphicsContext::JustificationInPixels(iWordJustExcess, iWordJustNum); |
|
3147 } |
|
3148 if (iCharJustNum < (glyphs + length - count)) // there's at least 1 combined glyph to come |
|
3149 { |
|
3150 // otherwise we can skip this slow bit and just increment |
|
3151 if (iFont.GetCharacterPosition2(param, shapeInfo)) |
|
3152 { |
|
3153 count = param.iPosInText - 1; // -1 because it gets incremented anyway |
|
3154 } |
|
3155 } |
|
3156 glyphs++; |
|
3157 } |
|
3158 if (shapeInfo.IsOpen()) |
|
3159 { |
|
3160 shapeInfo.Close(); |
|
3161 } |
|
3162 |
|
3163 if (aUp) |
|
3164 { |
|
3165 iLastPrintPosition.iY -= excess; |
|
3166 } |
|
3167 else |
|
3168 { |
|
3169 iLastPrintPosition.iY += excess; |
|
3170 } |
|
3171 } |
|
3172 |
|
3173 |
|
3174 /** |
|
3175 Selects a font for text drawing but does not take a copy. |
|
3176 The original must not be destroyed until SetFont(), SetFontNoDuplicate(), ResetFont() |
|
3177 or the destructor is called. |
|
3178 |
|
3179 @param aFont A pointer to the font to be used. |
|
3180 @panic DGDI 12, if aFont has no handle or is not a CFbsFont. |
|
3181 */ |
|
3182 EXPORT_C void CDirectGdiContext::SetFontNoDuplicate(const CDirectGdiFont* aFont) |
|
3183 { |
|
3184 GRAPHICS_TRACE("CDirectGdiContext::SetFontNoDuplicate"); |
|
3185 // Note: We pass a ptr in, rather than a reference, because otherwise the caller would almost always have to do complex casting |
|
3186 GRAPHICS_ASSERT_ALWAYS(aFont->TypeUid() == KCFbsFontUid, EDirectGdiPanicInvalidFont); |
|
3187 GRAPHICS_ASSERT_ALWAYS(aFont->Handle(), EDirectGdiPanicInvalidFont); |
|
3188 |
|
3189 if (iFont.Handle() == aFont->Handle()) |
|
3190 { |
|
3191 return; |
|
3192 } |
|
3193 |
|
3194 ResetFont(); |
|
3195 iFont = *aFont; |
|
3196 iEngine->SetFont(iFont.Address()->UniqueFontId()); |
|
3197 } |
|
3198 |
|
3199 |
|
3200 /** |
|
3201 Checks to see if a brush pattern is currently set. |
|
3202 |
|
3203 @return ETrue is a brush pattern is currently set, EFalse if no brush pattern is currently set. |
|
3204 */ |
|
3205 EXPORT_C TBool CDirectGdiContext::HasBrushPattern() const |
|
3206 { |
|
3207 GRAPHICS_TRACE("CDirectGdiContext::HasBrushPattern"); |
|
3208 return iBrushPatternUsed; |
|
3209 } |
|
3210 |
|
3211 |
|
3212 /** |
|
3213 Tests whether a font is used. |
|
3214 |
|
3215 @return ETrue, if a font is being used; EFalse, otherwise. |
|
3216 */ |
|
3217 EXPORT_C TBool CDirectGdiContext::HasFont() const |
|
3218 { |
|
3219 GRAPHICS_TRACE("CDirectGdiContext::HasFont"); |
|
3220 TBool result = EFalse; |
|
3221 if (iFont.Handle() != KNullHandle) |
|
3222 result = ETrue; |
|
3223 return result; |
|
3224 } |
|
3225 |
|
3226 |
|
3227 /** |
|
3228 Externalises the context and the drawing engine object to the write stream. |
|
3229 It is important that the font and brush bitmap of the GC is maintained between |
|
3230 calls to ExternalizeL() and InternalizeL(). The font handle and brush bitmap handle |
|
3231 is externalised, not the underlying data. This is done for performance reasons. |
|
3232 |
|
3233 @param aWriteStream Write stream. |
|
3234 |
|
3235 @pre None. |
|
3236 @post The context and drawing engine object states are written to the write stream. |
|
3237 |
|
3238 @see MDirectGdiEngine::InternalizeL |
|
3239 @leave If there was an error writing to the write stream. |
|
3240 */ |
|
3241 EXPORT_C void CDirectGdiContext::ExternalizeL(RWriteStream& aWriteStream) |
|
3242 { |
|
3243 GRAPHICS_TRACE("CDirectGdiContext::ExternalizeL"); |
|
3244 aWriteStream << KDirectGDIContext_VerNo; |
|
3245 iEngine->ExternalizeL(aWriteStream); |
|
3246 |
|
3247 aWriteStream << iOrigin; |
|
3248 aWriteStream.WriteInt32L(iFont.Handle()); |
|
3249 aWriteStream.WriteInt32L(iCharJustExcess); |
|
3250 aWriteStream.WriteInt32L(iCharJustNum); |
|
3251 aWriteStream.WriteInt32L(iWordJustExcess); |
|
3252 aWriteStream.WriteInt32L(iWordJustNum); |
|
3253 aWriteStream << iLastPrintPosition; |
|
3254 aWriteStream.WriteUint8L(iStrikethrough); |
|
3255 aWriteStream.WriteUint8L(iUnderline); |
|
3256 aWriteStream << iPenColor; |
|
3257 aWriteStream.WriteUint32L(iPenSize.iWidth); |
|
3258 aWriteStream.WriteUint32L(iPenSize.iHeight); |
|
3259 aWriteStream.WriteUint8L(iPenStyle); |
|
3260 aWriteStream.WriteUint8L(iDrawMode); |
|
3261 aWriteStream << iTextShadowColor; |
|
3262 aWriteStream << iBrushColor; |
|
3263 aWriteStream.WriteInt32L(iBrushPattern.Handle()); |
|
3264 aWriteStream.WriteUint8L(iBrushStyle); |
|
3265 aWriteStream.WriteUint8L(iBrushPatternUsed); |
|
3266 aWriteStream << iBrushOrigin; |
|
3267 aWriteStream.WriteUint8L(iAutoUpdateJustification); |
|
3268 } |
|
3269 |
|
3270 |
|
3271 /** |
|
3272 Internalises the context and the drawing engine object from the read stream. |
|
3273 It is important that the font and brush bitmap of the GC is maintained between |
|
3274 calls to ExternalizeL() and InternalizeL(). The font handle and brush bitmap handle |
|
3275 is externalised, not the underlying data. This is done for performance reasons. |
|
3276 |
|
3277 @param aReadStream Read stream. |
|
3278 |
|
3279 @pre The font has not been released since the last call of CDirectGdiContext::ExternalizeL on the stream |
|
3280 @pre The handle of the brush pattern bitmap has not been closed since the call to CDirectGdiContext::ExternalizeL on the stream. |
|
3281 @post The context and drawing engine object states are updated with the values from the read stream. |
|
3282 |
|
3283 @see MDirectGdiEngine::ExternalizeL |
|
3284 @leave If there was an error reading from the read stream. |
|
3285 */ |
|
3286 EXPORT_C void CDirectGdiContext::InternalizeL(RReadStream& aReadStream) |
|
3287 { |
|
3288 GRAPHICS_TRACE("CDirectGdiContext::InternalizeL"); |
|
3289 TUint16 archiveVerNo = 0; |
|
3290 aReadStream >> archiveVerNo; |
|
3291 iEngine->InternalizeL(aReadStream); |
|
3292 |
|
3293 TPoint origin; |
|
3294 aReadStream >> origin; |
|
3295 SetOrigin(origin); |
|
3296 ResetFont(); |
|
3297 TInt fontHandle = aReadStream.ReadInt32L(); |
|
3298 if(fontHandle) |
|
3299 { |
|
3300 TInt res = iFont.Duplicate(fontHandle); |
|
3301 if(res == KErrNone) |
|
3302 { |
|
3303 iEngine->SetFont(iFont.Address()->UniqueFontId()); |
|
3304 } |
|
3305 else |
|
3306 { |
|
3307 iDriver.SetError(res); |
|
3308 } |
|
3309 } |
|
3310 iCharJustExcess = aReadStream.ReadUint32L(); |
|
3311 iCharJustNum = aReadStream.ReadUint32L(); |
|
3312 iWordJustExcess = aReadStream.ReadUint32L(); |
|
3313 iWordJustNum = aReadStream.ReadUint32L(); |
|
3314 aReadStream >> iLastPrintPosition; |
|
3315 iStrikethrough = (DirectGdi::TFontStrikethrough)aReadStream.ReadUint8L(); |
|
3316 iUnderline = (DirectGdi::TFontUnderline)aReadStream.ReadUint8L(); |
|
3317 TRgb penColor; |
|
3318 aReadStream >> penColor; |
|
3319 SetPenColor(penColor); |
|
3320 TSize penSize; |
|
3321 penSize.iWidth = aReadStream.ReadUint32L(); |
|
3322 penSize.iHeight = aReadStream.ReadUint32L(); |
|
3323 SetPenSize(penSize); |
|
3324 DirectGdi::TPenStyle penStyle = (DirectGdi::TPenStyle)aReadStream.ReadUint8L(); |
|
3325 SetPenStyle(penStyle); |
|
3326 DirectGdi::TDrawMode drawMode = (DirectGdi::TDrawMode)aReadStream.ReadUint8L(); |
|
3327 SetDrawMode(drawMode); |
|
3328 TRgb textShadowColor; |
|
3329 aReadStream >> textShadowColor; |
|
3330 SetTextShadowColor(textShadowColor); |
|
3331 TRgb brushColor; |
|
3332 aReadStream >> brushColor; |
|
3333 SetBrushColor(brushColor); |
|
3334 TInt patternHandle = aReadStream.ReadInt32L(); |
|
3335 if (patternHandle) |
|
3336 { |
|
3337 // Brush pattern must be set before style, otherwise there'll be a panic! |
|
3338 SetBrushPattern(patternHandle); |
|
3339 } |
|
3340 DirectGdi::TBrushStyle brushStyle; |
|
3341 brushStyle = (DirectGdi::TBrushStyle)aReadStream.ReadInt8L(); |
|
3342 SetBrushStyle(brushStyle); |
|
3343 iBrushPatternUsed = (TBool)aReadStream.ReadUint8L(); |
|
3344 TPoint brushOrigin; |
|
3345 aReadStream >> brushOrigin; |
|
3346 SetBrushOrigin(brushOrigin); |
|
3347 iAutoUpdateJustification = (TBool)aReadStream.ReadUint8L(); |
|
3348 } |
|
3349 |
|
3350 |
|
3351 /** |
|
3352 Retrieves the currently set brush colour. |
|
3353 |
|
3354 @return The current brush colour. |
|
3355 */ |
|
3356 EXPORT_C TRgb CDirectGdiContext::BrushColor() const |
|
3357 { |
|
3358 return iBrushColor; |
|
3359 } |
|
3360 |
|
3361 |
|
3362 /** |
|
3363 Retrieves the currently set pen colour. |
|
3364 |
|
3365 @return The current pen colour. |
|
3366 */ |
|
3367 EXPORT_C TRgb CDirectGdiContext::PenColor() const |
|
3368 { |
|
3369 return iPenColor; |
|
3370 } |
|
3371 |
|
3372 /** |
|
3373 Retrieves the currently set text shadow colour. |
|
3374 |
|
3375 @return The current text shadow colour. |
|
3376 */ |
|
3377 EXPORT_C TRgb CDirectGdiContext::TextShadowColor() const |
|
3378 { |
|
3379 return iTextShadowColor; |
|
3380 } |
|
3381 |
|
3382 /** |
|
3383 Draws an image based resource which may be generated using non-native rendering API such as OpenGL ES |
|
3384 or OpenVG. The resource will be drawn at the specified position in its original size with orientation |
|
3385 according to the specified rotation parameter. The current clipping region applies. The resource can be |
|
3386 drawn rotated using the DirectGdi::TGraphicsRotation enum which defines possible rotation values in |
|
3387 clockwise degrees. |
|
3388 |
|
3389 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
3390 |
|
3391 @param aPos The position of the top-left corner of the resource. |
|
3392 @param aSource The resource to be drawn. |
|
3393 @param aRotation The rotation to be applied to the resource before it is drawn. The default value is DirectGdi::EGraphicsRotationNone. |
|
3394 |
|
3395 @pre Drawing context has been activated on a rendering target. The resource has been fully constructed. |
|
3396 @post Request to draw resource has been accepted. There is no guarantee that the request has been completed |
|
3397 when this method returns. |
|
3398 |
|
3399 @panic DGDI 7, if the rendering context has not been activated. |
|
3400 */ |
|
3401 EXPORT_C void CDirectGdiContext::DrawResource( |
|
3402 const TPoint& aPos, |
|
3403 const RDirectGdiDrawableSource& aSource, |
|
3404 DirectGdi::TGraphicsRotation aRotation) |
|
3405 { |
|
3406 GRAPHICS_TRACE("CDirectGdiContext::DrawResource"); |
|
3407 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3408 |
|
3409 if (aSource.Handle() != KNullHandle) |
|
3410 { |
|
3411 iEngine->DrawResource(aPos, aSource, aRotation); |
|
3412 } |
|
3413 else |
|
3414 { |
|
3415 iDriver.SetError(KErrBadHandle); |
|
3416 } |
|
3417 } |
|
3418 |
|
3419 /** |
|
3420 Draws an image based resource. The resource will be rendered to the given destination rectangle on |
|
3421 rendering target in its original dimensions with orientation according to the specified rotation parameter. |
|
3422 Drawing will be clipped to the given destination rectangle. The current clipping region applies. |
|
3423 |
|
3424 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
3425 |
|
3426 @param aDestRect Destination rectangle to which the resource will be rendered. |
|
3427 @param aSource The resource to be drawn. |
|
3428 @param aRotation Rotation to be applied to the resource before it is drawn. Default value is DirectGdi::EGraphicsRotationNone. |
|
3429 |
|
3430 @pre Drawing context has been activated on a rendering target. The resource has been fully constructed. |
|
3431 @post Request to draw resource has been accepted. There is no guarantee that the request has been completed |
|
3432 when this method returns. |
|
3433 |
|
3434 @panic DGDI 7, if the rendering context has not been activated. |
|
3435 */ |
|
3436 EXPORT_C void CDirectGdiContext::DrawResource(const TRect& aDestRect, |
|
3437 const RDirectGdiDrawableSource& aSource, |
|
3438 DirectGdi::TGraphicsRotation aRotation) |
|
3439 { |
|
3440 GRAPHICS_TRACE("CDirectGdiContext::DrawResource"); |
|
3441 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3442 |
|
3443 if (aSource.Handle() != KNullHandle) |
|
3444 { |
|
3445 if ((aDestRect.Width() > 0) && (aDestRect.Height() > 0)) |
|
3446 { |
|
3447 iEngine->DrawResource(aDestRect, aSource, aRotation); |
|
3448 } |
|
3449 } |
|
3450 else |
|
3451 { |
|
3452 iDriver.SetError(KErrBadHandle); |
|
3453 } |
|
3454 } |
|
3455 |
|
3456 |
|
3457 /** |
|
3458 Draws an image based resource. The resource is rendered into the given destination rectangle. |
|
3459 Scaling (stretching or compression) applies if the destination rectangle is different from the |
|
3460 source rectangle. The resource orientation is set based on the specified rotation parameter |
|
3461 before scaling and drawing operations are performed. |
|
3462 |
|
3463 If the user modifies the content of the resource after issuing a DrawResource() command (from the |
|
3464 same thread), the adaptation must make sure that the user’s operations are serialised within |
|
3465 that thread, for example, DrawResource() is processed before the modify operations. The adaptation |
|
3466 does not guarantee the result if the resource modification is performed from threads other than |
|
3467 the one that issued the DrawResource() command. To achieve a guaranteed result in that case, users |
|
3468 must perform synchronisation between any threads that operate on the resource and issue Finish() |
|
3469 on the driver whenever necessary. When using other renderers or mappings, synchronisation is needed |
|
3470 even when this is from within the same thread. |
|
3471 |
|
3472 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
3473 |
|
3474 @param aDestRect The destination rectangle to which the resource will be rendered. |
|
3475 @param aSource The resource to draw. |
|
3476 @param aSrcRect The source rectangle specifying the area/sub-area of the resource to be rendered. |
|
3477 @param aRotation Rotation to be applied to the resource before it is drawn |
|
3478 |
|
3479 @pre The rendering target has been activated. The resource has been fully constructed. |
|
3480 @post Request to draw an image based resource has been accepted. There is no guarantee that the |
|
3481 request has been completed when this method returns. |
|
3482 |
|
3483 @panic DGDI 7, if the rendering context has not been activated. |
|
3484 */ |
|
3485 EXPORT_C void CDirectGdiContext::DrawResource( |
|
3486 const TRect& aDestRect, |
|
3487 const RDirectGdiDrawableSource& aSource, |
|
3488 const TRect& aSrcRect, |
|
3489 DirectGdi::TGraphicsRotation aRotation) |
|
3490 { |
|
3491 GRAPHICS_TRACE("CDirectGdiContext::DrawResource"); |
|
3492 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3493 |
|
3494 if (aSource.Handle() != KNullHandle) |
|
3495 { |
|
3496 if ((aDestRect.Width() > 0) && (aDestRect.Height() > 0) |
|
3497 && (aSrcRect.Width() > 0) && (aSrcRect.Height() > 0)) |
|
3498 { |
|
3499 iEngine->DrawResource(aDestRect, aSource, aSrcRect, aRotation); |
|
3500 } |
|
3501 } |
|
3502 else |
|
3503 { |
|
3504 iDriver.SetError(KErrBadHandle); |
|
3505 } |
|
3506 } |
|
3507 |
|
3508 |
|
3509 /** |
|
3510 Draws a non-image based resource. The resource will be rendered into the given destination rectangle. |
|
3511 The current clipping region applies. The adaptation is free to interpret the parameters and may define |
|
3512 their own rules on how to handle the rendering of a non-image based resource. |
|
3513 |
|
3514 In the event of a failure, the error state is set to one of the system-wide error codes. |
|
3515 |
|
3516 @param aDestRect The destination rectangle to which the resource will be rendered. |
|
3517 @param aSource The resource. |
|
3518 @param aParam Parameters specifying how to draw the resource. |
|
3519 |
|
3520 @pre The rendering target has been activated. The resource has been fully constructed. |
|
3521 @post Request to draw a non-image based resource has been accepted. |
|
3522 There is no guarantee that the request has been completed when this method returns. |
|
3523 |
|
3524 @panic DGDI 7, if the rendering context has not been activated. |
|
3525 */ |
|
3526 EXPORT_C void CDirectGdiContext::DrawResource( |
|
3527 const TRect& aDestRect, |
|
3528 const RDirectGdiDrawableSource& aSource, |
|
3529 const TDesC8& aParam) |
|
3530 { |
|
3531 GRAPHICS_TRACE("CDirectGdiContext::DrawResource"); |
|
3532 GRAPHICS_ASSERT_ALWAYS(iActivated, EDirectGdiPanicContextNotActivated); |
|
3533 |
|
3534 if (aSource.Handle() != KNullHandle) |
|
3535 { |
|
3536 if ((aDestRect.Width() > 0) && (aDestRect.Height() > 0)) |
|
3537 { |
|
3538 iEngine->DrawResource(aDestRect, aSource, aParam); |
|
3539 } |
|
3540 } |
|
3541 else |
|
3542 { |
|
3543 iDriver.SetError(KErrBadHandle); |
|
3544 } |
|
3545 } |
|
3546 |
|
3547 /** |
|
3548 Retrieves a pointer to an instance of the appropriate extension interface implementation. |
|
3549 |
|
3550 @param aInterfaceId Interface identifier of the interface to be retrieved. |
|
3551 @param aInterface On return, holds the specified interface, or NULL if the interface cannot be found. |
|
3552 |
|
3553 @pre None. |
|
3554 @post None. |
|
3555 |
|
3556 @return KErrNone If the interface is supported, KErrNotSupported otherwise. |
|
3557 */ |
|
3558 EXPORT_C TInt CDirectGdiContext::GetInterface(TUid aInterfaceId, TAny*& aInterface) |
|
3559 { |
|
3560 GRAPHICS_TRACE("CDirectGdiContext::GetInterface"); |
|
3561 return iEngine->GetInterface(aInterfaceId, aInterface); |
|
3562 } |
|
3563 |
|
3564 /** |
|
3565 Release the brush pattern's handle, and mark it as no longer used. |
|
3566 */ |
|
3567 void CDirectGdiContext::CleanUpBrushPattern() |
|
3568 { |
|
3569 iBrushPattern.Reset(); |
|
3570 iBrushPatternUsed = EFalse; |
|
3571 } |
|
3572 |
|
3573 /** |
|
3574 @internalTechnology |
|
3575 |
|
3576 Returns the baseline correction associated with this font. |
|
3577 This value is used to alter the underline/strikethrough position applied to linked fonts. |
|
3578 |
|
3579 @return The baseline correction value set by the rasterizer; or 0 if not set |
|
3580 */ |
|
3581 TInt CDirectGdiContext::BaselineCorrection() |
|
3582 { |
|
3583 TOpenFontMetrics metrics; |
|
3584 if (iFont.GetFontMetrics(metrics)) |
|
3585 return metrics.BaselineCorrection(); |
|
3586 else |
|
3587 return 0; |
|
3588 } |