better definition of intent filters to open from file managers

This commit is contained in:
Dominik 2012-09-12 16:03:39 +02:00
parent b9abe386cd
commit 511cc4af9f
5 changed files with 130 additions and 97 deletions

View file

@ -18,10 +18,31 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android" <manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="org.thialfihar.android.apg" package="org.thialfihar.android.apg"
android:installLocation="auto" android:installLocation="auto"
android:versionCode="50" android:versionCode="20000"
android:versionName="2.0" > android:versionName="2.0" >
<!-- APG 2 starting with versionCode 50! --> <!--
General remarks
===============
- APG 2 starting with versionCode 20000!
Registration of APG to file types
=================================
General remarks about file ending conventions:
- *.gpg for binary files
- *.asc for ascii armored files
The actual content can be anything.
The file ending only shows if it is binary or ascii encoded.
Remarks about the ugly android:pathPattern:
We are matching all files with a specific file ending.
This is done in an ugly way because of Android limitations.
Read http://stackoverflow.com/questions/1733195/android-intent-filter-for-a-particular-file-extension
and http://stackoverflow.com/questions/3400072/pathpattern-to-match-file-extension-does-not-work-if-a-period-exists-elsewhere-i/8599921
for more information.
-->
<uses-sdk <uses-sdk
android:minSdkVersion="7" android:minSdkVersion="7"
@ -67,6 +88,55 @@
<intent-filter> <intent-filter>
<action android:name="android.intent.action.SEARCH" /> <action android:name="android.intent.action.SEARCH" />
</intent-filter> </intent-filter>
<intent-filter android:label="@string/intent_import_key" >
<action android:name="org.thialfihar.android.apg.intent.IMPORT" />
<category android:name="android.intent.category.DEFAULT" />
<data android:mimeType="*/*" />
</intent-filter>
<intent-filter android:label="@string/intent_import_key" >
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:host="*" />
<data android:scheme="file" />
<data android:scheme="content" />
<data android:mimeType="*/*" />
<data android:pathPattern=".*\\.gpg" />
<data android:pathPattern=".*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
</intent-filter>
<intent-filter android:label="@string/intent_import_key" >
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:host="*" />
<data android:scheme="file" />
<data android:scheme="content" />
<data android:mimeType="*/*" />
<data android:pathPattern=".*\\.asc" />
<data android:pathPattern=".*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.asc" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.asc" />
</intent-filter>
<meta-data <meta-data
android:name="android.app.searchable" android:name="android.app.searchable"
@ -168,23 +238,7 @@
<data android:mimeType="*/*" /> <data android:mimeType="*/*" />
</intent-filter> </intent-filter>
<intent-filter android:label="@string/intent_decrypt_file" >
<!--
General remarks about file ending conventions:
- *.gpg for binary files
- *.asc for ascii armored files
The actual content can be anything.
The file ending only shows if it is binary or ascii encoded.
Remarks about the ugly android:pathPattern:
We are matching all files with a specific file ending.
This is done in an ugly way because of Android limitations.
Read http://stackoverflow.com/questions/1733195/android-intent-filter-for-a-particular-file-extension
and http://stackoverflow.com/questions/3400072/pathpattern-to-match-file-extension-does-not-work-if-a-period-exists-elsewhere-i/8599921
for more information.
-->
<intent-filter>
<action android:name="android.intent.action.VIEW" /> <action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.DEFAULT" />
@ -205,7 +259,7 @@
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" /> <data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" /> <data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.gpg" />
</intent-filter> </intent-filter>
<intent-filter> <intent-filter android:label="@string/intent_decrypt_file" >
<action android:name="android.intent.action.VIEW" /> <action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.DEFAULT" />
@ -227,47 +281,6 @@
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.asc" /> <data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\..*\\.asc" />
</intent-filter> </intent-filter>
</activity> </activity>
<!-- <activity -->
<!-- android:name=".deprecated.GeneralActivity" -->
<!-- android:configChanges="orientation|screenSize|keyboardHidden|keyboard" -->
<!-- android:label="@string/app_name" -->
<!-- android:theme="@android:style/Theme.Dialog" > -->
<!-- <intent-filter> -->
<!-- <action android:name="android.intent.action.VIEW" /> -->
<!-- <action android:name="android.intent.action.SEND" /> -->
<!-- <category android:name="android.intent.category.DEFAULT" /> -->
<!-- <data -->
<!-- android:mimeType="*/*" -->
<!-- android:scheme="file" /> -->
<!-- </intent-filter> -->
<!-- <intent-filter> -->
<!-- <action android:name="android.intent.action.VIEW" /> -->
<!-- <action android:name="android.intent.action.SEND" /> -->
<!-- <category android:name="android.intent.category.DEFAULT" /> -->
<!-- </intent-filter> -->
<!-- <intent-filter> -->
<!-- <action android:name="android.intent.action.VIEW" /> -->
<!-- <action android:name="android.intent.action.SEND" /> -->
<!-- <category android:name="android.intent.category.DEFAULT" /> -->
<!-- <data -->
<!-- android:mimeType="text/*" -->
<!-- android:scheme="" /> -->
<!-- </intent-filter> -->
<!-- </activity> -->
<activity
android:name=".ui.MailListActivity"
android:configChanges="orientation|screenSize|keyboardHidden|keyboard"
android:label="@string/title_mailInbox" />
<activity <activity
android:name=".ui.KeyServerQueryActivity" android:name=".ui.KeyServerQueryActivity"
android:configChanges="orientation|screenSize|keyboardHidden|keyboard" android:configChanges="orientation|screenSize|keyboardHidden|keyboard"
@ -301,6 +314,11 @@
<service android:name=".service.PassphraseCacheService" /> <service android:name=".service.PassphraseCacheService" />
<service android:name=".service.ApgService" /> <service android:name=".service.ApgService" />
<provider
android:name=".provider.DataProvider"
android:authorities="org.thialfihar.android.apg.provider"
android:readPermission="org.thialfihar.android.apg.permission.READ_KEY_DETAILS" />
<!-- TODO: need to be moved into new service model --> <!-- TODO: need to be moved into new service model -->
<service <service
android:name=".deprecated.ApgService2" android:name=".deprecated.ApgService2"
@ -317,10 +335,6 @@
android:value="2" /> android:value="2" />
</service> </service>
<provider
android:name=".provider.DataProvider"
android:authorities="org.thialfihar.android.apg.provider"
android:readPermission="org.thialfihar.android.apg.permission.READ_KEY_DETAILS" />
<provider <provider
android:name=".deprecated.ApgServiceBlobProvider" android:name=".deprecated.ApgServiceBlobProvider"
android:authorities="org.thialfihar.android.apg.provider.apgserviceblobprovider" android:authorities="org.thialfihar.android.apg.provider.apgserviceblobprovider"

View file

@ -334,10 +334,15 @@
<string name="help_about_version">Version:</string> <string name="help_about_version">Version:</string>
<!-- Import from QR Code --> <!-- Import from QR Code -->
<string name="import_from_qr_code_import">Import key (only locally)</string> <string name="import_from_qr_code_import">Import key (only locally)</string>
<string name="import_from_qr_code_import_sign_and_upload">Import, Sign, and upload key</string> <string name="import_from_qr_code_import_sign_and_upload">Import, Sign, and upload key</string>
<string name="import_from_qr_code_scan_again">Scan qr code again</string> <string name="import_from_qr_code_scan_again">Scan qr code again</string>
<string name="import_from_qr_code_finish">Finish</string> <string name="import_from_qr_code_finish">Finish</string>
<!-- Intent labels -->
<string name="intent_decrypt_file">APG: Decrypt File</string>
<string name="intent_import_key">APG: Import Key</string>
<string name="intent_send_encrypt">APG: Encrypt</string>
<string name="intent_send_decrypt">APG: Decrypt</string>
</resources> </resources>

View file

@ -251,26 +251,39 @@ public class DecryptActivity extends SherlockFragmentActivity {
mSource.showNext(); mSource.showNext();
} }
boolean decryptImmediately = false;
mIntent = getIntent(); mIntent = getIntent();
// handled separately from other actions as it uses mIntent.setAction()
if (Intent.ACTION_VIEW.equals(mIntent.getAction())) { if (Intent.ACTION_VIEW.equals(mIntent.getAction())) {
Uri uri = mIntent.getData();
try { // TODO: old implementation of ACTION_VIEW. Is this used in K9?
InputStream attachment = getContentResolver().openInputStream(uri);
ByteArrayOutputStream byteOut = new ByteArrayOutputStream(); // Uri uri = mIntent.getData();
byte bytes[] = new byte[1 << 16]; // try {
int length; // InputStream attachment = getContentResolver().openInputStream(uri);
while ((length = attachment.read(bytes)) > 0) { // ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
byteOut.write(bytes, 0, length); // byte bytes[] = new byte[1 << 16];
} // int length;
byteOut.close(); // while ((length = attachment.read(bytes)) > 0) {
String data = new String(byteOut.toByteArray()); // byteOut.write(bytes, 0, length);
mMessage.setText(data); // }
} catch (FileNotFoundException e) { // byteOut.close();
// ignore, then // String data = new String(byteOut.toByteArray());
} catch (IOException e) { // mMessage.setText(data);
// ignore, then // } catch (FileNotFoundException e) {
} // // ignore, then
} else if (ACTION_DECRYPT.equals(mIntent.getAction())) { // } catch (IOException e) {
// // ignore, then
// }
// same as ACTION_DECRYPT_FILE but decrypt it immediately
mIntent.setAction(ACTION_DECRYPT_FILE);
decryptImmediately = true;
}
if (ACTION_DECRYPT.equals(mIntent.getAction())) {
Log.d(Constants.TAG, "Apg Intent DECRYPT startet"); Log.d(Constants.TAG, "Apg Intent DECRYPT startet");
Bundle extras = mIntent.getExtras(); Bundle extras = mIntent.getExtras();
if (extras == null) { if (extras == null) {
@ -317,10 +330,7 @@ public class DecryptActivity extends SherlockFragmentActivity {
mReplyTo = extras.getString(EXTRA_REPLY_TO); mReplyTo = extras.getString(EXTRA_REPLY_TO);
mSubject = extras.getString(EXTRA_SUBJECT); mSubject = extras.getString(EXTRA_SUBJECT);
} else if (ACTION_DECRYPT_FILE.equals(mIntent.getAction())) { } else if (ACTION_DECRYPT_FILE.equals(mIntent.getAction())) {
mInputFilename = mIntent.getDataString(); mInputFilename = mIntent.getData().getPath();
if ("file".equals(mIntent.getScheme())) {
mInputFilename = Uri.decode(mInputFilename.substring(7));
}
mFilename.setText(mInputFilename); mFilename.setText(mInputFilename);
guessOutputFilename(); guessOutputFilename();
mSource.setInAnimation(null); mSource.setInAnimation(null);
@ -420,8 +430,9 @@ public class DecryptActivity extends SherlockFragmentActivity {
updateSource(); updateSource();
if (mSource.getCurrentView().getId() == R.id.sourceMessage if (decryptImmediately
&& (mMessage.getText().length() > 0 || mData != null || mContentUri != null)) { || (mSource.getCurrentView().getId() == R.id.sourceMessage && (mMessage.getText()
.length() > 0 || mData != null || mContentUri != null))) {
decryptClicked(); decryptClicked();
} }
} }

View file

@ -432,11 +432,9 @@ public class EncryptActivity extends SherlockFragmentActivity {
mSource.showNext(); mSource.showNext();
} }
} else if (ACTION_ENCRYPT_FILE.equals(mIntent.getAction())) { } else if (ACTION_ENCRYPT_FILE.equals(mIntent.getAction())) {
if ("file".equals(mIntent.getScheme())) { mInputFilename = mIntent.getData().getPath();
mInputFilename = Uri.decode(mIntent.getDataString().replace("file://", "")); mFilename.setText(mInputFilename);
mFilename.setText(mInputFilename); guessOutputFilename();
guessOutputFilename();
}
mSource.setInAnimation(null); mSource.setInAnimation(null);
mSource.setOutAnimation(null); mSource.setOutAnimation(null);
while (mSource.getCurrentView().getId() != R.id.sourceFile) { while (mSource.getCurrentView().getId() != R.id.sourceFile) {

View file

@ -44,7 +44,6 @@ import android.content.Intent;
import android.database.Cursor; import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteQueryBuilder; import android.database.sqlite.SQLiteQueryBuilder;
import android.net.Uri;
import android.os.Bundle; import android.os.Bundle;
import android.os.Handler; import android.os.Handler;
import android.os.Message; import android.os.Message;
@ -143,9 +142,15 @@ public class KeyListActivity extends SherlockFragmentActivity {
mListAdapter = new KeyListAdapter(this, searchString); mListAdapter = new KeyListAdapter(this, searchString);
mList.setAdapter(mListAdapter); mList.setAdapter(mListAdapter);
// handled separately from other actions as it uses intent.setAction()
if (Intent.ACTION_VIEW.equals(intent.getAction())) {
// same as ACTION_IMPORT invoked from a file manager
intent.setAction(ACTION_IMPORT);
}
if (ACTION_IMPORT.equals(intent.getAction())) { if (ACTION_IMPORT.equals(intent.getAction())) {
if ("file".equals(intent.getScheme()) && intent.getDataString() != null) { if ("file".equals(intent.getScheme()) && intent.getDataString() != null) {
mImportFilename = Uri.decode(intent.getDataString().replace("file://", "")); mImportFilename = intent.getData().getPath();
} else { } else {
mImportData = intent.getStringExtra(EXTRA_TEXT); mImportData = intent.getStringExtra(EXTRA_TEXT);
} }