|
1 // Copyright (c) 1997-2009 Nokia Corporation and/or its subsidiary(-ies). |
|
2 // All rights reserved. |
|
3 // This component and the accompanying materials are made available |
|
4 // under the terms of "Eclipse Public License v1.0" |
|
5 // which accompanies this distribution, and is available |
|
6 // at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
7 // |
|
8 // Initial Contributors: |
|
9 // Nokia Corporation - initial contribution. |
|
10 // |
|
11 // Contributors: |
|
12 // |
|
13 // Description: |
|
14 |
|
15 #include <eiknotapi.h> |
|
16 #include <AknUtils.h> |
|
17 #include <AknLayoutFont.h> |
|
18 #include <AknBidiTextUtils.h> |
|
19 #include <AknsUtils.h> |
|
20 #include <AknsDrawUtils.h> |
|
21 #include <ecom/implementationproxy.h> |
|
22 #include <AknsBasicBackgroundControlContext.h> |
|
23 #include <AknWsEventObserver.h> |
|
24 #include <apgwgnam.h> |
|
25 //#include <aknappui.h> |
|
26 #include "alfappfwproxyops.h" |
|
27 #include "huiskinbackroundlayout.h" |
|
28 |
|
29 // hollow notifier implementation to get access on AppFw inside eikon server |
|
30 class CAlfAppFwNotifier : public CBase, public MEikSrvNotifierBase2, public MCoeMessageMonitorObserver |
|
31 { |
|
32 public: |
|
33 ~CAlfAppFwNotifier() |
|
34 { |
|
35 delete iBitmap; |
|
36 delete iTempSkinBmp; |
|
37 delete iTempMaskBmp; |
|
38 delete iSkinControlContext; |
|
39 } |
|
40 |
|
41 void MonitorWsMessage(const TWsEvent& aEvent) |
|
42 { |
|
43 if (aEvent.Type() == EEventWindowGroupListChanged) |
|
44 { |
|
45 UpdateWgListL(); |
|
46 } |
|
47 else if (aEvent.Type() == KEikDynamicLayoutVariantSwitch || |
|
48 aEvent.Type() == KEikInputLanguageChange) |
|
49 { |
|
50 if (iLayoutMirrored != AknLayoutUtils::LayoutMirrored()) |
|
51 { |
|
52 iLayoutMirrored = AknLayoutUtils::LayoutMirrored(); |
|
53 if (iLayoutMirroredMessage.IsNull()) |
|
54 { |
|
55 iLayoutMirroredUpdated = ETrue; |
|
56 } |
|
57 else |
|
58 { |
|
59 iLayoutMirroredMessage.Complete(iLayoutMirrored); |
|
60 iLayoutMirroredUpdated = EFalse; |
|
61 } |
|
62 } |
|
63 } |
|
64 } |
|
65 |
|
66 CAlfAppFwNotifier( |
|
67 TUid aNotifierUid, |
|
68 TUid aChannel, |
|
69 TInt aPriority ) |
|
70 : iWsSession(CCoeEnv::Static()->WsSession()) |
|
71 { |
|
72 iInfo.iUid = aNotifierUid; |
|
73 iInfo.iChannel= aChannel; |
|
74 iInfo.iPriority = aPriority; |
|
75 *iWgIdArray = -1; // indicates array uninitialized |
|
76 iLayoutMirrored = AknLayoutUtils::LayoutMirrored(); |
|
77 iLayoutMirroredUpdated = ETrue; |
|
78 CCoeEnv::Static()->AddMessageMonitorObserverL(*this); |
|
79 CCoeEnv::Static()->RootWin().EnableScreenChangeEvents(); |
|
80 } |
|
81 |
|
82 public: |
|
83 // from MEikSrvNotifierBase2 |
|
84 TPtrC8 UpdateL(const TDesC8&) |
|
85 { |
|
86 return KNullDesC8(); |
|
87 } |
|
88 |
|
89 void Cancel() |
|
90 { |
|
91 } |
|
92 |
|
93 void StartL(const TDesC8& aBuffer, TInt aReplySlot, const RMessagePtr2& aMessage) |
|
94 { |
|
95 TInt err = KErrNone; |
|
96 TAlfCommandParams* params = (TAlfCommandParams*) aBuffer.Ptr(); |
|
97 switch (params->iCommand) |
|
98 { |
|
99 case EAlfIsMirrorred: |
|
100 { |
|
101 if (iLayoutMirroredUpdated) |
|
102 { |
|
103 aMessage.Complete(iLayoutMirrored); |
|
104 iLayoutMirroredUpdated = EFalse; |
|
105 } |
|
106 else |
|
107 { |
|
108 iLayoutMirroredMessage = aMessage; |
|
109 } |
|
110 return; |
|
111 } |
|
112 case EAlfCbaLocation: |
|
113 { |
|
114 err = AknLayoutUtils::CbaLocation(); |
|
115 break; |
|
116 } |
|
117 case EAlfLayoutMetricsRect: |
|
118 { |
|
119 TRect rect(0,0,0,0); |
|
120 AknLayoutUtils::LayoutMetricsRect((AknLayoutUtils::TAknLayoutMetrics)params->iInt1, rect); |
|
121 TPckgC<TRect> response(rect); |
|
122 err = aMessage.Write(aReplySlot, response); |
|
123 break; |
|
124 } |
|
125 case EAlfGetCachedColor: |
|
126 { |
|
127 TAknsItemID id; |
|
128 id.iMajor = params->iInt1; |
|
129 id.iMinor = params->iInt2; |
|
130 MAknsSkinInstance* skin = AknsUtils::SkinInstance(); |
|
131 TRgb color = KRgbBlack; |
|
132 err = AknsUtils::GetCachedColor(skin, color, id, params->iInt3 ); |
|
133 if (!err) |
|
134 { |
|
135 TPckgC<TRgb> ret(color); |
|
136 err = aMessage.Write(aReplySlot, ret); |
|
137 } |
|
138 break; |
|
139 } |
|
140 case EAlfConvertVisualAndClip: |
|
141 { |
|
142 TUint desLength = aMessage.GetDesMaxLength(aReplySlot); |
|
143 HBufC* replyDes = HBufC::NewLC(desLength/2+1); |
|
144 TPtr ptr = replyDes->Des(); |
|
145 aMessage.Read(aReplySlot, ptr); |
|
146 // ToDo: Wo to get font from client.. |
|
147 //CFont font = Use Font spec to get the font?? |
|
148 //AknBidiTextUtils::ConvertToVisualAndClipL(ptr, font, params->iInt2, params->iInt3); |
|
149 err = aMessage.Write(aReplySlot, ptr); |
|
150 CleanupStack::PopAndDestroy(); |
|
151 break; |
|
152 } |
|
153 case EAlfGetSkinBackgroundBitmap: |
|
154 { |
|
155 TRect dummy; |
|
156 TRect skinRect; |
|
157 TAknsItemID id; |
|
158 |
|
159 id.iMajor = params->iInt1; |
|
160 id.iMinor = params->iInt2; |
|
161 |
|
162 GetRectForItem(id, dummy, skinRect); |
|
163 |
|
164 if (!iBitmap) |
|
165 { |
|
166 iBitmap = new (ELeave) CFbsBitmap(); |
|
167 User::LeaveIfError( iBitmap->Create(skinRect.Size(), EColor64K) ); // is 64k still valid? |
|
168 } |
|
169 |
|
170 User::LeaveIfError(iBitmap->Resize(skinRect.Size())); |
|
171 |
|
172 if (!iSkinControlContext) |
|
173 { |
|
174 iSkinControlContext = CAknsBasicBackgroundControlContext::NewL( |
|
175 KAknsIIDQsnBgScreen, TRect(TPoint(0, 0), CCoeEnv::Static()->ScreenDevice()->SizeInPixels()), ETrue); |
|
176 } |
|
177 |
|
178 CFbsBitmapDevice* device = CFbsBitmapDevice::NewL(iBitmap); |
|
179 CleanupStack::PushL(device); |
|
180 |
|
181 CFbsBitGc* gc = 0; |
|
182 User::LeaveIfError( device->CreateContext(gc) ); |
|
183 CleanupStack::PushL(gc); |
|
184 iSkinControlContext->SetRect(skinRect); |
|
185 iSkinControlContext->SetBitmap(id); |
|
186 |
|
187 AknsDrawUtils::DrawBackground(AknsUtils::SkinInstance(), iSkinControlContext, NULL, *gc, TPoint(0,0), skinRect, |
|
188 KAknsDrawParamDefault); |
|
189 |
|
190 CleanupStack::PopAndDestroy(gc); |
|
191 CleanupStack::PopAndDestroy(device); |
|
192 TPckg<TInt> ret(iBitmap->Handle()); |
|
193 err = aMessage.Write(aReplySlot, ret); |
|
194 break; |
|
195 } |
|
196 case EAlfGetSkinBitmap: |
|
197 { |
|
198 // local override input params |
|
199 TAlfCommandParams2* params = (TAlfCommandParams2*) aBuffer.Ptr(); |
|
200 TAknsItemID id; |
|
201 |
|
202 id.iMajor = params->iInt1; |
|
203 id.iMinor = params->iInt2; |
|
204 |
|
205 // recycle ownership through these, assuming synchronized client implementation !! |
|
206 delete iTempSkinBmp; |
|
207 iTempSkinBmp = 0; |
|
208 delete iTempMaskBmp; |
|
209 iTempMaskBmp = 0; |
|
210 |
|
211 TRAP(err, AknsUtils::CreateIconL( AknsUtils::SkinInstance(), id, |
|
212 iTempSkinBmp, iTempMaskBmp, |
|
213 params->iFileName, params->iInt3,params->iInt4)); |
|
214 |
|
215 if (err == KErrNotFound) // lets retry without mask |
|
216 { |
|
217 delete iTempSkinBmp; |
|
218 iTempSkinBmp = 0; |
|
219 delete iTempMaskBmp; |
|
220 iTempMaskBmp = 0; |
|
221 // try if we have better luck without mask |
|
222 AknsUtils::CreateIconL( AknsUtils::SkinInstance(), id, |
|
223 iTempSkinBmp, params->iFileName, params->iInt3); |
|
224 |
|
225 } |
|
226 |
|
227 if (iTempSkinBmp) |
|
228 { |
|
229 AknIconUtils::DisableCompression(iTempSkinBmp); |
|
230 AknIconUtils::SetSize( iTempSkinBmp, params->iSize, params->iScaleMode ); |
|
231 } |
|
232 |
|
233 if (iTempMaskBmp) |
|
234 { |
|
235 AknIconUtils::DisableCompression(iTempSkinBmp); |
|
236 AknIconUtils::SetSize( iTempMaskBmp, params->iSize, params->iScaleMode ); |
|
237 } |
|
238 |
|
239 TInt2 ret; |
|
240 ret.iInt1 = iTempSkinBmp->Handle(); |
|
241 ret.iInt2 = iTempMaskBmp?iTempMaskBmp->Handle():0; |
|
242 TPckg<TInt2> retp = ret; |
|
243 err = aMessage.Write(aReplySlot, retp); |
|
244 break; |
|
245 } |
|
246 case EGetCachedSkinItemData: |
|
247 { |
|
248 TAknsItemID id; |
|
249 |
|
250 id.iMajor = params->iInt1; |
|
251 id.iMinor = params->iInt2; |
|
252 |
|
253 TAlfCachedSkinItemArray array; |
|
254 array.iCount = 0; |
|
255 CAknsItemData* data = AknsUtils::SkinInstance()->CreateUncachedItemDataL( id, (TAknsItemType)params->iInt3 ); |
|
256 |
|
257 if (data) |
|
258 { |
|
259 CAknsImageTableItemData* itdata = static_cast<CAknsImageTableItemData*>(data); |
|
260 array.iCount = Min(9, itdata->NumberOfImages()); |
|
261 for(TInt i = 0; i<array.iCount;i++) |
|
262 { |
|
263 array.iImages[i] = itdata->ImageIID(i); |
|
264 } |
|
265 delete data; |
|
266 } |
|
267 TPckgC<TAlfCachedSkinItemArray> retp(array); |
|
268 err = aMessage.Write(aReplySlot, retp); |
|
269 break; |
|
270 } |
|
271 |
|
272 case EGetListOfWindowGroups: |
|
273 { |
|
274 if (*iWgIdArray == -1) // uninitialized |
|
275 { |
|
276 CCoeEnv::Static()->RootWin().EnableGroupListChangeEvents(); |
|
277 UpdateWgListL(); |
|
278 } |
|
279 |
|
280 if (*iWgIdArray != 0) |
|
281 { // updated array exists, return it |
|
282 CompleteWgListMessage(aMessage, aReplySlot); |
|
283 } |
|
284 else |
|
285 { // let messages wait for updates |
|
286 iWgMessage = aMessage; |
|
287 iWgReplySlot = aReplySlot; |
|
288 } |
|
289 |
|
290 return; // message completed asynchronously |
|
291 } |
|
292 |
|
293 |
|
294 default: |
|
295 { |
|
296 err = KErrNotSupported; |
|
297 break; |
|
298 } |
|
299 } |
|
300 aMessage.Complete(err); |
|
301 } |
|
302 |
|
303 TPtrC8 StartL(const TDesC8&) |
|
304 { |
|
305 return KNullDesC8(); |
|
306 } |
|
307 |
|
308 MEikSrvNotifierBase2::TNotifierInfo Info() const |
|
309 { |
|
310 return iInfo; |
|
311 } |
|
312 |
|
313 MEikSrvNotifierBase2::TNotifierInfo RegisterL() |
|
314 { |
|
315 return iInfo; |
|
316 } |
|
317 |
|
318 void Release() |
|
319 { |
|
320 delete this; |
|
321 } |
|
322 |
|
323 void UpdateWgListL() |
|
324 { |
|
325 TInt wgId=0; |
|
326 const TInt count=iWsSession.NumWindowGroups(); |
|
327 if (count) |
|
328 { |
|
329 TInt* ptr = iWgIdArray; |
|
330 Mem::FillZ(iWgIdArray,160); |
|
331 CArrayFixFlat<TInt>* wgIdArray=new(ELeave) CArrayFixFlat<TInt>(count); |
|
332 CleanupStack::PushL(wgIdArray); |
|
333 CApaWindowGroupName* wgName=CApaWindowGroupName::NewL(iWsSession); |
|
334 CleanupStack::PushL(wgName); |
|
335 User::LeaveIfError(iWsSession.WindowGroupList(wgIdArray)); // all groups |
|
336 iWgEntriesWritten = 0; |
|
337 for (TInt ii=0; ii < count-1; ii++) |
|
338 { |
|
339 wgId=(*wgIdArray)[ii]; |
|
340 wgName->ConstructFromWgIdL(wgId); |
|
341 if(!wgName->Hidden() && wgName->AppUid().iUid) // lets skip the hidden groups and groups w/o AppUid at the time being |
|
342 { |
|
343 *ptr = wgId; |
|
344 ptr++; |
|
345 *ptr = wgName->AppUid().iUid; |
|
346 ptr++; |
|
347 iWgEntriesWritten++; |
|
348 } |
|
349 if (iWgEntriesWritten == 20) // magic, interim patch until we have better way to pair wg ids & clien app uids |
|
350 { |
|
351 break; |
|
352 } |
|
353 } |
|
354 CleanupStack::PopAndDestroy(2); // wgIdArray, wgName |
|
355 if (iWgIdArray[0] && !iWgMessage.IsNull()) |
|
356 { |
|
357 CompleteWgListMessage(iWgMessage, iWgReplySlot); |
|
358 } |
|
359 } |
|
360 } |
|
361 |
|
362 void CompleteWgListMessage(const RMessagePtr2& aMessage, TInt aReplySlot) |
|
363 { |
|
364 if (Mem::Compare((TUint8*)iWgIdArray, 8*iWgEntriesWritten, (TUint8*)iWgIdArray2,8*iWgEntriesWritten)) |
|
365 { |
|
366 TPtrC8 ret((TUint8*)iWgIdArray, 160); |
|
367 if (!aMessage.IsNull()) |
|
368 { |
|
369 TInt err = aMessage.Write(aReplySlot, ret); |
|
370 aMessage.Complete(err); |
|
371 } |
|
372 Mem::Copy((TUint8*)iWgIdArray2, (TUint8*)iWgIdArray,160); |
|
373 } |
|
374 Mem::FillZ(iWgIdArray, 160); |
|
375 } |
|
376 |
|
377 private: |
|
378 MEikSrvNotifierBase2::TNotifierInfo iInfo; |
|
379 CFbsBitmap* iBitmap; |
|
380 CFbsBitmap* iTempSkinBmp; |
|
381 CFbsBitmap* iTempMaskBmp; |
|
382 CAknsBasicBackgroundControlContext* iSkinControlContext; |
|
383 TInt iWgIdArray[40]; // magic, cool |
|
384 TInt iWgIdArray2[40]; // magic, cool |
|
385 RMessagePtr2 iWgMessage; |
|
386 TInt iWgReplySlot; |
|
387 RWsSession& iWsSession; |
|
388 TUint iWgEntriesWritten; |
|
389 RMessagePtr2 iLayoutMirroredMessage; |
|
390 TBool iLayoutMirrored; |
|
391 TBool iLayoutMirroredUpdated; |
|
392 }; |
|
393 |
|
394 CArrayPtr<MEikSrvNotifierBase2>* NotifierArray() |
|
395 { |
|
396 CArrayPtrFlat<MEikSrvNotifierBase2>* array = new CArrayPtrFlat<MEikSrvNotifierBase2>(1); |
|
397 if ( array ) |
|
398 { |
|
399 CAlfAppFwNotifier* notif = new CAlfAppFwNotifier(TUid::Uid(KAlfAppFwProxyUid),TUid::Uid(KAlfAppFwProxyUid), MEikSrvNotifierBase2::ENotifierPriorityHigh); |
|
400 if ( notif ) |
|
401 { |
|
402 TRAP_IGNORE(array->AppendL(notif)); // we have reserver granularity of one already |
|
403 } |
|
404 } |
|
405 return array; |
|
406 } |
|
407 |
|
408 |
|
409 const TImplementationProxy ImplementationTable[] = |
|
410 { |
|
411 IMPLEMENTATION_PROXY_ENTRY(KAlfAppFwProxyUid,NotifierArray) |
|
412 }; |
|
413 |
|
414 EXPORT_C const TImplementationProxy* ImplementationGroupProxy(TInt& aTableCount) |
|
415 { |
|
416 aTableCount = sizeof(ImplementationTable) / sizeof(TImplementationProxy) ; |
|
417 return ImplementationTable; |
|
418 } |
|
419 |
|
420 // end of file |