יצרני מכשירים יכולים לחשוף תוספים כמו בוקה, מצב לילה ו-HDR למפתחים של צד שלישי דרך ממשק Camera Extensions שסופק על ידי ספריית ספקי ה-OEM. מפתחים יכולים להשתמש ב-Camera2 Extensions API וב-CameraX Extensions API כדי לגשת לתוספים שהוטמעו בספריית הספקים של יצרן הציוד המקורי.
רשימת התוספים הנתמכים, שזהה ב-Camera2 וב-CameraX, מופיעה במאמר בנושא CameraX Extensions API. אם רוצים להוסיף תוסף, צריך לדווח על באג באמצעות Issue Tracker.
בדף הזה מוסבר איך להטמיע ולהפעיל את ספריית ספקי ה-OEM במכשירים.
ארכיטקטורה
בתרשים הבא מתוארת הארכיטקטורה של הממשק Camera Extensions או extensions-interface:
איור 1. תרשים הארכיטקטורה של תוספי המצלמה
כפי שמוצג בתרשים, כדי לתמוך בתוספי מצלמה, צריך להטמיע את extensions-interface שסופק על ידי ספריית ספק ה-OEM. ספריית ספק ה-OEM מאפשרת שני ממשקי API: CameraX Extensions API ו-Camera2 Extensions API, שמשמשים את אפליקציות CameraX ו-Camera2, בהתאמה, כדי לגשת לתוספים של הספק.
הטמעה של ספריית ספקים של OEM
כדי להטמיע את ספריית הספקים של יצרן ציוד מקורי, מעתיקים את הקבצים camera-extensions-stub לפרויקט של ספריית מערכת. הקבצים האלה מגדירים את הממשק של Camera Extensions.
קובצי camera-extensions-stub מחולקים לקטגוריות הבאות:
קבצים חיוניים לממשק (לא לשנות)
PreviewExtenderImpl.javaImageCaptureExtenderImpl.javaExtenderStateListener.javaProcessorImpl.javaPreviewImageProcessorImpl.javaCaptureProcessorImpl.javaCaptureStageImpl.javaRequestUpdateProcessorImpl.javaProcessResultImpl.javaadvanced/AdvancedExtenderImpl.javaadvanced/Camera2OutputConfigImpl.javaadvanced/Camera2SessionConfigImpl.javaadvanced/ImageProcessorImpl.javaadvanced/ImageReaderOutputConfigImpl.javaadvanced/ImageReferenceImpl.javaadvanced/MultiResolutionImageReaderOutputConfigImpl.javaadvanced/OutputSurfaceImpl.javaadvanced/RequestProcessorImpl.javaadvanced/SessionProcessorImpl.javaadvanced/SurfaceOutputConfigImpl.java
הטמעות חובה (הוספת ההטמעה)
ExtensionVersionImpl.javaInitializerImpl.java
שיעורים להרחבת בוקה (צריך להטמיע אותם אם יש תמיכה בתוסף בוקה)
BokehImageCaptureExtenderImpl.javaBokehPreviewExtenderImpl.javaadvanced/BokehAdvancedExtenderImpl.java
כיתות להארכת הלילה (מטמיעים את התכונה אם היא נתמכת)
NightImageCaptureExtenderImpl.javaNightPreviewExtenderImpl.javaadvanced/NightAdvancedExtenderImpl.java
מחלקות להרחבה אוטומטית (צריך להטמיע אותן אם יש תמיכה בהרחבה אוטומטית)
AutoImageCaptureExtenderImpl.javaAutoPreviewExtenderImpl.javaadvanced/AutoAdvancedExtenderImpl.java
מחלקות של HDR extender (צריך להטמיע אותן אם יש תמיכה בהרחבת HDR)
HdrImageCaptureExtenderImpl.javaHdrPreviewExtenderImpl.javaadvanced/HdrAdvancedExtenderImpl.java
מחלקות להרחבת התכונה 'ריטוש פנים' (צריך להטמיע אותן אם התוסף 'ריטוש פנים' נתמך)
BeautyImageCaptureExtenderImpl.javaBeautyPreviewExtenderImpl.javaadvanced/BeautyAdvancedExtenderImpl.java
Utilities (אופציונלי, אפשר למחוק)
advanced/Camera2OutputConfigImplBuilder.javaadvanced/Camera2SessionConfigImplBuilder.java
אתם לא חייבים לספק הטמעה לכל תוסף. אם לא מטמיעים תוסף, מגדירים את isExtensionAvailable() להחזרת false או מסירים את המחלקות המתאימות של Extender. ממשקי ה-API של Camera2 ו-CameraX Extensions
מדווחים לאפליקציה שהתוסף לא זמין.
במאמר הזה נסביר איך ממשקי ה-API של Camera2 ו-CameraX Extensions פועלים עם ספריית הספק כדי להפעיל תוסף. התרשים הבא מדגים את התהליך מקצה לקצה באמצעות התוסף Night כדוגמה:
איור 2. הטמעה של תוסף לילה
אימות הגרסה:
Camera2/X מבצעת קריאות ל-
ExtensionVersionImpl.checkApiVersion()כדי לוודא שהגרסהextensions-interfaceשהוטמעה על ידי יצרן הציוד המקורי תואמת לגרסאות שנתמכות על ידי Camera2/X.הפעלה של ספריית הספקים:
ל-
InitializerImplיש methodinit()שמאחלת את ספריית הספק. האתחול של Camera2/X מסתיים לפני הגישה למחלקות Extender.יצירת מופעים של מחלקות Extender:
יוצר מופעים של מחלקות Extender עבור התוסף. יש שני סוגים של כלי להרחבת מילות מפתח: כלי בסיסי להרחבת מילות מפתח וכלי מתקדם להרחבת מילות מפתח. צריך להטמיע סוג Extender אחד לכל התוספים. מידע נוסף על ההבדלים בין כלי בסיסי להרחבת טווח החיפוש לבין כלי מתקדם להרחבת טווח החיפוש
Camera2/X יוצר אינסטנסים של מחלקות Extender ומקיים איתן אינטראקציה כדי לאחזר מידע ולאפשר את התוסף. בתוסף נתון, Camera2/X יכול ליצור מופעים של מחלקות Extender כמה פעמים. לכן, לא מומלץ לבצע אתחול כבד בקונסטרוקטור או בקריאה
init(). הפעולות המורכבות מתבצעות רק כשסשן המצלמה עומד להתחיל, למשל כשמתבצעת קריאה ל-onInit()ב-Basic Extender או כשמתבצעת קריאה ל-initSession()ב-Advanced Extender.בתוסף Night, מופעלות הדוגמאות הבאות של מחלקות Extender עבור סוג Basic Extender:
NightImageCaptureExtenderImpl.javaNightPreviewExtenderImpl.java
ובסוג Advanced Extender:
NightAdvancedExtenderImpl.java
בדיקת הזמינות של התוסף:
לפני שמפעילים את התוסף,
isExtensionAvailable()בודק אם התוסף זמין במזהה המצלמה שצוין דרך מופע Extender.מאחלים את המאריך עם פרטי המצלמה:
Camera2/X קוראת ל-
init()במופע Extender ומעבירה לו את מזהה המצלמהCameraCharacteristics.פרטי השאילתה:
מפעיל את המחלקה Extender כדי לאחזר מידע כמו רזולוציות נתמכות, השהיית צילום סטילס משוערת ומפתחות בקשת צילום מה-Extender בהכנה להפעלת התוסף.
הפעלת התוסף ב-Extender:
המחלקה Extender מספקת את כל הממשקים שנדרשים להפעלת המחלקה. היא מציעה מנגנון לחיבור הטמעה של OEM (יצרן ציוד מקורי) ל-Camera2 פייפליין, כמו הוספת פרמטרים של בקשת צילום או הפעלת מעבד פוסט.
בסוג Advanced Extender, Camera2/X מתקשר עם
SessionProcessorImplכדי להפעיל את התוסף. Camera2/X מאחזר את מופעSessionProcessorImplעל ידי קריאה ל-createSessionProcessor()ב-Extender.
בקטעים הבאים מוסבר בפירוט על תהליך ההרחבה.
אימות גרסה
כשספריית הספקים של יצרן הציוד המקורי נטענת מהמכשיר בזמן הריצה, Camera2/X
בודקת אם הספרייה תואמת לגרסה extensions-interface.
extensions-interface משתמש בפורמט סמנטי לניהול גרסאות, או בפורמט MAJOR.MINOR.PATCH, למשל, 1.1.0 או 1.2.0. עם זאת, רק הגרסאות העיקריות והמשניות משמשות במהלך אימות הגרסה.
כדי לאמת את הגרסה, מתבצעת קריאה ל-Camera2/X
ExtensionVersionImpl.checkApiVersion() עם הגרסה הנתמכת
extensions-interface. לאחר מכן, Camera2/X משתמשת בגרסה שמדווחת על ידי ספריית ה-OEM כדי לקבוע אם אפשר להפעיל את התוסף ואילו יכולות הוא צריך להפעיל.
תאימות לגרסה ראשית
אם הגרסאות העיקריות של ממשק התוסף שונות בין Camera2/X לבין ספריית הספק, התוסף נחשב לא תואם והוא מושבת.
תאימות לדורות קודמים
כל עוד הגרסה הראשית זהה, Camera2/X מבטיחה תאימות לאחור לספריות של ספקי OEM שנבנו עם גרסאות קודמות של extensions-interface. לדוגמה, אם Camera2/X תומך בגרסה 1.3.0, ספריות הספקים של יצרני ה-OEM שהטמיעו גרסאות 1.0.0, 1.1.0 ו-1.2.0 עדיין תואמות.extensions-interface זה גם אומר שאחרי שמטמיעים גרסה ספציפית של ספריית הספק, Camera2/X מוודא שהספרייה תהיה תואמת לאחור לגרסאות extension-interface עתידיות.
תאימות קדימה
תאימות קדימה לספריות של ספקים בגרסאות חדשות יותר של extensions-interface תלויה בכם, יצרני ה-OEM. אם אתם צריכים תכונות מסוימות כדי להטמיע את התוספים,
אולי כדאי להפעיל את התוספים החל מגרסה מסוימת. במקרה כזה, אפשר להחזיר את הגרסה הנתמכת של extensions-interface אם גרסת הספרייה Camera2/X עומדת בדרישות. אם הגרסאות Camera2/X לא נתמכות, אפשר להחזיר גרסה לא תואמת כמו 99.0.0 כדי להשבית את התוספים.
הפעלה ראשונית של ספריית ספק
אחרי אימות גרסת extensions-interface שהוטמעה בספריית ה-OEM, Camera2/X מתחילה את תהליך האתחול. השיטה InitializerImpl.init() מאותתת לספריית ה-OEM שאפליקציה מנסה להשתמש בתוספים.
Camera2/X לא מבצעת קריאות נוספות לספריית ה-OEM (מלבד בדיקת הגרסה) עד שספריית הספקים של ה-OEM קוראת ל-OnExtensionsInitializedCallback.onSuccess() כדי להודיע על השלמת האתחול.
צריך להטמיע את
InitializerImpl
מגרסה extensions-interface 1.1.0. Camera2/X מדלג על שלב האתחול של הספרייה אם ספריית הספק של יצרן הציוד המקורי מטמיעה את extensions-interface 1.0.0.
השוואה בין כלי בסיסי להרחבת מילות מפתח לבין כלי מתקדם להרחבת מילות מפתח
יש שני סוגים של הטמעה של extensions-interface: Basic Extender ו-Advanced Extender. התמיכה ב-Advanced Extender החלה בגרסה extensions-interface 1.2.0.
הטמעה של Basic Extender לתוספים שמבצעים עיבוד של תמונות ב-HAL של המצלמה או שמשתמשים במעבד פוסט שיכול לעבד זרמי YUV.
הטמעה של Advanced Extender לתוספים שצריכים להתאים אישית את הגדרות הסטרימינג של Camera2 ולשלוח בקשות צילום לפי הצורך.
השוואה בין התכונות מופיעה בטבלה הבאה:
| Basic Extender | מאריך מתקדם | |
|---|---|---|
| הגדרות של עדכונים לכיתה | תוקן תצוגה מקדימה: PRIVATE או YUV_420_888 (אם קיים מעבד) תמונה סטטית: JPEG או YUV_420_888 (אם קיים מעבד)
|
ניתן להתאמה אישית על ידי יצרן הציוד המקורי (OEM). |
| שליחת בקשה לצילום מסך | רק Camera2/X יכולה לשלוח בקשות צילום. אפשר להגדיר את הפרמטרים לבקשות האלה. כשמעבד מסופק לצילום תמונות, Camera2/X יכול לשלוח כמה בקשות צילום ולשלוח את כל התמונות ותוצאות הצילום למעבד. | מוקצה לכם מופע RequestProcessorImpl כדי להריץ את בקשת הצילום של camera2 ולקבל תוצאות ותמונה.
Camera2/X מפעיל את |
| Hooks בצינור העברת הנתונים של המצלמה |
|
|
| מתאים ל | תוספים שמוטמעים ב-HAL של המצלמה או במעבד שמבצע עיבוד של תמונות YUV. |
|
| גרסת ה-API הנתמכת | Camera2 Extensions: Android 13 ואילך CameraX Extensions: camera-extensions גרסה 1.1.0 ואילך |
תוספים ל-Camera2: Android 12L ואילך תוספים ל-CameraX: camera-extensions 1.2.0-alpha03 ואילך |
מסלולי המשתמש באפליקציה
בטבלה הבאה מוצגים שלושה סוגים של תהליכי עבודה באפליקציה והקריאות המתאימות ל-Camera Extensions API. Camera2/X מספקת את ממשקי ה-API האלה, אבל צריך להטמיע את ספריית הספק בצורה נכונה כדי לתמוך בתהליכים האלה, שמתוארים בפירוט רב יותר בקטע בהמשך.
| תוספים של Camera2 | תוספים ל-CameraX | |
|---|---|---|
| זמינות של הרחבות לשאילתות | CameraExtensionCharacteristics
.getSupportedExtensions
|
ExtensionsManager.
isExtensionAvailable
|
| מידע על השאילתה | CameraExtensionCharacteristics.
getExtensionSupportedSizes
CameraExtensionCharacteristics.
getEstimatedCaptureLatencyRangeMillis
CameraExtensionCharacteristics.
getAvailableCaptureRequestKeys
CameraExtensionCharacteristics.
getAvailableCaptureResultKeys
|
ExtensionsManager.
getEstimatedCaptureLatencyRange
CameraX מטפלת בשאר המידע בספרייה. |
| תצוגה מקדימה וצילום תמונות סטילס כשהתוסף מופעל | CameraDevice.
createExtensionSession
|
val cameraSelector = ExtensionsManager.
getExtensionEnabledCameraSelector
|
Basic Extender
ממשק Basic Extender מספק הוקים לכמה מקומות בצינור העברת הנתונים של המצלמה. לכל סוג של תוסף יש מחלקות Extender תואמות שספקי OEM צריכים להטמיע.
בטבלה הבאה מפורטים סוגי ה-Extender שספקי OEM צריכים להטמיע עבור כל תוסף:
| Extender classes to implement | |
|---|---|
| לילה | NightPreviewExtenderImpl.java
|
| HDR | HdrPreviewExtenderImpl.java
|
| אוטומטי | AutoPreviewExtenderImpl.java
|
| Bokeh | BokehPreviewExtenderImpl.java
|
| ריטוש פנים | BeautyPreviewExtenderImpl.java
|
בדוגמה הבאה אנחנו משתמשים ב-PreviewExtenderImpl וב-ImageCaptureExtenderImpl כערכי placeholder. מחליפים אותם בשמות של הקבצים שאתם מטמיעים.
התכונה 'הארכה בסיסית' כוללת את היכולות הבאות:
- הוספת פרמטרים של ביקורים כשמגדירים את
CameraCaptureSession(onPresetSession). - הודעה על אירועי הפתיחה והסגירה של סשן התיעוד, ושליחת בקשה אחת להודעה ל-HAL עם הפרמטרים שהוחזרו (
onEnableSession,onDisableSession). - הוספת פרמטרים של תיעוד לבקשה
(
PreviewExtenderImpl.getCaptureStage,ImageCaptureExtenderImpl.getCaptureStages). - מוסיפים מעבדים לתצוגה מקדימה ולצילום תמונות סטילס שיכולים לעבד את הזרם
YUV_420_888.
נראה איך Camera2/X מפעיל את extensions-interface כדי להשיג את שלושת תהליכי העבודה של האפליקציה שצוינו למעלה.
תהליך באפליקציה 1: בדיקת הזמינות של התוסף
איור 3. תהליך האפליקציה 1 ב-Basic Extender
בתהליך הזה, Camera2/X קוראת ישירות לשיטה isExtensionAvailable() של PreviewExtenderImpl ושל ImageCaptureExtenderImpl בלי לקרוא ל-init(). שתי המחלקות של Extender צריכות להחזיר true כדי להפעיל את התוספים.
לרוב, זה השלב הראשון באפליקציות כדי לבדוק אם סוג התוסף שצוין נתמך עבור מזהה מצלמה מסוים לפני שמפעילים את התוסף. הסיבה לכך היא שחלק מהתוספים נתמכים רק במזהי מצלמה מסוימים.
תהליך העבודה באפליקציה 2: שליחת שאילתה לקבלת מידע
איור 4. תהליך אימות באפליקציה 2 בתוסף הבסיסי
אחרי שקובעים אם התוסף זמין, האפליקציות צריכות לשלוח שאילתה לגבי המידע הבא לפני שמפעילים את התוסף.
עדיין מתעד את טווח השהייה של הלכידה:
ImageCaptureExtenderImpl.getEstimatedCaptureLatencyRangeמחזירה את הטווח של השהייה של הלכידה עבור האפליקציה כדי להעריך אם מתאים להפעיל את התוסף לתרחיש הנוכחי.גדלים נתמכים לתצוגה מקדימה ולמשטח ללכידת תמונות:
ImageCaptureExtenderImpl.getSupportedResolutionsו-PreviewExtenderImpl.getSupportedResolutionsמחזירים רשימה של פורמטים של תמונות וגדלים שנתמכים עבור פורמט וגודל של משטח.מפתחות נתמכים של בקשות ותוצאות: Camera2/X מפעיל את השיטות הבאות כדי לאחזר את מפתחות הבקשות ומפתחות התוצאות הנתמכים של הלכידה מההטמעה שלכם:
ImageCaptureExtenderImpl.getAvailableCaptureRequestKeysImageCaptureExtenderImpl.getAvailableCapturetResultKeys
Camera2/X תמיד קוראת ל-init() קודם במחלקות Extender האלה לפני שהיא מבקשת מידע נוסף.
תהליך השימוש באפליקציה 3: תצוגה מקדימה/צילום תמונה כשהתוסף מופעל (הטמעה של HAL)
איור 5. תהליך האפליקציה 3 ב-Basic Extender
בתרשים שלמעלה מוצג התהליך העיקרי של הפעלת התצוגה המקדימה וצילום תמונות סטילס באמצעות תוסף ללא מעבד. כלומר, שכבת ה-HAL של המצלמה מעבדת את התוסף.
בתהליך הזה, Camera2/X קודם קוראת ל-init() ואז ל-onInit, וכך מודיעה לכם שסשן מצלמה עומד להתחיל עם התוספים שצוינו.
אפשר לבצע אתחול של פעולות כבדות ב-onInit().
כשמגדירים את CameraCaptureSession, Camera2/X מפעיל את onPresetSession כדי לקבל את פרמטרים של הסשן. אחרי שמגדירים את סשן הצילום בהצלחה, Camera2/X מפעיל את onEnableSession ומחזיר מופע של CaptureStageImpl שמכיל את פרמטרי הצילום. Camera2/X
שולחת מיד בקשה אחת עם פרמטרי הצילום האלה כדי להודיע ל-HAL. באופן דומה, לפני שסוגרים את סשן הצילום, Camera2/X מפעילה את
onDisableSession ואז שולחת בקשה אחת עם פרמטרי הצילום שהוחזרו.
הבקשה החוזרת שמופעלת על ידי Camera2/X מכילה את פרמטרי הבקשה שמוחזרים על ידי PreviewExtenderImpl.getCaptureStage(). בנוסף, בקשת צילום התמונה מכילה את הפרמטרים שמוחזרים על ידי ImageCaptureExtenderImpl.getCaptureStages().
לבסוף, Camera2/X מפעיל את onDeInit() אחרי שסשן המצלמה מסתיים.
אפשר לשחרר משאבים בonDeinit().
מעבד תצוגה מקדימה
בנוסף ל-HAL של המצלמה, אפשר להטמיע תוספים גם במעבד.
מטמיעים את PreviewExtenderImpl.getProcessorType כדי לציין את סוג המעבד, כמו שמוסבר בהמשך:
PROCESSOR_TYPE_NONE: אין מעבד. התמונות מעובדות ב-HAL של המצלמה.
PROCESSOR_TYPE_REQUEST_UPDATE_ONLY: סוג המעבד מאפשר לעדכן את הבקשה החוזרת עם פרמטרים חדשים של בקשת צילום על סמךTotalCaptureResultהעדכני.השיטה
PreviewExtenderImpl.getProcessorצריכה להחזיר מופע שלRequestUpdateProcessorImplשמטפל במופעTotalCaptureResultומחזיר מופע שלCaptureStageImplכדי לעדכן את הבקשה החוזרת. הערךPreviewExtenderImpl.getCaptureStage()צריך לשקף גם את תוצאת העיבוד ולהחזיר את הערך האחרון שלCaptureStageImpl.
PROCESSOR_TYPE_IMAGE_PROCESSOR: הסוג הזה מאפשר לכם להטמיע מעבד כדי לעבד תמונותYUV_420_888ולכתוב את הפלט אלPRIVATE.צריך להטמיע ולהחזיר מופע של
PreviewImageProcessorImplב-PreviewExtenderImpl.getProcessor. המעבד אחראי לעיבוד תמונות הקלטYUV_420_888. הוא צריך לכתוב את הפלט בפורמטPRIVATEשל התצוגה המקדימה. Camera2/X משתמשת בפלטפורמתYUV_420_888במקום ב-PRIVATEכדי להגדיר אתCameraCaptureSessionלתצוגה מקדימה.התרשים הבא ממחיש את התהליך:
איור 6. תצוגה מקדימה של התהליך עם PreviewImageProcessorImpl
הממשק של PreviewImageProcessorImpl הוא הרחבה של ProcessImpl ויש בו שלוש שיטות חשובות:
onOutputSurface(Surface surface, int imageFormat)מגדיר את משטח הפלט של המעבד. PreviewImageProcessorImpl,imageFormatהוא פורמט פיקסלים כמוPixelFormat.RGBA_8888.
onResolutionUpdate(Size size)מגדיר את הגודל של תמונת הקלט.
onImageFormatUpdate(int imageFormat)מגדיר את פורמט התמונה של תמונת הקלט. בשלב הזה, אפשר להשתמש רק ב-YUV_420_888.
מעבד צילום תמונות
כדי לצלם תמונות סטילס, אפשר להטמיע מעבד על ידי החזרת מופע של CaptureProcessorImpl באמצעות ImageCaptureExtenderImpl.getCaptureProcessor. המעבד אחראי לעבד רשימה של תמונות שצולמו YUV_420_888 ומופעים של TotalCaptureResult ולכתוב את הפלט בממשק YUV_420_888.
אפשר להניח בבטחה שהתצוגה המקדימה מופעלת ופועלת לפני ששולחים את הבקשה לצילום תמונה.
התרשים הבא מציג את התהליך:
איור 7. המשך צילום המסך באמצעות CaptureProcessorImpl
Camera2/X משתמשת במשטח בפורמט
YUV_420_888לצילום תמונות כדי להגדיר את סשן הצילום. Camera2/X מכין אתCaptureProcessorImplעל ידי קריאה ל:CaptureProcessorImpl.onImageFormatUpdate()עםYUV_420_888.-
CaptureProcessorImpl.onResolutionUpdate()עם גודל תמונת הקלט. -
CaptureProcessorImpl.onOutputSurface()עם פלטYUV_420_888במשטח.
ImageCaptureExtenderImpl.getCaptureStagesמחזירה רשימה שלCaptureStageImpl, כאשר כל רכיב ממופה למופעCaptureRequestעם פרמטרים של לכידה שנשלחים על ידי Camera2/X. לדוגמה, אם הפונקציה מחזירה רשימה של שלושה מופעים שלCaptureStageImpl, Camera2/X שולח שלוש בקשות צילום עם פרמטרים מתאימים של צילום באמצעות ה-APIcaptureBurst.getCaptureStages()התמונות והמופעים של
TotalCaptureResultשמתקבלים נארזים יחד ונשלחים אלCaptureProcessorImplלעיבוד.
CaptureProcessorImplכותב את התוצאה Image (פורמטYUV_420_888) אל משטח הפלט שצוין על ידי הקריאהonOutputSurface(). המערכת Camera2/X ממירה אותו לתמונות JPEG אם צריך.
תמיכה בתוצאות ובמפתחות של בקשות לתיעוד
בנוסף לתצוגה מקדימה של המצלמה ולצילום, אפליקציות יכולות להגדיר זום, פרמטרים של פלאש או להפעיל הקשה למיקוד. יכול להיות שהפרמטרים האלה לא תואמים להטמעה של התוסף.
הוספנו את ה-methods הבאות ל-extensions-interface 1.3.0 כדי לאפשר לכם לחשוף את הפרמטרים שההטמעה שלכם תומכת בהם:
-
ImageCaptureExtenderImpl.getAvailableCaptureRequestKeys()מחזירה את המפתחות של בקשות הצילום שנתמכים בהטמעה שלכם. -
ImageCaptureExtenderImpl.getAvailableCaptureResultKeys()מחזירה את המפתחות של תוצאות הצילום שנכללים בתוצאות הצילום.
אם רכיב HAL של המצלמה מעבד את התוסף, Camera2/X מאחזר את תוצאות הצילום ב-CameraCaptureSession.CaptureCallback. אבל אם המעבד מיושם, אז Camera2/X מאחזר את תוצאות הצילום ב-ProcessResultImpl, שמועבר למתודה process() ב-PreviewImageProcessorImpl וב-CaptureProcessorImpl.
אתם אחראים לדיווח על תוצאת הצילום דרך ProcessResultImpl אל Camera2/X.
לדוגמה, אפשר לעיין בהגדרה של הממשק CaptureProcessorImpl שבהמשך.
בגרסה extensions-interface 1.3.0 ואילך, מתבצעת קריאה שנייה ל-process():
Interface CaptureProcessorImpl extends ProcessorImpl {
// invoked when extensions-interface version < 1.3.0
void process(Map<Integer, Pair<Image, TotalCaptureResult>> results);
// invoked when extensions-interface version >= 1.3.0
void process(Map<Integer, Pair<Image, TotalCaptureResult>> results,
ProcessResultImpl resultCallback, Executor executor);
}
לפעולות נפוצות במצלמה כמו זום, הקשה למיקוד, פלאש ופיצוי חשיפה, מומלץ לתמוך במקשים הבאים גם לבקשת צילום וגם לתוצאת צילום:
- זום:
CaptureRequest#CONTROL_ZOOM_RATIOCaptureRequest#SCALER_CROP_REGION
- מיקוד בהקשה:
CaptureRequest#CONTROL_AF_MODECaptureRequest#CONTROL_AF_TRIGGERCaptureRequest#CONTROL_AF_REGIONSCaptureRequest#CONTROL_AE_REGIONSCaptureRequest#CONTROL_AWB_REGIONS
- Flash:
CaptureRequest#CONTROL_AE_MODECaptureRequest#CONTROL_AE_PRECAPTURE_TRIGGERCaptureRequest#FLASH_MODE
- פיצוי חשיפה:
CaptureRequest#CONTROL_AE_EXPOSURE_COMPENSATION
במקרה של תוספים בסיסיים שמטמיעים גרסה 1.2.0 או גרסאות קודמות, CameraX Extensions API תומך באופן מפורש בכל המפתחות שלמעלה. בגרסה
extensions-interface 1.3.0, גם CameraX וגם Camera2 מכבדות את הרשימה שמוחזרת
ותומכות רק במפתחות שמופיעים בה. לדוגמה, אם מחליטים להחזיר רק את CaptureRequest#CONTROL_ZOOM_RATIO ואת CaptureRequest#SCALER_CROP_REGION בהטמעה של גרסה 1.3.0, המשמעות היא שרק זום נתמך באפליקציה, אבל לא ניתן להשתמש בהקשה למיקוד, בפלאש ובפיצוי חשיפה.
מאריך מתקדם
Advanced Extender הוא סוג של הטמעה של ספק שמבוססת על Camera2 API.
סוג ה-Extender הזה נוסף בגרסה extensions-interface 1.2.0. בהתאם ליצרן המכשיר, יכול להיות שהתוספים יוטמעו בשכבת האפליקציה, וזה תלוי בגורמים הבאים:
הגדרת שידור בהתאמה אישית: הגדרה של שידורים בהתאמה אישית כמו שידור RAW או שידורים מרובים למזהי מצלמות פיזיים שונים.
יכולת לשלוח בקשות Camera2: תמיכה בלוגיקה מורכבת של אינטראקציה שיכולה לשלוח בקשות צילום עם פרמטרים שמבוססים על התוצאות של בקשות קודמות.
Advanced Extender מספק מעטפת או שכבת ביניים, כך שתוכלו להתאים אישית את הגדרות הסטרימינג ולשלוח בקשות ללכידה לפי דרישה.
קבצים להטמעה
כדי לעבור להטמעה של Advanced Extender, השיטה isAdvancedExtenderImplemented() ב-ExtensionVersionImpl צריכה להחזיר true. יצרני ציוד מקורי (OEM) צריכים להטמיע את המחלקות המתאימות של Extender לכל סוג תוסף. קבצי ההטמעה של Advanced Extender נמצאים בחבילה advanced.
| כיתות להרחבה להטמעה | |
|---|---|
| לילה | advanced/NightAdvancedExtenderImpl.java
|
| HDR | advanced/HdrAdvancedExtenderImpl.java
|
| אוטומטי | advanced/AutoAdvancedExtenderImpl.java
|
| Bokeh | advanced/BokehAdvancedExtenderImpl.java
|
| ריטוש פנים | advanced/BeautyAdvancedExtenderImpl.java
|
בדוגמה הבאה, אנחנו משתמשים ב-AdvancedExtenderImpl כ-placeholder.
מחליפים אותו בשם של קובץ ה-Extender של התוסף שרוצים להטמיע.
בואו נראה איך Camera2/X מפעיל את extensions-interface כדי להשיג את שלושת תהליכי העבודה באפליקציה.
תהליך באפליקציה 1: בדיקת הזמינות של תוספים
איור 8. תהליך באפליקציה 1 ב-Advanced Extender
קודם כול, האפליקציה בודקת אם התוסף שצוין נתמך.
תהליך העבודה באפליקציה 2: שליחת שאילתה לקבלת מידע
איור 9. זרימת אפליקציה 2 ב-Advanced Extender
אחרי הקריאה ל-AdvancedExtenderImpl.init(), האפליקציה יכולה לשלוח שאילתה לגבי המידע הבא על AdvancedExtenderImpl:
השהיית צילום משוערת של תמונות סטילס:
AdvancedExtenderImpl.getEstimatedCaptureLatencyRange()מחזירה את טווח ההשהיה של הצילום באפליקציה כדי להעריך אם מתאים להפעיל את התוסף בתרחיש הנוכחי.רזולוציות נתמכות לתצוגה מקדימה ולצילום תמונות:
AdvancedExtenderImpl.getSupportedPreviewOutputResolutions()מחזירה מיפוי של פורמט התמונה לרשימת הגדלים שנתמכים עבור פורמט וגודל של משטח תצוגה מקדימה. יצרני ציוד מקורי (OEM) צריכים לתמוך בפורמטPRIVATEלפחות.
AdvancedExtenderImpl.getSupportedCaptureOutputResolutions()מחזירה את הפורמט והגדלים הנתמכים של משטח ללכידת תמונות סטילס. יצרני ציוד מקורי חייבים לתמוך בפלט בפורמטיםJPEGו-YUV_420_888.
AdvancedExtenderImpl.getSupportedYuvAnalysisResolutions()מחזירה את הגדלים הנתמכים של זרםYUV_420_888נוסף לניתוח תמונות. אם לא קיימת תמיכה ב-YUV surface של ניתוח תמונות, הפונקציהgetSupportedYuvAnalysisResolutions()צריכה להחזירnullאו רשימה ריקה.
מפתחות/תוצאות זמינים של בקשות צילום (נוספו בגרסה
extensions-interface1.3.0): Camera2/X מפעילה את השיטות הבאות כדי לאחזר את מפתחות בקשות הצילום ומפתחות התוצאות הנתמכים מההטמעה שלכם:AdvancedExtenderImpl.getAvailableCaptureRequestKeysAdvancedExtenderImpl.getAvailableCaptureResultKeys
מידע נוסף זמין במאמר בנושא תמיכה במפתחות ובתוצאות של בקשות לתיעוד.
תהליך השימוש באפליקציה 3: תצוגה מקדימה או צילום תמונה כשהתוסף מופעל
איור 10. זרימת אפליקציה 3 ב-Advanced Extender
בתרשים שלמעלה מוצג התהליך העיקרי של הפעלת התצוגה המקדימה וצילום תמונות סטילס עבור סוג המאריך המתקדם. נסביר מה צריך לעשות בכל שלב.
SessionProcessorImplinstanceההטמעה העיקרית של Advanced Extender נמצאת ב-
SessionProcessorImpl, שאחראי על אספקת הגדרת סשן בהתאמה אישית ועל שליחת בקשות ללכידה כדי להתחיל את התצוגה המקדימה ואת בקשת הלכידה. הפונקציהAdvancedExtenderImpl.createSessionProcessor()מופעלת כדי להחזיר את המופעSessionProcessorImpl.initSession
SessionProcessorImpl.initSession()מאתחל את הסשן של התוסף. כאן מקצים משאבים ומחזירים הגדרת סשן להכנתCameraCaptureSession.בפרמטרים של הקלט, Camera2/X מציין את ההגדרות של משטח הפלט לתצוגה מקדימה, לצילום תמונות סטילס ולניתוח אופציונלי של תמונות YUV. הגדרת פלט זו (
OutputSurfaceImpl) מכילה את המשטח, הגודל ופורמט התמונה שאוחזרו על ידי השיטות הבאות ב-AdvancedExtenderImpl:getSupportedPreviewOutputResolutions()getSupportedCaptureOutputResolutions()getSupportedYuvAnalysisResolutions()
צריך להחזיר מופע של
Camera2SessionConfigImpl, שמורכב מרשימה של מופעים שלCamera2OutputConfigImplומהפרמטרים של הסשן שמשמשים להגדרתCameraCaptureSession. באחריותכם להפיק את תמונות המצלמה הנכונות אל משטחי הפלט שמועברים על ידי Camera2/X. אלה כמה אפשרויות להפעלת הפלט:- עיבוד ב-HAL של המצלמה: אפשר להוסיף ישירות את משטחי הפלט ל-
CameraCaptureSessionבאמצעות הטמעה שלSurfaceOutputConfigImpl. ההגדרה הזו קובעת את משטח הפלט שסופק לפייפליין המצלמה ומאפשרת ל-HAL של המצלמה לעבד את התמונה. עיבוד של פלטפורמת
ImageReaderביניים (RAW, YUV וכו'): מוסיפים את פלטפורמותImageReaderהביניים אלCameraCaptureSessionעם מופעImageReaderOutputConfigImpl.צריך לעבד את התמונות הביניים ולכתוב את תמונת התוצאה אל משטח הפלט.
- שימוש בשיתוף של משטח Camera2: כדי לשתף משטח עם משטח אחר, מוסיפים מופע
Camera2OutputConfigImplכלשהו לשיטהgetSurfaceSharingOutputConfigs()של מופעCamera2OutputConfigImplאחר. הפורמט והגודל של המשטח חייבים להיות זהים.
לכל
Camera2OutputConfigImpl, כוללSurfaceOutputConfigImplו-ImageReaderOutputConfigImpl, צריך להיות מזהה ייחודי (getId()), שמשמש לציון פלטפורמת היעד ולאחזור התמונה מ-ImageReaderOutputConfigImpl.
onCaptureSessionStartו-RequestProcessorImplכש-
CameraCaptureSessionמתחיל וה-Camera framework מפעיל אתonConfigured(), Camera2/X מפעיל אתSessionProcessorImpl.onCaptureSessionStart()עם ה-Camera2 request wrapperRequestProcessImpl. Camera2/X מטמיע אתRequestProcessImpl, שמאפשר לכם להריץ את בקשות הצילום ולאחזר תמונות אם נעשה שימוש ב-ImageReaderOutputConfigImpl.ממשקי ה-API של
RequestProcessImplדומים לממשקי ה-API של Camera2CameraCaptureSessionמבחינת ביצוע בקשות. ההבדלים הם:- משטח היעד מצוין על ידי המזהה של מופע
Camera2OutputConfigImpl. - היכולת לאחזר את התמונה של
ImageReader.
אתם יכולים להתקשר למספר
RequestProcessorImpl.setImageProcessor()עם מזההCamera2OutputConfigImplספציפי כדי לרשום מופעImageProcessorImplלקבלת תמונות.המופע
RequestProcessImplהופך ללא חוקי אחרי קריאות של Camera2/XSessionProcessorImpl.onCaptureSessionEnd().- משטח היעד מצוין על ידי המזהה של מופע
הפעלת התצוגה המקדימה וצילום תמונה
בהטמעה של הכלי המתקדם להרחבת הכיסוי, אפשר לשלוח בקשות לתיעוד דרך הממשק של
RequestProcessorImpl. Camera2/X מודיע לכם להתחיל את הבקשה החוזרת לתצוגה מקדימה או את רצף הצילום של תמונות סטילס על ידי קריאה ל-SessionProcessorImpl#startRepeatingול-SessionProcessorImpl#startCaptureבהתאמה. כדי למלא את הבקשות האלה לצפייה בתצוגה מקדימה ולצילום תמונות, צריך לשלוח בקשות לצילום.ב-Camera2/X מוגדרים גם פרמטרים של בקשת צילום באמצעות
SessionProcessorImpl#setParameters. חובה להגדיר את פרמטרים הבקשה האלה (אם הפרמטרים נתמכים) גם בבקשות החוזרות וגם בבקשות היחידות.אתם צריכים לתמוך לפחות ב-
CaptureRequest.JPEG_ORIENTATIONוב-CaptureRequest.JPEG_QUALITY. extensions-interface1.3.0 תומך במפתחות של בקשות ותוצאות, שמוצגים בשיטות הבאות:AdvancedExtenderImpl.getAvailableCaptureRequestKeys()AdvancedExtenderImpl.getAvailableCaptureResultKeys()
כשמפתחים מגדירים את המפתחות ברשימה
getAvailableCaptureRequestKeys, צריך להפעיל את הפרמטרים ולוודא שתוצאת הלכידה מכילה את המפתחות ברשימהgetAvailableCaptureResultKeys.startTriggerהפונקציה
SessionProcessorImpl.startTrigger()מופעלת כדי להתחיל את הטריגר, כמוCaptureRequest.CONTROL_AF_TRIGGERו-CaptureRequest.CONTROL_AE_PRECAPTURE_TRIGGER. אפשר להתעלם ממפתחות של בקשות ללכידת נתונים שלא פורסמו ב-AdvancedExtenderImpl.getAvailableCaptureRequestKeys().התמיכה ב-
startTrigger()קיימת מאז גרסהextensions-interface1.3.0. היא מאפשרת לאפליקציות להטמיע הקשה להתמקדות והבזק עם תוספים.פינוי נפח
בסיום סשן צילום, הפונקציה
SessionProcessorImpl.onCaptureSessionEnd()מופעלת לפני הסגירה שלCameraCaptureSession. אחרי שסוגרים את סשן הלכידה,deInitSession()מבצע ניקוי.
תצוגה מקדימה של תמיכה, צילום תמונות וניתוח תמונות
כדאי להשתמש בתוסף גם בתרחישים של תצוגה מקדימה וגם בתרחישים של צילום תמונות. עם זאת, אם זמן האחזור גבוה מדי ומונע הצגה חלקה של התצוגה המקדימה, אפשר להחיל את התוסף רק על צילום תמונות סטילס.
בסוג Basic Extender, בלי קשר להפעלת התוסף לתצוגה מקדימה, צריך להטמיע את ImageCaptureExtenderImpl ואת PreviewExtenderImpl עבור תוסף נתון. לעתים קרובות, אפליקציה משתמשת גם בזרם YUV כדי לנתח את תוכן התמונה, למשל כדי למצוא קודי QR או טקסט. כדי לתמוך בתרחיש השימוש הזה בצורה טובה יותר, צריך לתמוך בשילוב של זרם תצוגה מקדימה, צילום תמונה וזרם YUV_420_888 להגדרת CameraCaptureSession. כלומר, אם מטמיעים מעבד, צריך לתמוך בשילוב של שלושה זרמי YUV_420_888.
ב-Advanced Extender, Camera2/X מעבירה שלוש משטחי פלט לשיחה SessionProcessorImpl.initSession(). פלטפורמות הפלט האלה מיועדות לתצוגה מקדימה, לצילום תמונות ולניתוח תמונות, בהתאמה. צריך לוודא שמשטחי הפלט של התצוגה המקדימה ושל צילום התמונות מציגים את הפלט התקין. עם זאת, לגבי משטח הפלט של ניתוח התמונה, צריך לוודא שהוא פועל רק כשהוא לא null. אם ההטמעה לא תומכת בשידור של ניתוח התמונות, אפשר להחזיר רשימה ריקה ב-AdvancedExtenderImpl.getSupportedYuvAnalysisResolutions(). כך מוודאים שפלט ניתוח התמונה תמיד יהיה null ב-SessionProcessorImpl.initSession().
תמיכה בצילום וידאו
הארכיטקטורה הנוכחית של Camera Extension תומכת רק בתרחישי השימוש של תצוגה מקדימה וצילום תמונות סטילס. אנחנו לא תומכים בהפעלת התוסף בפלטפורמות MediaCodec
או MediaRecorder לצורך הקלטת הסרטון. עם זאת, יכול להיות שאפליקציות יקליטו את הפלט של התצוגה המקדימה.
אנחנו בודקים את האפשרות לתמוך בפלטפורמות MediaCodec ו-MediaRecorder.
מטא-נתונים ספציפיים לתוסף
ב-Android מגרסה 14 ואילך, מטא-נתונים ספציפיים לתוספים מאפשרים ללקוחות של תוספי מצלמה להגדיר ולקבל הגדרות ותוצאות ספציפיות לבקשות צילום של תוספים. באופן ספציפי, לקוחות של תוסף מצלמה יכולים להשתמש בפרמטר EXTENSION_STRENGTH של בקשת הצילום כדי לשלוט בעוצמת התוסף, ובתוצאת הצילום EXTENSION_CURRENT_TYPE כדי לציין את סוג התוסף המופעל.
תיעוד בקשות
פרמטר הבקשה EXTENSION_STRENGTH של התוסף קובע את עוצמת האפקט של העיבוד שאחרי. תוצאת הלכידה המתאימה כוללת את ערך עוצמת ברירת המחדל אם הלקוח לא מגדיר את הפרמטר הזה באופן מפורש. אפשר להחיל את הפרמטר הזה על סוגי התוספים האלה באופן הבא:
BOKEH: קובע את רמת הטשטוש.-
HDRו-NIGHT: מאפשרים לשלוט במספר התמונות שמוזגו ובבהירות של התמונה הסופית. -
FACE_RETOUCH: שליטה ברמת השיפור הקוסמטי והחלקת העור.
הטווח הנתמך של הפרמטר EXTENSION_STRENGTH הוא בין 0 ל-100, כאשר 0 מציין שלא מתבצע עיבוד של התוסף או העברת סיגנל ללא שינוי, ו-100 מציין את עוצמת התוסף המקסימלית של אפקט העיבוד.
כדי להוסיף תמיכה ב-EXTENSION_STRENGTH, צריך להשתמש בממשקי ה-API של הפרמטרים הספציפיים לספק שהוצגו בגרסה 1.3.0 של ממשק ספריית התוספים. מידע נוסף זמין במאמר getAvailableCaptureRequestKeys().
תוצאות הצילום
תוצאת הלכידה של EXTENSION_CURRENT_TYPE מאפשרת להטמעות של תוספים להודיע ללקוחות על סוג התוסף הפעיל.
מכיוון שתוספים שמשתמשים בסוג AUTO עוברים באופן דינמי בין סוגי תוספים כמו HDR ו-NIGHT בהתאם לתנאי הסצנה, אפליקציות של תוספי מצלמה יכולות להשתמש ב-EXTENSION_CURRENT_TYPE כדי להציג מידע על התוסף הנוכחי שנבחר על ידי התוסף AUTO.
אומדן זמן האחזור של צילום סטילס בזמן אמת
ב-Android מגרסה 14 ואילך, לקוחות של תוספי מצלמה יכולים לשלוח שאילתות לגבי אומדנים של זמן האחזור של צילום תמונות סטילס בזמן אמת על סמך הסצנה ותנאי הסביבה באמצעות getRealtimeStillCaptureLatency(). השיטה הזו מספקת אומדנים מדויקים יותר מהשיטה הסטטית getEstimatedCaptureLatencyRangeMillis(). על סמך הערכת זמן האחזור, האפליקציות יכולות להחליט לדלג על עיבוד התוסף או להציג אינדיקציה כדי להודיע למשתמשים על פעולה ממושכת.
CameraExtensionSession.StillCaptureLatency latency;
latency = extensionSession.getRealtimeStillCaptureLatency();
// The capture latency from ExtensionCaptureCallback#onCaptureStarted() until ExtensionCaptureCallback#onCaptureProcessStarted().
latency.getCaptureLatency();
// The processing latency from ExtensionCaptureCallback#onCaptureProcessStarted() until the processed frame returns to the client.
latency.getProcessingLatency();
כדי לתמוך בהערכות של זמן האחזור של צילום תמונות סטילס בזמן אמת, צריך להטמיע את הפעולות הבאות:
- תוספים בסיסיים:
ImageCaptureExtenderImpl.getRealtimeCaptureLatency() - תוספים מתקדמים:
SessionProcessorImpl.getRealtimeCaptureLatency
קריאות חוזרות (callback) לדיווח על התקדמות העיבוד
ב-Android מגרסה 14 ואילך, לקוחות של תוספי מצלמה יכולים לקבל קריאות חוזרות (callback) לגבי התקדמות של פעולות עיבוד ארוכות של צילום תמונות סטילס. האפליקציות יכולות להציג למשתמשים את ההתקדמות הנוכחית כדי לשפר את חוויית המשתמש הכוללת.
אפליקציות יכולות להשתמש בקוד הבא כדי לשלב את התכונה הזו:
import android.hardware.camera2.CameraExtensionSession.
ExtensionCaptureCallback;
{
…
class AppCallbackImpl extends ExtensionCaptureCallback {
…
@Override
public void onCaptureProcessProgressed(
@NonNull CameraExtensionSession session,
@NonNull CaptureRequest request,
@IntRange(from = 0, to = 100) int progress) {
// Update app UI with current progress
}
}
…
}
כדי לתמוך בהחזרות (callback) של התקדמות העיבוד של הלכידה, ההטמעה של ספק התוסף צריכה לקרוא להחזרות הבאות עם ערך ההתקדמות הנוכחי:
- תוספים בסיסיים:
ProcessResultImpl.onCaptureProcessProgressed() - תוספים מתקדמים:
CaptureCallback.onCaptureProcessProgressed()
צילום מסך של פוסט
ב-Android מגרסה 14 ואילך, תוספי מצלמה יכולים לספק תצוגה מקדימה (תמונה בתצוגה מקדימה) באמצעות setPostviewOutputConfiguration.
כדי לשפר את חוויית המשתמש, אפליקציות יכולות להציג תמונת פלייסהולדר כשהשהייה בעיבוד של תוסף מתארכת, ולהחליף את התמונה כשהתמונה הסופית זמינה. אפליקציות יכולות להגדיר ולשלוח בקשות לצילום תמונות אחרי צפייה במודעה באמצעות קוד ההפניה הבא:
{
…
if (!CameraExtensionCharacteristics.isPostviewAvailable()) {
continue;
}
…
ExtensionSessionConfiguration extensionConfiguration = new
ExtensionSessionConfiguration(
CameraExtensionCharacteristics.EXTENSION_NIGHT,
outputConfig,
backgroundExecutor,
extensionSessionStateCallback
);
extensionConfiguration.setPostviewOutputConfiguration(
postviewImageOutput);
…
CaptureRequest.Builder captureRequestBuilder =
cameraDevice.createCaptureRequest(
CameraDevice.TEMPLATE_STILL_CAPTURE);
captureRequestBuilder.addTarget(stillImageReader.getSurface());
captureRequestBuilder.addTarget(postviewImageSurface);
CaptureRequest captureRequest = captureRequestBuilder.build();
…
}
כדי לתמוך בתיעוד של צילומי מסך אחרי צפייה, ההטמעה של הספק צריכה לכלול את הפעולות הבאות:
תוספים בסיסיים:
CaptureProcessorImpl.onPostviewOutputSurfaceו-CaptureProcessorImpl.processWithPostviewתוספים מתקדמים:
SessionProcessorImpl.startCaptureWithPostview
תמיכה בפלט של SurfaceView
ב-Android מגרסה 14 ואילך, לקוחות של תוספי מצלמה יכולים להשתמש בנתיבי עיבוד של תצוגה מקדימה שעברו אופטימיזציה לצריכת חשמל ולביצועים, על ידי רישום מופע של SurfaceView לפלט של תצוגה מקדימה עבור בקשות חוזרות.
כדי לתמוך בפלט SurfaceView, ההטמעה של תוסף הספק צריכה להיות מסוגלת להזרים ולהציג תצוגה מקדימה למופעים של SurfaceView. כדי לוודא שיש תמיכה, מריצים את מודול SurfaceViewExtensionPreviewTest.javaCTS.
סוגי סשנים ספציפיים לספק
התכונה מאפשרת להטמעות של תוספים של ספקים לבחור סוג ספציפי של סשן של ספק שיוגדר בסשן הפנימי של צילום המצלמה במקום ערך ברירת המחדל.
התכונה פועלת באופן מלא במסגרת ובמערך הספקים, ואין לה השפעה על ה-API שגלוי ללקוחות או לציבור.
כדי לבחור סוג סשן ספציפי לספק, צריך להטמיע את הערכים הבאים בספריות התוספים:
* ExtenderStateListener.onSessionType() לתוספים בסיסיים
* Camera2SessionConfigImpl.getSessionType() לתוספים מתקדמים
היסטוריית הגרסאות של ממשק התוספים
בטבלה הבאה מפורטת היסטוריית הגרסאות של ממשק תוסף המצלמה. תמיד צריך להטמיע את ספריית הספק עם הגרסה העדכנית ביותר.
| Version | תכונות שנוספו |
|---|---|
| 1.0.0 |
|
| 1.1.0 |
|
| 1.2.0 |
|
| 1.3.0 |
|
| 1.4.0 |
|
הטמעה לדוגמה
ההטמעות הבאות של ספריות ספקים של יצרני ציוד מקורי זמינות ב-frameworks/ex.
advancedSample: הטמעה בסיסית של Advanced Extender.
sample: הטמעה בסיסית של Basic Extender.
service_based_sample: הטמעה שמדגימה איך לארח תוספי מצלמה ב-Service. ההטמעה הזו כוללת את הרכיבים הבאים:
oem_library: ספריית OEM של תוספים למצלמה עבור Camera2 ו-CameraX Extensions APIs שמטמיעה אתExtensions-Interface. הוא פועל כצינור להעברת נתונים ומעביר שיחות מ-Extensions-Interfaceלשירות. הספרייה הזו מספקת גם קובצי AIDL ומחלקות wrapper כדי לתקשר עם השירות.התכונה 'הארכת שיחות מתקדמת' מופעלת כברירת מחדל. כדי להפעיל את Basic Extender, צריך לשנות את
ExtensionsVersionImpl#isAdvancedExtenderImplementedל-returnfalse.extensions_service: הטמעה לדוגמה של שירות התוספים. מוסיפים כאן את ההטמעה. הממשק להטמעה בשירות דומה ל-Extensions-Interface. לדוגמה, הטמעה שלIAdvancedExtenderImpl.Stubמבצעת את אותן פעולות כמוAdvancedExtenderImpl. כדי להפוך אתImageואתTotalCaptureResultלניתנים להעברה, צריך להגדיר אתImageWrapperואתTotalCaptureResultWrapper.
הגדרת ספריית הספק במכשיר
ספריית הספקים של יצרן הציוד המקורי לא מוטמעת באפליקציה, אלא נטענת מהמכשיר בזמן הריצה על ידי Camera2/X. ב-CameraX, התג <uses-library> מצהיר שהספרייה androidx.camera.extensions.impl, שמוגדרת בקובץ AndroidManifest.xml של הספרייה camera-extensions, היא תלות של CameraX וצריך לטעון אותה בזמן הריצה. ב-Camera2, המסגרת טוענת שירות הרחבות שמצהיר גם על כך שספריית <uses-library>loads the same
androidx.camera.extensions.impl נטענת בזמן הריצה.
כך אפליקציות צד שלישי שמשתמשות בתוספים יכולות לטעון באופן אוטומטי את ספריית הספקים של יצרן הציוד המקורי (OEM). ספריית ה-OEM מסומנת כאופציונלית, כך שאפליקציות יכולות לפעול במכשירים שאין בהם את הספרייה. Camera2/X מטפלת בהתנהגות הזו באופן אוטומטי כשמנסים להשתמש בהרחבת מצלמה באפליקציה, כל עוד יצרן המכשיר מציב את ספריית ה-OEM במכשיר כך שהאפליקציה תוכל לגלות אותה.
כדי להגדיר את ספריית ה-OEM במכשיר:
- מוסיפים קובץ הרשאות, שנדרש על ידי התג
<uses-library>, באמצעות הפורמט הבא:/etc/permissions/ANY_FILENAME.xml. לדוגמה,/etc/permissions/camera_extensions.xml. הקבצים בספרייה הזו מספקים מיפוי של הספרייה שצוינה ב-<uses-library>לנתיב הקובץ בפועל במכשיר. בדוגמה שלמטה מוסבר איך להוסיף את המידע הנדרש לקובץ.
- הערך של
nameחייב להיותandroidx.camera.extensions.implכי זו הספרייה ש-CameraX מחפשת. -
fileהוא הנתיב המוחלט של הקובץ שמכיל את הטמעת התוספים (לדוגמה,/system/framework/androidx.camera.extensions.impl.jar).
<?xml version="1.0" encoding="utf-8"?> <permissions> <library name="androidx.camera.extensions.impl" file="OEM_IMPLEMENTED_JAR" /> </permissions>
- הערך של
ב-Android מגרסה 12 ואילך, במכשירים שתומכים בתוספים של CameraX, צריך להגדיר את המאפיין ro.camerax.extensions.enabled לערך true, כדי לאפשר שאילתה לגבי התמיכה של המכשיר בתוספים.
כדי לעשות את זה, מוסיפים את השורה הבאה לקובץ ה-make של המכשיר:
PRODUCT_VENDOR_PROPERTIES += \
ro.camerax.extensions.enabled=true \
אימות
כדי לבדוק את ההטמעה של ספריית ספקי ה-OEM במהלך שלב הפיתוח, אפשר להשתמש באפליקציה לדוגמה בכתובת androidx-main/camera/integration-tests/extensionstestapp/, שמפעילה תוספים שונים של ספקים.
אחרי שמסיימים את ההטמעה, משתמשים בכלי לאימות תוספים למצלמה כדי להריץ בדיקות אוטומטיות וידניות ולוודא שהספרייה של הספק הוטמעה בצורה נכונה.
מצב נוף מורחב לעומת תוספים למצלמה
כדי להשתמש בתוסף אפקט בוקה, בנוסף לחשיפה שלו באמצעות תוספי מצלמה, אפשר לחשוף את התוסף באמצעות מצב נוף מורחב, שמופעל באמצעות המקש CONTROL_EXTENDED_SCENE_MODE.
פרטים נוספים על ההטמעה זמינים במאמר Camera bokeh.
למצב נוף מורחב יש פחות הגבלות בהשוואה לתוספי מצלמה באפליקציות Camera2. לדוגמה, אפשר להפעיל מצב נוף מורחב במופע רגיל של CameraCaptureSession שתומך בשילובים גמישים של זרמים ובפרמטרים של בקשות ללכידה. לעומת זאת, תוספים למצלמה תומכים רק בקבוצה קבועה של סוגי סטרימינג, והתמיכה שלהם בפרמטרים של בקשות צילום מוגבלת.
חיסרון של מצב נוף מורחב הוא שאפשר להטמיע אותו רק ב-HAL של המצלמה, מה שאומר שצריך לוודא שהוא פועל בכל אמצעי הבקרה האורתוגונליים שזמינים למפתחי אפליקציות.
מומלץ לחשוף את אפקט הבוקה באמצעות מצב נוף מורחב וגם באמצעות Camera Extensions, כי יכול להיות שאפליקציות יעדיפו להשתמש בממשק API מסוים כדי להפעיל את אפקט הבוקה. מומלץ להשתמש קודם במצב נוף המורחב, כי זו הדרך הכי גמישה לאפליקציות להפעיל את תוסף אפקט בוקה. אחר כך תוכלו להטמיע את ממשק תוספי המצלמה על סמך מצב נוף מורחב. אם קשה להטמיע את אפקט הבוקה ב-HAL של המצלמה, למשל כי נדרש מעבד פוסט שפועל בשכבת האפליקציה כדי לעבד תמונות, מומלץ להטמיע את תוסף הבוקה באמצעות הממשק Camera Extensions.
שאלות נפוצות
יש הגבלות על רמות API?
כן. זה תלוי בקבוצת התכונות של Android API שנדרשת להטמעה של ספריית הספק של יצרן הציוד המקורי. לדוגמה, הפקודה ExtenderStateListener.onPresetSession() משתמשת בקריאה SessionConfiguration.setSessionParameters() כדי להגדיר קבוצת תגים בסיסית. הקריאה הזו זמינה רק ברמת API 28 ומעלה. פרטים על שיטות ספציפיות בממשק מופיעים במאמרי העזרה של ה-API.