2 ** |
2 ** |
3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). |
3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). |
4 ** All rights reserved. |
4 ** All rights reserved. |
5 ** Contact: Nokia Corporation (qt-info@nokia.com) |
5 ** Contact: Nokia Corporation (qt-info@nokia.com) |
6 ** |
6 ** |
7 ** This file is part of the QtGui of the Qt Toolkit. |
7 ** This file is part of the QtGui module of the Qt Toolkit. |
8 ** |
8 ** |
9 ** $QT_BEGIN_LICENSE:LGPL$ |
9 ** $QT_BEGIN_LICENSE:LGPL$ |
10 ** No Commercial Usage |
10 ** No Commercial Usage |
11 ** This file contains pre-release code and may not be distributed. |
11 ** This file contains pre-release code and may not be distributed. |
12 ** You may use this file in accordance with the terms and conditions |
12 ** You may use this file in accordance with the terms and conditions |
39 ** |
39 ** |
40 ****************************************************************************/ |
40 ****************************************************************************/ |
41 |
41 |
42 // This flag changes the implementation to use S60 CDcoumentHandler |
42 // This flag changes the implementation to use S60 CDcoumentHandler |
43 // instead of apparch when opening the files |
43 // instead of apparch when opening the files |
44 #undef USE_DOCUMENTHANDLER |
44 #define USE_DOCUMENTHANDLER |
45 |
45 |
46 #include <qcoreapplication.h> |
46 #include <qcoreapplication.h> |
47 #include <qdir.h> |
47 #include <qdir.h> |
48 #include <qurl.h> |
48 #include <qurl.h> |
49 #include <private/qcore_symbian_p.h> |
49 #include <private/qcore_symbian_p.h> |
62 #include <apgtask.h> // TApaTaskList, TApaTask |
62 #include <apgtask.h> // TApaTaskList, TApaTask |
63 #include <rsendas.h> // RSendAs |
63 #include <rsendas.h> // RSendAs |
64 #include <rsendasmessage.h> // RSendAsMessage |
64 #include <rsendasmessage.h> // RSendAsMessage |
65 |
65 |
66 #ifdef Q_WS_S60 |
66 #ifdef Q_WS_S60 |
67 # include <pathinfo.h> // PathInfo |
67 # include <pathinfo.h> // PathInfo |
68 # ifdef USE_DOCUMENTHANDLER |
68 # ifdef USE_DOCUMENTHANDLER |
69 # include <documenthandler.h> // CDocumentHandler |
69 # include <documenthandler.h> // CDocumentHandler |
|
70 # include <aknserverapp.h> |
70 # endif |
71 # endif |
71 #elif defined(USE_DOCUMENTHANDLER) |
72 #else |
72 # error CDocumentHandler requires support for S60 |
73 # warning CDocumentHandler requires support for S60 |
|
74 # undef USE_DOCUMENTHANDLER // Fallback to RApaLsSession based implementation |
73 #endif |
75 #endif |
74 |
76 |
75 QT_BEGIN_NAMESPACE |
77 QT_BEGIN_NAMESPACE |
76 |
78 |
77 _LIT(KCacheSubDir, "Cache\\"); |
79 _LIT(KCacheSubDir, "Cache\\"); |
98 QAutoClose(const QAutoClose&); |
100 QAutoClose(const QAutoClose&); |
99 QAutoClose& operator=(const QAutoClose&); |
101 QAutoClose& operator=(const QAutoClose&); |
100 private: |
102 private: |
101 R* mPtr; |
103 R* mPtr; |
102 }; |
104 }; |
|
105 |
|
106 #ifdef USE_DOCUMENTHANDLER |
|
107 class QS60DocumentHandler : public MAknServerAppExitObserver |
|
108 { |
|
109 public: |
|
110 QS60DocumentHandler() :docHandler(0) {} |
|
111 |
|
112 ~QS60DocumentHandler() { |
|
113 delete docHandler; |
|
114 } |
|
115 |
|
116 CDocumentHandler& documentHandler() { |
|
117 // In case user calls openUrl twice subsequently, before the first embedded app is closed |
|
118 // we use the same CDocumentHandler instance. Using same instance makes sure the first |
|
119 // launched embedded app is closed and latter one gets embedded to our app. |
|
120 // Using different instance would help only theoretically since user cannot interact with |
|
121 // several embedded apps at the same time. |
|
122 if(!docHandler) { |
|
123 QT_TRAP_THROWING(docHandler = CDocumentHandler::NewL()); |
|
124 docHandler->SetExitObserver(this); |
|
125 } |
|
126 return *docHandler; |
|
127 } |
|
128 |
|
129 private: // From MAknServerAppExitObserver |
|
130 void HandleServerAppExit(TInt /*aReason*/) { |
|
131 delete docHandler; |
|
132 docHandler = 0; |
|
133 } |
|
134 |
|
135 private: |
|
136 CDocumentHandler* docHandler; |
|
137 }; |
|
138 Q_GLOBAL_STATIC(QS60DocumentHandler, qt_s60_documenthandler); |
|
139 #endif |
|
140 |
103 |
141 |
104 static void handleMailtoSchemeLX(const QUrl &url) |
142 static void handleMailtoSchemeLX(const QUrl &url) |
105 { |
143 { |
106 // this function has many intermingled leaves and throws. Qt and Symbian objects do not have |
144 // this function has many intermingled leaves and throws. Qt and Symbian objects do not have |
107 // destructor dependencies, and cleanup object is used to prevent cleanup stack dependency on stack. |
145 // destructor dependencies, and cleanup object is used to prevent cleanup stack dependency on stack. |
268 User::LeaveIfError(appArcSession.StartDocument(aUrl, id, |
306 User::LeaveIfError(appArcSession.StartDocument(aUrl, id, |
269 RApaLsSession::ESwitchFiles)); // ELaunchNewApp |
307 RApaLsSession::ESwitchFiles)); // ELaunchNewApp |
270 CleanupStack::PopAndDestroy(); // appArcSession |
308 CleanupStack::PopAndDestroy(); // appArcSession |
271 #else |
309 #else |
272 // This is an alternative way to launch app associated to MIME type |
310 // This is an alternative way to launch app associated to MIME type |
273 // CDocumentHandler would support opening apps in embedded mode, |
311 // CDocumentHandler also supports opening apps in embedded mode. |
274 // but our Qt application window group seems to always get switched on top of embedded one |
|
275 // -> Cannot use menus etc of embedded app -> used |
|
276 |
|
277 CDocumentHandler* docHandler = CDocumentHandler::NewLC(); |
|
278 TDataType temp; |
312 TDataType temp; |
279 //Standalone file opening fails for some file-types at least in S60 3.1 emulator |
313 qt_s60_documenthandler()->documentHandler().OpenFileEmbeddedL(aUrl, temp); |
280 //For example .txt file fails with KErrAlreadyInUse and music files with KERN-EXEC 0 |
|
281 //Workaround is to use OpenFileEmbeddedL |
|
282 //docHandler->OpenFileL(aUrl, temp); |
|
283 |
|
284 // Opening file with CDocumentHandler will leave if file does not exist |
|
285 // Leave is trapped in openDocument and false returned to user. |
|
286 docHandler->OpenFileEmbeddedL(aUrl, temp); |
|
287 CleanupStack::PopAndDestroy(docHandler); |
|
288 #endif |
314 #endif |
289 } |
315 } |
290 |
316 |
291 #ifdef USE_SCHEMEHANDLER |
317 #ifdef USE_SCHEMEHANDLER |
292 // The schemehandler component only exist in private SDK. This implementation |
318 // The schemehandler component only exist in private SDK. This implementation |
353 |
379 |
354 switch (type) { |
380 switch (type) { |
355 case DesktopLocation: |
381 case DesktopLocation: |
356 qWarning("No desktop concept in Symbian OS"); |
382 qWarning("No desktop concept in Symbian OS"); |
357 // But lets still use some feasible default |
383 // But lets still use some feasible default |
358 path.Append(writableDataRoot()); |
384 path.Append(writableDataRoot()); |
359 break; |
385 break; |
360 case DocumentsLocation: |
386 case DocumentsLocation: |
361 path.Append(writableDataRoot()); |
387 path.Append(writableDataRoot()); |
362 break; |
388 break; |
363 case FontsLocation: |
389 case FontsLocation: |
398 break; |
424 break; |
399 case CacheLocation: |
425 case CacheLocation: |
400 CEikonEnv::Static()->FsSession().PrivatePath(path); |
426 CEikonEnv::Static()->FsSession().PrivatePath(path); |
401 path.Insert(0, writableExeDrive().Name()); |
427 path.Insert(0, writableExeDrive().Name()); |
402 path.Append(KCacheSubDir); |
428 path.Append(KCacheSubDir); |
403 break; |
429 break; |
404 default: |
430 default: |
405 // Lets use feasible default |
431 // Lets use feasible default |
406 path.Append(writableDataRoot()); |
432 path.Append(writableDataRoot()); |
407 break; |
433 break; |
408 } |
434 } |
409 |
435 |
410 // Convert to cross-platform format and clean the path |
436 // Convert to cross-platform format and clean the path |
411 QString nativePath = QString::fromUtf16(path.Ptr(), path.Length()); |
437 QString nativePath = QString::fromUtf16(path.Ptr(), path.Length()); |