ב-Android 13 הוצגה ספרייה סטטית שניתנת להגדרה על ידי הספק, שנקראת libtonemap. הספרייה הזו מגדירה פעולות של מיפוי גוונים ומשותפת לתהליך SurfaceFlinger ולהטמעות של Hardware Composer (HWC).
התכונה הזו מאפשרת ליצרני ציוד מקורי (OEM) להגדיר ולשתף את האלגוריתמים שלהם למיפוי גוונים של התצוגה בין המסגרת לבין הספקים, וכך לצמצם את אי ההתאמה במיפוי הגוונים.
לפני Android 13, פעולות מיפוי טונים ספציפיות לתצוגה לא שותפו בין HWC, SurfaceFlinger ואפליקציות. בהתאם לנתיב העיבוד, תוכן HDR הוביל לחוסר התאמה באיכות התמונה, שבה תוכן HDR עבר מיפוי טונים למרחב פלט בדרכים שונות. ההבדל הזה היה מורגש בתרחישים כמו סיבוב המסך, שבהם אסטרטגיית הקומפוזיציה משתנה בין ה-GPU לבין ה-DPU, ובהבדלים בהתנהגות העיבוד בין TextureView לבין SurfaceView.
בדף הזה מוסבר על הממשק, ההתאמה האישית ופרטי האימות של הספרייה libtonemap.
ממשק לספריית מיפוי הגוונים
הספרייה libtonemap מכילה הטמעות שמגובות על ידי CPU ו-shaders של SkSL, שאפשר לחבר אותם על ידי SurfaceFlinger להרכבה של קצה עורפי של GPU, ועל ידי HWC ליצירת טבלת בדיקה (LUT) של מיפוי טונים. נקודת הכניסה ל-libtonemap היא android::tonemap::getToneMapper(), שמחזירה אובייקט שמיישם את הממשק ToneMapper.
ממשק ToneMapper תומך ביכולות הבאות:
יצירת טבלת מיפוי טונים
הממשק
ToneMapper::lookupTonemapGainהוא הטמעה של shader ב-CPU שהוגדר ב-libtonemap_LookupTonemapGain(). הוא משמש לבדיקות יחידה במסגרת, ושותפים יכולים להשתמש בו כדי לקבל עזרה ביצירת LUT למיפוי גוונים בתוך צינור הצבעים שלהם.הפונקציה
libtonemap_LookupTonemapGain()מקבלת ערכי צבע במרחב לינארי לא מנורמל, גם ב-RGB לינארי וגם ב-XYZ, ומחזירה ערך מסוג float שמתאר בכמה צריך להכפיל את צבעי הקלט במרחב לינארי.יצירת הצללה של SkSL
הממשק
ToneMapper::generateTonemapGainShaderSkSL()מחזיר מחרוזת של הצללה ב-SkSL, בהינתן מרחב נתונים של מקור ויעד. ה-shader של SkSL מחובר להטמעה של Skia ב-RenderEngine, רכיב ההרכבה המואץ על ידי GPU של SurfaceFlinger. ה-shader מחובר גם ל-libhwui, כדי שמיפוי הטונים מ-HDR ל-SDR יוכל להתבצע ביעילות עבורTextureView. מחרוזת שנוצרת מוטמעת ב-SkSL shaders אחרים שבהם נעשה שימוש ב-Skia, ולכן ה-shader צריך לעמוד בכללים הבאים:- מחרוזת ה-shader צריכה לכלול נקודת כניסה עם החתימה
float libtonemap_LookupTonemapGain(vec3 linearRGB, vec3 xyz), כאשרlinearRGBהוא הערך של הניטים המוחלטים של פיקסלי ה-RGB במרחב לינארי, ו-xyzהואlinearRGBשהומר ל-XYZ. - לכל שיטות העזר שבהן נעשה שימוש במחרוזת ה-shader צריך להוסיף את הקידומת
libtonemap_כדי שלא יהיה ניגוד בין הגדרות ה-shader של המסגרת. באופן דומה, התחילית של נתוני קלט אחידים צריכה להיותin_libtonemap_.
- מחרוזת ה-shader צריכה לכלול נקודת כניסה עם החתימה
יצירת משתנים אחידים של SkSL
הממשק
ToneMapper::generateShaderSkSLUniforms()מחזיר את הנתונים הבאים, בהינתן מטא-נתוניםstructשמתארים מטא-נתונים מסטנדרטים שונים של HDR ותנאי תצוגה:רשימה של משתנים אחידים שקשורים ל-shader של SkSL.
הערכים האחידים
in_libtonemap_displayMaxLuminanceו-in_libtonemap_inputMaxLuminance. הערכים האלה משמשים את ה-shaders של המסגרת כשמבצעים שינוי קנה מידה של הקלט ל-libtonemap, ומנרמלים את הפלט לפי הצורך.
בשלב הזה, התהליך של יצירת משתני Uniform לא תלוי במרחב הנתונים של הקלט והפלט.
התאמה אישית
הטמעת ההפניה של ספריית libtonemap מניבה תוצאות מקובלות. עם זאת, יכול להיות שהאלגוריתם למיפוי טונים שמשמש להרכבה ב-GPU יהיה שונה מזה שמשמש להרכבה ב-DPU, ולכן שימוש בהטמעה לדוגמה עלול לגרום להבהוב בתרחישים מסוימים, כמו אנימציית סיבוב. התאמה אישית יכולה לפתור בעיות כאלה באיכות התמונה שספציפיות לספק.
מומלץ מאוד ליצרני ציוד מקורי (OEM) לבטל את ההטמעה של libtonemap כדי להגדיר מחלקת משנה משלהם של ToneMapper, שמוחזרת על ידי getToneMapper().
כשמבצעים התאמה אישית של ההטמעה, השותפים צריכים לבצע אחת מהפעולות הבאות:
- לשנות את ההטמעה של
libtonemapישירות. - להגדיר ספרייה סטטית משלהם, לקמפל את הספרייה כספרייה עצמאית ולהחליף את הקובץ
libtonemapשל הספרייה.aבקובץ שנוצר מהספרייה המותאמת אישית שלהם.
הספקים לא צריכים לשנות קוד ליבה, אבל כמה ספקים צריכים להעביר פרטים על אלגוריתמים למיפוי טונים של DPU כדי להטמיע אותם בצורה נכונה.
אימות
כדי לאמת את ההטמעה:
הפעלה של סרטוני HDR במסך בכל תקן HDR שמערכת התצוגה תומכת בו, כמו HLG, HDR10, HDR10+ או DolbyVision.
כדאי להפעיל או להשבית את ההגדרה 'הוספת שכבות על ידי GPU' כדי לוודא שלא יהיו הבהובים שמשתמשים יוכלו לראות.
משתמשים בפקודה
adbהבאה כדי להפעיל או להשבית את ההרכבה של ה-GPU:adb shell service call SurfaceFlinger 1008 i32 <0 to enable HWC composition, 1 to force GPU composition>
בעיות נפוצות
יכולות להתרחש הבעיות הבאות בהטמעה הזו:
התופעה של פסים נוצרת כשדיוק היעד של הרינדור שמשמש להרכבת ה-GPU נמוך מהערך הרגיל של תוכן HDR. לדוגמה, יכול להיות שיופיעו פסי צבע אם הטמעה של HWC תומכת בפורמטים אטומים של 10 ביט ל-HDR כמו RGBA1010102 או P010, אבל דורשת שהכתיבה של קומפוזיציית ה-GPU תהיה בפורמט של 8 ביט כמו RGBA8888 כדי לתמוך באלפא.
שינוי צבע עדין נגרם מהבדלים בכמות המידע אם ה-DPU פועל ברמת דיוק שונה מזו של ה-GPU.
כל אחת מהבעיות האלה קשורה להבדלים בדיוק היחסי של החומרה הבסיסית. פתרון עקיף נפוץ הוא לוודא שיש שלב של דית'רינג (dithering) בנתיבים עם דיוק נמוך יותר, כך שההבדלים בדיוק פחות מורגשים.