ฉันต้องการดาวน์โหลดไฟล์ที่มีนามสกุลเฉพาะจาก 'net และส่งผ่านไปยังแอปพลิเคชันของฉันเพื่อจัดการกับมัน แต่ฉันไม่สามารถหาตัวกรองความตั้งใจได้ ประเภทไฟล์ไม่รวมอยู่ในประเภทไฟล์และฉันลองใช้
<data android:path="*.ext" />
แต่ฉันไม่สามารถทำงานนั้นได้
ฉันต้องการดาวน์โหลดไฟล์ที่มีนามสกุลเฉพาะจาก 'net และส่งผ่านไปยังแอปพลิเคชันของฉันเพื่อจัดการกับมัน แต่ฉันไม่สามารถหาตัวกรองความตั้งใจได้ ประเภทไฟล์ไม่รวมอยู่ในประเภทไฟล์และฉันลองใช้
<data android:path="*.ext" />
แต่ฉันไม่สามารถทำงานนั้นได้
คำตอบ:
นี่คือวิธีที่ฉันกำหนดกิจกรรมของฉันใน AndroidManifest.xml เพื่อให้สิ่งนี้ใช้งานได้
<activity android:name="com.keepassdroid.PasswordActivity">
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="file" />
<data android:mimeType="*/*" />
<data android:pathPattern=".*\\.kdb" />
<data android:host="*" />
</intent-filter>
</activity>
scheme
ของfile
บ่งบอกว่านี่ควรจะเกิดขึ้นเมื่อไฟล์ถูกเปิดท้องถิ่น (แทนที่จะโปรโตคอลเช่น HTTP)
mimeType
สามารถตั้งค่า*/*
ให้ตรงกับประเภทละครใบ้ใดก็ได้
pathPattern
เป็นที่ที่คุณระบุส่วนขยายที่คุณต้องการจับคู่ (ในตัวอย่างนี้.kdb
) .*
ที่จุดเริ่มต้นตรง squence ของตัวละครใด ๆ สตริงเหล่านี้ต้องการการหลีกเลี่ยงสองครั้งดังนั้นจึง\\\\.
ตรงกับช่วงเวลาที่แท้จริง จากนั้นปิดท้ายด้วยนามสกุลไฟล์ของคุณ ข้อแม้อย่างหนึ่งของ pathPattern คือนั่น.*
ไม่ใช่การจับคู่แบบโลภอย่างที่คุณคาดหวังหากเป็นนิพจน์ทั่วไป รูปแบบนี้จะไม่สามารถจับคู่เส้นทางที่มี.
ก่อนหน้า.kdb
. หากต้องการทราบรายละเอียดเพิ่มเติมเกี่ยวกับปัญหานี้และวิธีแก้ไขปัญหาโปรดดูที่นี่
สุดท้ายตามเอกสารของ Android จำเป็นต้องใช้ทั้งสองhost
และscheme
แอตทริบิวต์เพื่อให้pathPattern
แอตทริบิวต์ทำงานได้ดังนั้นเพียงตั้งค่าให้สัญลักษณ์แทนเพื่อให้ตรงกับสิ่งใด ๆ
ตอนนี้ถ้าคุณเลือก.kdb
ไฟล์ในแอพเช่น Linda File Manager แอพของฉันจะแสดงเป็นตัวเลือก ฉันควรทราบว่าสิ่งนี้เพียงอย่างเดียวไม่อนุญาตให้คุณดาวน์โหลดประเภทไฟล์นี้ในเบราว์เซอร์เนื่องจากสิ่งนี้จะลงทะเบียนกับรูปแบบไฟล์เท่านั้น การมีแอปอย่าง Linda File Manager บนโทรศัพท์ของคุณจะเป็นการรีสตาร์ทตัวเองโดยทั่วไปทำให้คุณสามารถดาวน์โหลดไฟล์ประเภทใดก็ได้
.kdbx
ส่วนขยายเพื่อให้ ES file explorer เปิดไฟล์ kdbx เมื่อฉันถูกชี้ไปที่โพสต์นี้ เห็นได้ชัดว่าหาก Intent มีประเภท MIME ว่างเปล่าตัวกรอง Intent นี้จะไม่ทำงาน !! นอกจากนี้ยังเป็นไปได้ที่จะมี Intent โดยใช้สตริง EMPTY เป็นตัวดำเนินการและเป็นเพียง URI Google เอกสารตอบสนองต่อเจตนานั้นดังนั้นจึงต้องถูกต้อง
<data>
แท็กที่มีแอตทริบิวต์ 4 รายการ การมี 4 แท็กนั้นเป็นตรรกะหรือ - ซึ่งใช้ได้กับ Android 2 - แต่ Android 4 นั้นเข้มงวดกว่า ดูstackoverflow.com/questions/20650378/…
\\\\.
ตรงกับช่วงเวลาตามตัวอักษรทำไมคุณไม่ใช้มันเพื่อสร้าง.kdb
ส่วนขยายเช่นนี้: \\\\.kdb
?
มีข้อมูลที่ผิดมากมายในหัวข้อนี้ไม่น้อยจากเอกสารของ Google เอง สิ่งที่ดีที่สุดและด้วยตรรกะที่แปลกอาจเป็นไปได้ว่าเอกสารจริงเพียงอย่างเดียวคือซอร์สโค้ด
การใช้ตัวกรองความตั้งใจมีตรรกะที่เกือบจะขัดต่อคำอธิบาย รหัสแยกวิเคราะห์เป็นชิ้นอื่น ๆ ที่เกี่ยวข้องของปริศนา
ตัวกรองต่อไปนี้ค่อนข้างใกล้เคียงกับพฤติกรรมที่สมเหตุสมผล รูปแบบเส้นทางใช้สำหรับความ"file"
ตั้งใจของโครงการ
การจับคู่รูปแบบประเภท mime ส่วนกลางจะจับคู่ทุกประเภทตราบเท่าที่นามสกุลไฟล์ตรงกัน สิ่งนี้ไม่สมบูรณ์แบบ แต่เป็นวิธีเดียวที่จะจับคู่ลักษณะการทำงานของตัวจัดการไฟล์เช่น ES File Explorer และ จำกัด เฉพาะ Intent ที่ URI / นามสกุลไฟล์ตรงกัน
ฉันไม่ได้รวมรูปแบบอื่น ๆ เช่น"http"
ที่นี่ แต่อาจใช้งานได้ดีกับตัวกรองเหล่านี้ทั้งหมด
โครงร่างแปลก ๆ คือ"content"
ส่วนขยายที่ไม่สามารถใช้ได้กับตัวกรอง แต่ตราบใดที่ผู้ให้บริการระบุประเภท MIME ของคุณ (เช่น Gmail จะส่งต่อประเภท MIME สำหรับไฟล์แนบโดยไม่มีข้อ จำกัด ) ตัวกรองจะตรงกัน
Gotchas ที่ต้องระวัง:
scheme
และhost
จะต้องมีการระบุไว้สำหรับpath
กฎระเบียบในการแข่งขัน (ตรงกันข้ามกับคู่มือ API ของ Google ในปัจจุบัน)""
ซึ่งถูกกรองแตกต่างกันมากจนnull
ไม่สามารถจับคู่ได้อย่างชัดเจนและสามารถจับคู่ได้โดย"*/*"
ตัวกรองที่มีความเสี่ยงเท่านั้น"*/*"
กรองจะไม่ตรงกับเจตจำนงกับnull
ชนิดไมม์ - ที่ต้องมีการกรองแยกต่างหากสำหรับกรณีนี้โดยเฉพาะไม่มีชนิดไมม์ที่ทั้งหมด"content"
โครงการเท่านั้นที่สามารถจับคู่โดยชนิดไมม์เพราะชื่อไฟล์เดิมไม่สามารถใช้ได้ในเจตนา (อย่างน้อยกับ Gmail)"data"
องค์ประกอบที่แยกจากกันนั้น (เกือบ) ไม่เกี่ยวข้องกับการตีความโดยมีข้อยกเว้นเฉพาะhost
และport
- ซึ่งจับคู่กัน อย่างอื่นไม่มีการเชื่อมโยงเฉพาะภายใน"data"
องค์ประกอบหรือระหว่าง"data"
องค์ประกอบเมื่อคำนึงถึงสิ่งเหล่านี้แล้วนี่คือตัวอย่างพร้อมความคิดเห็น:
<!--
Capture content by MIME type, which is how Gmail broadcasts
attachment open requests. pathPattern and file extensions
are ignored, so the MIME type *MUST* be explicit, otherwise
we will match absolutely every file opened.
-->
<intent-filter
android:icon="@drawable/icon"
android:label="@string/app_name"
android:priority="50" >
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.BROWSABLE" />
<category android:name="android.intent.category.DEFAULT" />
<data android:scheme="file" />
<data android:scheme="content" />
<data android:mimeType="application/vnd.my-type" />
</intent-filter>
<!--
Capture file open requests (pathPattern is honoured) where no
MIME type is provided in the Intent. An Intent with a null
MIME type will never be matched by a filter with a set MIME
type, so we need a second intent-filter if we wish to also
match files with this extension and a non-null MIME type
(even if it is non-null but zero length).
-->
<intent-filter
android:icon="@drawable/icon"
android:label="@string/app_name"
android:priority="50" >
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.BROWSABLE" />
<category android:name="android.intent.category.DEFAULT" />
<data android:scheme="file" />
<data android:host="*" />
<!--
Work around Android's ugly primitive PatternMatcher
implementation that can't cope with finding a . early in
the path unless it's explicitly matched.
-->
<data android:pathPattern=".*\\.my-ext" />
<data android:pathPattern=".*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\.my-ext" />
</intent-filter>
<!--
Capture file open requests (pathPattern is honoured) where a
(possibly blank) MIME type is provided in the Intent. This
filter may only be necessary for supporting ES File Explorer,
which has the probably buggy behaviour of using an Intent
with a MIME type that is set but zero-length. It's
impossible to match such a type except by using a global
wildcard.
-->
<intent-filter
android:icon="@drawable/icon"
android:label="@string/app_name"
android:priority="50" >
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.BROWSABLE" />
<category android:name="android.intent.category.DEFAULT" />
<data android:scheme="file" />
<data android:host="*" />
<data android:mimeType="*/*" />
<!--
Work around Android's ugly primitive PatternMatcher
implementation that can't cope with finding a . early in
the path unless it's explicitly matched.
-->
<data android:pathPattern=".*\\.my-ext" />
<data android:pathPattern=".*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\.my-ext" />
<data android:pathPattern=".*\\..*\\..*\\..*\\..*\\..*\\..*\\.my-ext" />
</intent-filter>
<data android:mimeType="*/*" />
ทั้งสามตัวเลือกและมันก็ใช้งานได้ดีสำหรับทุกแอปรวมถึง Google Drive และ Gmail
ฉันต้องยอมรับว่างานง่าย ๆ ในการเปิดไฟล์แนบจากอีเมลและไฟล์จากระบบไฟล์บน Android เป็นหนึ่งในประสบการณ์ที่น่าตื่นเต้นกว่าที่เคยมีมา ง่ายต่อการจัดการไฟล์จำนวนมากเกินไปหรือน้อยเกินไป แต่การทำให้ถูกต้องเป็นเรื่องยาก วิธีแก้ปัญหาส่วนใหญ่ที่โพสต์บน stackoverflow ทำงานไม่ถูกต้องสำหรับฉัน
ความต้องการของฉันคือ:
วิธีที่ดีที่สุดในการทำงานนี้คือการระบุประเภท MIME ที่กำหนดเองสำหรับไฟล์แนบของคุณ และคุณอาจเลือกที่จะมีนามสกุลไฟล์ที่กำหนดเอง สมมติว่าแอปของเรามีชื่อว่า "Cool App" และเราสร้างไฟล์แนบที่มี ".cool" ต่อท้าย
นี่เป็นสิ่งที่ใกล้เคียงที่สุดที่ฉันไปถึงเป้าหมายและมันได้ผล ... น่าพอใจ
<!-- Register to handle email attachments -->
<!-- WARNING: Do NOT use android:host="*" for these as they will not work properly -->
<intent-filter>
<!-- needed for properly formatted email messages -->
<data
android:scheme="content"
android:mimeType="application/vnd.coolapp"
android:pathPattern=".*\\.cool" />
<!-- needed for mangled email messages -->
<data
android:scheme="content"
android:mimeType="application/coolapp"
android:pathPattern=".*\\.cool" />
<!-- needed for mangled email messages -->
<data
android:scheme="content"
android:mimeType="application/octet-stream"
android:pathPattern=".*\\.cool" />
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
</intent-filter>
<!-- Register to handle file opening -->
<intent-filter>
<data android:scheme="file"
android:mimeType="*/*"
android:pathPattern=".*\\.cool"
android:host="*"/>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
</intent-filter>
หมายเหตุ:
pathPattern
ดูเหมือนว่าจะมากหรือน้อยละเว้นสำหรับสิ่งที่แนบมา (เมื่อใช้android:scheme="content"
) หากใครสักคนได้รับ pathPattern เพื่อตอบสนองต่อรูปแบบบางอย่างเท่านั้นฉันจะตื่นเต้นที่จะได้เห็นวิธีการandroid:host="*"
แอตทริบิวต์intent-filter
รวมบล็อกเหล่านี้แต่ฉันยังไม่ได้ตรวจสอบandroid:scheme="http"
สามารถใช้ได้ โปรดทราบว่าเบราว์เซอร์บางอย่างอาจเลอะandroid:mimeType
เพื่อให้การทดสอบกับandroid:mimeType="*/*"
และตรวจสอบในการดีบักสิ่งที่จะถูกส่งผ่านจริงแล้วกระชับกรองที่จะไม่จบลงด้วยการที่แอปที่น่ารำคาญที่จับทุกอย่างintent-filter
ได้รับการทดสอบด้วยแอป "ไฟล์ของฉัน" ของ Samsung บน Galaxy S3 FX Explorer ยังคงปฏิเสธที่จะเปิดไฟล์อย่างถูกต้องและฉันก็สังเกตว่าไม่มีการใช้ไอคอนแอพสำหรับไฟล์ อีกครั้งหากใครได้รับผลงานโปรดแสดงความคิดเห็นด้านล่างฉันหวังว่าคุณจะพบว่าสิ่งนี้มีประโยชน์และคุณจะไม่ต้องเสียเวลาไปกับการผสมผสานที่เป็นไปได้ทั้งหมด มีพื้นที่สำหรับการปรับปรุงดังนั้นยินดีรับฟังความคิดเห็น
android:label
ตัวกรองความตั้งใจคือสตริงที่ผู้ใช้จะเห็นในเมนูตัวเลือก โดยใช้ชื่อแอปพลิเคชันเริ่มต้น
คำตอบของ Brian ข้างต้นทำให้ฉันได้ 90% ไปที่นั่น เพื่อจบมันออกสำหรับประเภทละครใบ้ที่ฉันใช้
android:mimeType="*/*"
ฉันสงสัยว่าผู้โพสต์ก่อนหน้านี้พยายามโพสต์รายละเอียดแบบเดียวกัน แต่ถ้าขาดการใช้สตาร์สแลชสตาร์เป็นโค้ดแล้วการสแต็กโอเวอร์โฟลว์ก็แสดงให้เห็นว่ามันเป็นเพียงเครื่องหมายทับ
แทนที่จะandroid:path
ลองandroid:mimeType
ใช้ค่าประเภท MIME ของเนื้อหาชิ้นนี้ นอกจากนี้android:path
ไม่ยอมรับสัญลักษณ์แทน - ใช้android:pathPattern
สำหรับสิ่งนั้น
ฉันพยายามทำให้สิ่งนี้ใช้งานได้มานานแล้วและได้ลองใช้วิธีแก้ปัญหาที่แนะนำทั้งหมดโดยพื้นฐานแล้วและยังไม่สามารถให้ Android จดจำนามสกุลไฟล์เฉพาะได้ ฉันมีตัวกรองความตั้งใจด้วย"*/*"
mimetype ซึ่งเป็นสิ่งเดียวที่ดูเหมือนว่าจะใช้งานได้และตอนนี้เบราว์เซอร์ไฟล์แสดงรายการแอปของฉันเป็นตัวเลือกสำหรับการเปิดไฟล์อย่างไรก็ตามแอปของฉันแสดงเป็นตัวเลือกสำหรับการเปิดไฟล์ประเภทใดก็ได้แม้ว่า ฉันได้ระบุนามสกุลไฟล์โดยใช้แท็ก pathPattern สิ่งนี้ไปได้ไกลถึงแม้ในขณะที่ฉันพยายามดู / แก้ไขผู้ติดต่อในรายชื่อผู้ติดต่อของฉัน Android จะถามฉันว่าฉันต้องการใช้แอพของฉันเพื่อดูผู้ติดต่อหรือไม่และนั่นเป็นเพียงหนึ่งในหลาย ๆ สถานการณ์ที่เกิดเหตุการณ์นี้ขึ้นซึ่งน่ารำคาญมาก
ในที่สุดฉันก็พบว่ากลุ่ม Google นี้โพสต์พร้อมคำถามที่คล้ายกันซึ่งวิศวกรกรอบงาน Android ตอบกลับ เธออธิบายว่า Android ไม่รู้อะไรเลยเกี่ยวกับนามสกุลไฟล์มีเพียงประเภท MIME เท่านั้น ( https://groups.google.com/forum/#!topic/android-developers/a7qsSl3vQq0 )
ดังนั้นจากสิ่งที่ฉันได้เห็นลองและอ่าน Android ไม่สามารถแยกความแตกต่างระหว่างนามสกุลไฟล์และแท็ก pathPattern ได้โดยพื้นฐานแล้วเป็นการเสียเวลาและพลังงานอย่างมาก หากคุณโชคดีพอที่ต้องการเพียงไฟล์ประเภทละครใบ้บางประเภท (เช่นข้อความวิดีโอหรือเสียง) คุณสามารถใช้ตัวกรองความตั้งใจกับประเภทละครใบ้ หากคุณต้องการนามสกุลไฟล์เฉพาะหรือประเภทละครใบ้ที่ Android ไม่รู้จักอย่างไรก็ตามคุณก็โชคไม่ดี
หากฉันผิดเกี่ยวกับสิ่งนี้โปรดบอกฉันจนถึงตอนนี้ฉันได้อ่านทุกโพสต์และลองใช้วิธีแก้ปัญหาที่เสนอทั้งหมดที่ฉันพบ แต่ไม่มีใครได้ผล
ฉันสามารถเขียนอีกหนึ่งหน้าหรือสองหน้าเกี่ยวกับความธรรมดาของสิ่งต่างๆเหล่านี้ใน Android และประสบการณ์ของนักพัฒนาซอฟต์แวร์ที่แย่ลง แต่ฉันจะช่วยคุณไม่ให้โกรธ;) หวังว่าฉันจะช่วยใครบางคนได้
Android ได้เปลี่ยนไปใช้ URI ของเนื้อหาและประเภท MIME สำหรับตัวกรองความตั้งใจ
URI เนื้อหาไม่จำเป็นต้องมีนามสกุลหรือชื่อของไฟล์และจะแตกต่างกันระหว่างแอปพลิเคชันต่างๆที่ให้เนื้อหา / ไฟล์
ต่อไปนี้เป็นตัวอย่าง URI ของเนื้อหาจากแอปพลิเคชันอีเมลที่แตกต่างกันสำหรับไฟล์แนบอีเมลเดียวกัน :
Gmail -> content://com.google.android.gm.sapi/some_email@gmail.com/message_attachment_external/%23thread-a%3Ar332738858767305663/%23msg-a%3Ar-5439466788231005876/0.1?account_type=com.google&mimeType=application%2Foctet-stream&rendition=1
Outlook -> content://com.microsoft.office.outlook.fileprovider/outlookfile/data/data/com.microsoft.office.outlook/cache/file-download/file--2146063402/filename.customextention
แอพ Samsung Email -> content://com.samsung.android.email.attachmentprovider/1/1/RAW
ดังที่เห็นได้ว่าแตกต่างกันและไม่รับประกันว่าจะมีสิ่งที่เกี่ยวข้องกับไฟล์จริงของคุณ ดังนั้นคุณไม่สามารถใช้ไฟล์android:pathPattern
เหมือนที่แนะนำมากที่สุด
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<category android:name="android.intent.category.BROWSABLE"/>
<category android:name="android.intent.category.DEFAULT"/>
<data android:scheme="content"/>
<data android:host="*"/>
<!-- Required for Gmail and Samsung Email App -->
<data android:mimeType="application/octet-stream"/>
<!-- Required for Outlook -->
<data android:mimeType="application/my-custom-extension"/>
</intent-filter>
จากการทดสอบฉันพบ MIME-types ที่ Gmail, Outlook และ Samsung Email ใช้และเพิ่มสิ่งเหล่านั้นลงในตัวกรองความตั้งใจของฉัน
ฉันพบว่าด้วยวิธีแก้ปัญหาข้างต้นของฉันหากฉันเปิดไฟล์ใด ๆ ที่เป็นประเภทไบนารีไฟล์นั้นจะเปิดแอปของฉันโดยอัตโนมัติ ฉันจัดการสิ่งนี้ในกิจกรรมของฉันโดยแสดงสถานะล้มเหลวหากเราไม่สามารถแยกวิเคราะห์ไฟล์ได้ ฉันคิดว่านี่เป็นเหตุการณ์ที่ค่อนข้างหายากดังนั้นจึงเป็นเรื่องที่ยอมรับได้
ฉันไม่พบวิธีใด ๆ ในการเปิดแอปของฉันผ่านเบราว์เซอร์ไฟล์โดยไม่ต้องเพิ่ม<data android:mimeType="*/*"/>
ตัวกรองความตั้งใจของฉัน ฉันไม่สามารถใช้สิ่งนี้ได้เพราะมันจะเปิดแอปของฉันทุกครั้งที่ผู้ใช้คลิกไฟล์ใด ๆบนโทรศัพท์ของพวกเขา (ไม่ใช่แค่ไฟล์นามสกุลที่กำหนดเอง) ฉันไม่แนะนำให้เพิ่มสิ่งนี้ในตัวกรองความตั้งใจของคุณ
คำตอบของ Brian นั้นใกล้เคียงมาก แต่นี่เป็นวิธีที่สะอาดและปราศจากข้อผิดพลาดในการเรียกใช้แอปของคุณเมื่อพยายามเปิดไฟล์ที่มีนามสกุลที่คุณกำหนดเอง (ไม่จำเป็นต้องมีแบบแผนหรือโฮสต์):
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:mimeType="*/*" />
<data android:pathPattern="*.*\\.kdb" />
</intent-filter>
<data>
แท็กเดียวที่มีแอตทริบิวต์สี่รายการ โซลูชันของคุณอาจใช้ได้กับ Android 2 - แต่กฎต่างๆเข้มงวดมากขึ้น: stackoverflow.com/questions/20650378/…
host
และscheme
จะต้อง!
ใน Android 4 กฎนั้นเข้มงวดมากขึ้นกว่าที่เคยเป็นมา ใช้:
<data
android:host=""
android:mimeType="*/*"
android:pathPattern=".*\\.ext"
android:scheme="file"
></data>
ฉันเคยดิ้นรนกับเรื่องนี้มาพอสมควรสำหรับนามสกุลไฟล์ที่กำหนดเองด้วยตัวเอง หลังจากค้นหาเป็นจำนวนมากฉันพบหน้าเว็บนี้ซึ่งผู้โพสต์พบว่าคลาส patternMatcher ของ Android (ซึ่งใช้สำหรับการจับคู่ pathPattern ใน Intent-Filters) มีพฤติกรรมที่ไม่คาดคิดเมื่อเส้นทางของคุณมีอักขระตัวแรกของรูปแบบการจับคู่ของคุณที่อื่นในเส้นทาง (เช่นถ้าคุณพยายามจับคู่ "* .xyz" คลาส patternMatcher จะหยุดหากมี "x" อยู่ก่อนหน้าในเส้นทางของคุณ) นี่คือสิ่งที่เขาพบสำหรับวิธีแก้ปัญหาและทำงานให้ฉันแม้ว่ามันจะเป็นการแฮ็กเล็กน้อย:
PatternMatcher ใช้สำหรับ pathPattern ที่ IntentFilter แต่อัลกอริทึมของ PatternMatcher ค่อนข้างแปลกสำหรับฉัน นี่คืออัลกอริทึมของ Android PatternMatcher
หากมีรูปแบบ 'อักขระถัดไป' ของ '. *' อยู่ตรงกลางของสตริง PatternMatcher จะหยุดการวนซ้ำที่จุดนั้น (ดู PatternMatcher.java ของกรอบงาน Android)
เช่น สตริง: "this is a attachment" pattern: ". att. " Android PatternMatcher ป้อนลูปเพื่อจับคู่ ' 'รูปแบบจนกว่าจะพบกับอักขระถัดไปของรูปแบบ (ในตัวอย่างนี้' a ') So,' 'การจับคู่วนหยุดที่ดัชนี 8 -' a 'ระหว่าง' คือ 'และ' ของฉัน ' ดังนั้นผลลัพธ์ของการจับคู่นี้จะคืนค่าเป็น "เท็จ"
ค่อนข้างแปลกไม่ใช่เหรอ ในการแก้ปัญหานี้ - ลดความเป็นไปได้จริง - นักพัฒนาควรใช้ pathPattern ที่น่ารำคาญ
เช่น เป้าหมาย: จับคู่เส้นทาง uri ซึ่งรวมถึง "ข้อความ"
<intent-filter>
...
<data android:pathPattern=".*message.*" />
<data android:pathPattern=".*m.*message.*" />
<data android:pathPattern=".*m.*m.*message.*" />
<data android:pathPattern=".*m.*m.*m.*message.*" />
<data android:pathPattern=".*m.*m.*m.*m.*message.*" />
...
</intent-filter>
โดยเฉพาะเมื่อจับคู่กับนามสกุลไฟล์ที่กำหนดเอง
ไม่มีสิ่งใดที่ทำงานได้อย่างถูกต้องสำหรับการดำเนินการ VIEW หรือ SEND หากคำต่อท้ายไม่ได้ลงทะเบียนด้วยประเภท MIME ในระบบของ Android = ฐานข้อมูล MIME แบบกว้าง การตั้งค่าเดียวที่ฉันพบว่าไฟสำหรับคำต่อท้ายที่ระบุรวมถึงandroid:mimeType="*/*"
แต่การดำเนินการจะเริ่มทำงานสำหรับไฟล์ทั้งหมด ไม่ใช่สิ่งที่คุณต้องการอย่างชัดเจน!
ฉันไม่พบวิธีแก้ปัญหาที่เหมาะสมโดยไม่ต้องเพิ่ม mime และคำต่อท้ายในฐานข้อมูล mime ของ Android จนถึงตอนนี้ฉันยังไม่พบวิธีที่จะทำเช่นนั้น ถ้าใครรู้ตัวชี้จะยอดเยี่ยม
เมื่อเจตจำนงเป็นintent-filter
ไปตามintent-filter
ข้อกำหนดข้อกำหนดเหล่านี้คือ: (ลองนึกภาพรายการตรวจสอบ)
<action>
<category>
<data mimeType>
(แก้ไขอย่างง่าย: " / ")ทางเลือก:
ใด ๆ การจับคู่<data scheme>
(แก้ไขได้ง่าย: <data android:scheme="file" /> <data android:scheme="content" />
)
การจับคู่ใด ๆ<data host>
(แก้ไขง่าย: "*")
<data pathPattern/etc.>
(ตัวอย่างเช่น.*\\.0cc
)การกำหนด<data $type="">
องค์ประกอบหลายรายการทำเครื่องหมายในช่อง $ type iff ใด ๆ ที่<data $type=>
ตรงกับIntent
.
การละเว้น mimeType จะทำให้คุณเสียหายintent-filter
แม้ว่าจะดูเหมือนซ้ำซ้อน การละเว้น<data scheme/host/pathPattern>
ทำให้ตัวกรองของคุณตรงกับทุกอย่าง
https://f-droid.org/en/packages/de.k3b.android.intentintercept/เป็นแอปที่ออกแบบมาเพื่อรับIntent ทั้งหมดและช่วยให้คุณตรวจสอบเจตนาได้ application/octet-stream
ผมได้เรียนรู้ว่านามสกุลไฟล์ที่ไม่รู้จักเปิดผ่านผู้จัดการไฟล์แบบง่ายจะถูกส่งกับชนิดไมม์
https://stackoverflow.com/a/4621284/2683842รายงานว่า<data pathPattern=>
.*xyz
ถูกยกเลิกในครั้งแรกที่เห็นและจะล้มเหลวทันทีถ้าไม่ได้ตามมาด้วยx
yz
ดังนั้น/sdcard/.hidden/foo.0cc
จะไม่ผ่าน.*\\.0cc
เว้นแต่คุณจะพยายาม.*\\..*\\.0cc
แทน
ผลลัพธ์สุดท้าย:
<activity android:name=".Ft2NsfActivity">
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="file" />
<data android:scheme="content" />
<data android:host="*" />
<data android:pathPattern=".*\\.ftm"/>
<data android:pathPattern=".*\\..*\\.ftm"/>
<data android:pathPattern=".*\\..*\\..*\\.ftm"/>
<data android:pathPattern=".*\\..*\\..*\\..*\\.ftm"/>
<data android:pathPattern=".*\\.0cc"/>
<data android:pathPattern=".*\\..*\\.0cc"/>
<data android:pathPattern=".*\\..*\\..*\\.0cc"/>
<data android:pathPattern=".*\\..*\\..*\\..*\\.0cc"/>
<data android:mimeType="*/*" />
</intent-filter>
</activity>
หากคุณต้องการให้เปิดไฟล์โดยตรงจาก Gmail, ดรอปบ็อกซ์หรือเครื่องมือสร้างไฟล์ Android ใด ๆ ให้ใช้รหัสต่อไปนี้ (ลบ 'android: host = "*"' ที่ทำให้ไม่สามารถเข้าถึงไฟล์สำหรับ gmail ได้):
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<category android:name="android.intent.category.BROWSABLE"/>
<category android:name="android.intent.category.DEFAULT"/>
<data android:scheme="content" android:pathPattern=".*\\.kdb"
android:mimeType="application/octet-stream"/>
</intent-filter>
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<category android:name="android.intent.category.DEFAULT"/>
<data android:scheme="file" android:mimeType="*/*"
android:pathPattern=".*\\.kdb"/>
</intent-filter>
ต้องเขียนตัวกรองข้อมูลในหนึ่งคำสั่งตาม Android เวอร์ชัน 4.x
ใช้ตัวกรองด้านล่างเพื่อเปิดจากเบราว์เซอร์ gmail และไฟล์เบราว์เซอร์ (ทดสอบแล้ว) หมายเหตุ: โปรดอย่าผสานสองตัวกรองซึ่งจะทำให้เบราว์เซอร์ละเว้นแอปของคุณ (ทดสอบแล้ว)
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<category android:name="android.intent.category.DEFAULT"/>
<category android:name="android.intent.category.BROWSABLE"/>
<data android:scheme="file" android:pathPattern=".*\\.ext" android:mimeType="application/*"/>
<data android:scheme="content" android:pathPattern=".*\\.ext" android:mimeType="application/*"/>
</intent-filter>
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<category android:name="android.intent.category.DEFAULT"/>
<category android:name="android.intent.category.BROWSABLE"/>
<data android:scheme="http"
android:host="*"
android:pathPattern=".*\\.ext" />
<data android:scheme="https"
android:host="*"
android:pathPattern=".*\\.ext" />
<data android:scheme="ftp"
android:host="*"
android:pathPattern=".*\\.ext" />
</intent-filter>
อ่าน https://developer.android.com/training/sharing/receive นี้จะช่วยในการเริ่มต้น จากนั้นในไฟล์รายการให้ลองใช้ตัวกรองความตั้งใจด้านล่างเมื่อลงทะเบียนผู้รับในกิจกรรมที่จะเปิด
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<data android:scheme="content"/>
<category android:name="android.intent.category.BROWSABLE"/>
<category android:name="android.intent.category.DEFAULT" />
<data android:mimeType="application/your_extension" />
</intent-filter>
ตรวจสอบให้แน่ใจว่ามีการระบุส่วนขยายโดยไม่มี "." ในนั้น