خدمات پلاگین صوتی خودرو

سرویس‌های افزونه جدید خودرو OEM در اندروید ۱۴ امکان پیکربندی برخی از اجزای خودرو را فراهم می‌کنند. به طور خاص برای صدا، سه سرویس افزونه جدید معرفی شده‌اند که به OEMها امکان می‌دهند مدیریت صدا را در دستگاه‌های AAOS به صورت انعطاف‌پذیر پیکربندی کنند:

  • کنترل فوکوس صوتی
  • کنترل صدا و قطع صدا
  • کنترل حذف نویز صوتی

معماری سرویس افزونه خودرو

شکل زیر نمای کلی از خدمات خودرو و ارتباط آنها با خدمات خودرو OEM را ارائه می‌دهد. مشابه فرآیندهای برنامه و فرآیند خدمات خودرو، فرآیند خدمات خودرو OEM فضای فرآیندی خاص خود را اشغال می‌کند.

تصویر

سرویس Car با پیدا کردن کامپوننت تعریف شده در config_oemCarService ، سرویس OEM car را اجرا می‌کند. اگر config خالی باشد، سرویس OEM وجود ندارد و هیچ سرویسی اجرا نمی‌شود. این کامپوننت باید OemCarService را ارث‌بری کند. سرویس صوتی خودرو باید APIها را برای دریافت سرویس OEM صوتی خودرو بازنویسی کند:

public final class OemCarServiceImp extends OemCarService {
    @Override
    public OemCarAudioFocusService getOemAudioFocusService();

    @Override
    public OemCarAudioDuckingService getOemAudioDuckingService();

    @Override
    public OemCarAudioVolumeService getOemAudioVolumeService();
}

برای مثال ، به برنامه تست مرجع تعریف شده در packages/services/Car/tests/OemCarServiceTestApp مراجعه کنید.

اگرچه این سرویس توسط سرویس خودرو آغاز می‌شود، اما به طور خودکار مجوزهای موجود برای سرویس صوتی خودرو را به ارث نمی‌برد. به همین دلیل، هرگونه مجوز مورد نیاز توسط سرویس‌های OEM باید با مکانیزم مناسب اخذ شود. برای مثال، به packages/services/Car/data/etc/com.android.car.oemcarservice.testapp.xml مراجعه کنید.

خدمات صوتی خودرو با معماری سرویس OEM

در AAOS، سرویس صوتی خودرو این اقدامات را مدیریت می‌کند:

  • مسیریابی صوتی
  • تمرکز صوتی
  • حذف نویز صوتی
  • صدا و قطع صدا

قبل از اندروید ۱۴، این رفتار تا حد زیادی ثابت بود و فقط از طریق تنظیمات قابل تغییر بود، البته برای موارد بسیار محدود. اندروید ۱۴ مکانیزمی را برای سرویس صوتی خودرو معرفی کرد تا با یک جزء تعریف شده توسط OEM ارتباط برقرار کند که موارد زیر را مدیریت می‌کند:

  • تمرکز صوتی
  • حذف نویز صوتی
  • صدا و قطع صدا

شکل زیر یک معماری ساده‌شده برای سرویس صوتی خودرو و سرویس OEM خودرو را نشان می‌دهد. سرویس صوتی خودرو، هوک‌های مختلفی را تعریف می‌کند که می‌توانند سرویس صوتی OEM خودرو را برای مدیریت رفتار صوتی فراخوانی کنند. مورد دوم فقط در صورتی رخ می‌دهد که کامپوننت سرویس صوتی خودرو OEM مربوطه تعریف شده باشد. در غیر این صورت، سرویس صوتی خودرو از رفتار پیش‌فرض استفاده می‌کند.

تصویر

برای اطمینان از اینکه سرویس صوتی خودرو و سرویس صوتی OEM خودرو همیشه همگام هستند، برای هر تماس، سرویس صوتی خودرو بخش‌های مورد نیاز از وضعیت فعلی پشته صوتی را به سرویس صوتی OEM خودرو ارسال می‌کند. به عنوان مثال، هنگامی که سرویس صوتی خودرو درخواستی برای ارزیابی فوکوس صوتی را دریافت می‌کند، وضعیت فعلی پشته را به سرویس صوتی OEM خودرو ارسال می‌کند. وضعیت فعلی شامل دارنده فوکوس فعلی و از دست دهندگان فوکوس فعلی است. از دست دهندگان فوکوس، درخواست‌های فوکوسی هستند که هنوز بخشی از پشته هستند اما موقتاً فوکوس خود را از دست داده‌اند.

سرویس صوتی خودرو باید تمام فعالیت‌های صوتی در خودرو را مدیریت کند. اگر سرویس صوتی خودرو برخی از بخش‌های رفتار صوتی را مدیریت نکند، اطلاعات ارائه شده به سرویس صوتی OEM خودرو ناقص خواهد بود. به عنوان مثال، اگر یک OEM با ثبت سیاست فوکوس صوتی خود، نحوه مدیریت فوکوس صوتی در سرویس خودرو را بازنویسی کند، سرویس صوتی خودرو نمی‌تواند اطلاعات کاملی را به سرویس صوتی OEM خودرو ارائه دهد. این امر می‌تواند بر توانایی سرویس صوتی OEM خودرو در تصمیم‌گیری تأثیر بگذارد، زیرا ممکن است فاقد اطلاعاتی باشد که برای سرویس صوتی خودرو قابل مشاهده نیست.

برای انجام اقدامات، سرویس صوتی خودرو، سرویس‌های خودروی OEM را فراخوانی می‌کند. این فراخوانی‌ها در سراسر فرآیندها انجام می‌شوند که نیاز به ارتباط بین فرآیندی (IPC) دارد. IPC به هر فراخوانی تأخیر اضافه می‌کند. به حداقل رساندن تأخیر در سرویس OEM بسیار مهم است.

از آنجایی که فراخوانی‌های سرویس صوتی خودرو به سرویس OEM مسدود شده‌اند، سرویس OEM نباید سرویس صوتی خودرو را در ارزیابی‌های مستقیم API فراخوانی کند. در عوض، سرویس صوتی خودرو اطلاعات لازم را فراهم می‌کند تا فراخوانی‌های بین دو فرآیند فقط در یک جهت انجام شوند.

تعاریف خدمات صوتی خودرو OEM

خدمات فوکوس صوتی خودرو OEM

سرویس صوتی خودرو، درخواست‌های فوکوس صوتی از برنامه‌ها را با ثبت یک شنونده فوکوس سیاست صوتی مدیریت می‌کند. سرویس صوتی خودرو مکانیزمی برای مدیریت رفتار فوکوس بر اساس یک ماتریس تعامل استاتیک دارد. این ماتریس سه نوع تعامل مختلف را تعریف می‌کند:

  • تعامل همزمان. دارندگان تمرکز می‌توانند همزمان تمرکز خود را حفظ کنند.

  • تعاملات انحصاری. درخواست فوکوس ورودی، فوکوس را از دارنده فوکوس فعلی می‌گیرد.

  • رد تعامل. درخواست فوکوس ورودی بر اساس دارنده فوکوس فعلی رد شد.

اگرچه این برای برخی موارد استفاده در خودرو کافی است، اما تمام نیازهای تعاملی را که ممکن است به دلیل الزامات OEM متفاوت باشد، برآورده نمی‌کند. برای این منظور OemCarAudioFocusService را معرفی می‌کنیم:

public interface OEmCarAudioFocusService {
    OemCarAuddioFocusResults evaluateAudioFocusRequest(
        OemCarAudioFocusEvaluationRequest request);
    
    void notifyAudioFocusChange(
        List<AudioFocusEntry> holder,
        List<AudioFocusEntry> losers, int zoneId);
}

API evaluateAudioFocusRequest هر زمان که درخواستی برای فوکوس صوتی وجود داشته باشد که نیاز به ارزیابی داشته باشد، از سرویس صوتی خودرو فراخوانی می‌شود. این یک API دو طرفه است که برای بازگرداندن نتایج، بلوک‌هایی را ایجاد می‌کند. این درخواست شامل اطلاعاتی در مورد وضعیت فعلی پشته صوتی است:

این اطلاعات می‌تواند برای ارزیابی newFocusRequest در مقایسه با دارندگان فوکوس فعلی در focusHolders و بازندگان فوکوس فعلی در focusLosers استفاده شود. API باید نتایج زیر را برگرداند:

class OemCarAudioFocusResult {
    int audioZoneId;
    int audioFocusEvaluationResults;
    AudioFocusEntry focusResult;
    List<AudioFocusEntry> newLosers;
    List<AudioFocusEntry> newlyBlocked;
}

این شامل اطلاعات مربوط به نتایج ارزیابی واقعی در audioFocusEvaluationResults است که نشان می‌دهد آیا درخواست فعلی اعطا شده، به تأخیر افتاده یا شکست خورده است. هرگونه تغییر در پشته تمرکز فعلی باید بسته به ماهیت تغییر پشته، در ورودی‌های newLosers و newlyBlocked تنظیم شود.

جایی که newLosers شامل ورودی‌هایی است که قبلاً فوکوس را نگه می‌داشتند اما اکنون باید فوکوس را از دست بدهند، چه به صورت دائمی و چه به صورت گذرا. بازنده‌های فوکوس دائمی از پشته فوکوس صوتی بیشتر حذف می‌شوند و بازنده‌های فوکوس گذرا به پشته فوکوس بازنده‌های فعلی منتقل می‌شوند تا زمانی که فوکوس را دوباره به دست آورند یا از درخواست‌کننده فوکوس اصلی رها شوند. صرف نظر از این، شنونده فوکوس برای درخواست‌ها، فوکوس از دست رفته مربوطه را دریافت خواهد کرد.

لیست newlyBlocked شامل ورودی‌هایی است که قبلاً در لیست از دست دادن تمرکز بودند اما اکنون توسط ورودی جدید مسدود شده‌اند. این مسدود شدن می‌تواند دائمی یا گذرا باشد، برای مسدود شدن دائمی تمرکز، ورودی از پشته حذف می‌شود و از دست دادن تمرکز به شنونده‌های تمرکز ارسال می‌شود. برای از دست دادن تمرکز گذرا، ورودی در پشته از دست دادن تمرکز باقی می‌ماند اما یک مسدودکننده تمرکز جدید به لیست مسدودکننده‌های آن اضافه می‌شود، هیچ از دست دادن تمرکزی مانند آنچه قبلاً هنگام اولین مسدود شدن ارسال شده بود، ارسال نمی‌شود. درخواست در نهایت زمانی که همه مسدودکننده‌های فعلی حذف شوند، از حالت مسدود خارج می‌شود، یا اگر تمرکز رها شود، از پشته حذف می‌شود.

API دوم، notifyAudioFocusChange ، یک API تک‌راهه است که در هر درخواست فوکوس یا رها کردن صدا فراخوانی می‌شود. این API عمدتاً برای اطلاع‌رسانی به سرویس OEM در مورد تغییرات فوکوس استفاده می‌شود که ممکن است بر رفتار سرویس صوتی خودرو OEM تأثیر بگذارد.

دستورالعمل‌هایی برای ارزیابی تمرکز

در AAOS، از فوکوس صوتی برای مدیریت پخش صدا و تعیین اینکه کدام برنامه باید برای ارائه یک تجربه بهینه برای کاربر رعایت شود، استفاده می‌شود. به همین ترتیب، سرویس افزونه OEM باید هنگام مدیریت درخواست فوکوس صوتی موارد زیر را در نظر بگیرد:

  • بدون هیچ گونه فوکوس صوتی با اولویت بالا (مانند تماس تلفنی، موارد اضطراری یا ایمنی)، برنامه‌ها باید بتوانند فوکوس صوتی را به صورت گذرا یا دائمی به دست آورند.

  • در حالی که تمرکز رسانه‌ای فعال است، برنامه‌ها درخواست می‌کنند:

    • تمرکز استفاده از تماس، باید بتواند تمرکز را به صورت همزمان یا انحصاری دریافت کند.

    • تمرکز استفاده از ناوبری، باید بتواند تمرکز را به صورت همزمان یا انحصاری دریافت کند.

    • دستیار هنگام استفاده از فوکوس، باید بتواند فوکوس را به صورت همزمان یا انحصاری دریافت کند.

  • در حالی که برنامه‌های فوکوس صوتی با اولویت بالا (مانند تماس تلفنی، هشدار اضطراری یا هشدار ایمنی) فعال هستند، هرگونه درخواست فوکوس صوتی با تأخیر ورودی باید در صورت لزوم پذیرفته شود یا به تأخیر بیفتد.

اگرچه پیشنهادات بالا جامع نیستند، اما می‌توانند تضمین کنند که برنامه‌هایی که درخواست فوکوس می‌کنند، باید بتوانند در صورت عدم وجود صداهای با اولویت بالا، فوکوس را دریافت کنند. حتی در حالی که صداهای با اولویت بالا فعال هستند، درخواست‌های فوکوس با تأخیر همچنان باید رعایت شوند و باید بتوانند پس از قطع صدای با اولویت بالا، فوکوس را دریافت کنند.

خدمات حجم خودرو OEM

سرویس صوتی خودرو، رویدادهای کلید صدا را یا با گوش دادن به تنظیمات صدا از سیستم صوتی یا با گوش دادن به رویدادهای کلید صدا مستقیماً از سرویس ورودی خودرو مدیریت می‌کند. در هر مورد، رفتار پیش‌فرض سرویس صوتی خودرو این است که بر اساس پخش‌کننده‌های صوتی فعال و فهرست اولویت‌های زمینه صوتی، تعیین کند کدام گروه صدا را تغییر دهد.

ما دو لیست اولویت صدا ارائه می‌دهیم. لیست اول تمام زمینه‌های صوتی را به این ترتیب در نظر می‌گیرد. این لیست به ترتیب نزولی ارائه می‌شود، بالاترین اولویت در بالا و پایین‌ترین اولویت در پایین. به عنوان مثال، اگر صدای ناوبری و صدای موسیقی هر دو همزمان فعال باشند، در طول یک رویداد کلید صدا، صدای ناوبری تغییر می‌کند.

  1. ناوبری
  2. تماس بگیرید
  3. موسیقی
  4. اطلاعیه
  5. فرمان صوتی
  6. زنگ تماس
  7. صدای سیستم
  8. ایمنی
  9. زنگ هشدار
  10. اعلان
  11. وضعیت خودرو
  12. اورژانس

برای اینکه مدیریت رویدادهای مربوط به کلید صدا ساده‌تر شود، سرویس صوتی خودرو فهرستی از زمینه‌های صوتی با اولویت دوم دارد:

  1. تماس بگیرید
  2. رسانه
  3. اطلاعیه
  4. فرمان صوتی

این لیست همچنین به ترتیب نزولی ارائه شده است. هدف از این لیست دوم، امکان تغییر صداهای رایج‌تر از طریق رویدادهای کلیدی است. صداهای غیرمعمول، شاید با مدت زمان کوتاه‌تر، فقط از طریق رابط کاربری تنظیمات صوتی قابل مدیریت هستند.

نسخه واقعی صدا را می‌توان با پیکربندی audioVolumeAdjustmentContextsVersion تنظیم کرد. این پیکربندی را می‌توان روی 1 یا 2 تنظیم کرد ( 2 پیش‌فرض است).

برای ارائه انعطاف‌پذیری بیشتر در مدیریت صدا، OemCarAudioVolumeService در اندروید ۱۴ معرفی شده است:

public interface OemCarAudioVolumeService {
    OemCarvolumeChangeInfo getSuggestedGroupForVolumeChange(
OemCarAudioVolumeRequest request, int volumeAdjustment);
}

سرویس تنظیم صدای سیستم صوتی خودرو OEM یک متد واحد دارد که یک volumeAdjustment و یک OemCarAudioVolumeRequest را دریافت می‌کند:

class OemCarAudioVolumeRequest {
    int audioZoneId;
    int callState;
    List<AudioAttributes> activePlaybackAttributes;
    List<AudioAttributes> duckedAttributes;
    List<CarVolumeGroupInfo> volumeGroupState;
}

activePlaybackAttributes درخواست، ویژگی‌های صوتی فعال را دارد. duckedAttributes همگی ویژگی‌های صوتی در حال حاضر ducked هستند. volumeGroupState وضعیت فعلی گروه volume را دارد. درخواست، وضعیت فعلی پشته صوتی را نشان می‌دهد و می‌تواند برای تعیین اینکه کدام گروه volume باید تغییر کند، استفاده شود. نتایج باید در OemCarVolumeChangeInfo برگردانده شوند:

class OemCarVolumeChangeInfo {
    boolean change;
    CarVolumeGroupInfo volumeGroupChanged;
}

مقدار بولی change نشان می‌دهد که آیا هر volume تغییر کرده است یا خیر، true نشان می‌دهد که تغییری وجود دارد و volume group باید به‌روزرسانی شود. volumeGroupChanged گروه volume واقعی است که باید تغییر کند. این گروه باید مطابق پارامتر volumeAdjustment اصلی که به API ارسال می‌شود، تغییر کند. برای مثال، اگر نتایج نشان دهد که گروه volume ناوبری باید بی‌صدا شود، مقدار boolean برابر true خواهد بود و volume group برگردانده شده باید همان گروه volume مربوط به ناوبری باشد.

خدمات تخلیه خودرو OEM

سرویس صوتی خودرو، با نظارت بر تغییرات فوکوس صوتی و ارسال سیگنالی به AudioControl HAL در مورد اینکه کدام دستگاه‌های صوتی باید از فوکوس خارج شوند، حذف نویز صوتی را مدیریت می‌کند. هنگامی که فوکوس تغییر می‌کند، تمام دارندگان فوکوس فعال ارزیابی می‌شوند تا مشخص شود کدام یک باید بر اساس این مجموعه از قوانین استاتیک حذف نویز، حذف شوند:

  • صداهای اضطراری همه چیز را به جز صداهای تماس، محو می‌کنند
  • ایمنی همه چیز را به جز صداهای اضطراری نادیده می‌گیرد
  • سیستم ناوبری همه چیز را به جز صداهای ایمنی و اضطراری حذف می‌کند
  • همه چیز را به جز صداهای ایمنی، اضطراری و ناوبری، اردک صدا بزنید
  • صدای اردک‌ها، زنگ تلفن را به صدا درمی‌آورد
  • موسیقی و اعلان‌ها باید از همه چیز حذف شوند

این قوانین جامع نیستند و تولیدکنندگان اصلی تجهیزات (OEM) همچنان مسئول تعیین چگونگی کاهش صداها بر اساس این دستورالعمل‌ها هستند. تولیدکنندگان اصلی تجهیزات می‌توانند این توصیه‌ها را بر اساس الزامات موجود، فعالانه‌تر کنترل کنند. OemCarDuckingService در اندروید ۱۴ معرفی شده است:

class OemCarAudioDuckingService {
List<AudioAttributes>   evaluateAttributesToDuck(
        OemCarAudioVolumeRequest request);
}

این API هنگام تغییر فوکوس صدا از سرویس صدای خودرو فراخوانی می‌شود. این API از OemCarAudioVolumeRequest معرفی شده در سرویس صدای خودرو OEM استفاده می‌کند و شامل اطلاعات مرتبط برای تصمیم‌گیری در مورد اینکه کدام ویژگی‌ها باید حذف شوند، می‌باشد. لیست ویژگی‌های صوتی که باید از API حذف شوند با وضعیت صدای فعلی مقایسه می‌شود:

  • ویژگی صوتی در حال حاضر غیرفعال است:

    • در فهرست، همچنان از فهرست خارج می‌شود
    • در لیست نیست، حرکت به چپ و راست غیرفعال است
  • ویژگی صوتی در حال حاضر غیرفعال است:

    • در لیست، جاخالی داد
    • در لیست نیست، حرکت به چپ و راست غیرفعال است

سپس سرویس صوتی خودرو تعیین می‌کند که ویژگی‌های صوتی به کدام دستگاه‌های خروجی صوتی تعلق دارند و آنها را به ترتیب به لیست دستگاه‌های خروجی صوتیِ حذف‌شده یا لیست دستگاه‌های صوتیِ حذف‌شده اضافه می‌کند. این اطلاعات در نهایت به AudioControl HAL ارسال می‌شود تا حذف موردنیاز را در سطح سخت‌افزار انجام دهد.

شکل زیر یک نمودار توالی ساده‌شده از کنترل کاهش نویز صدا برای یک درخواست فوکوس را هنگام استفاده از سرویس کاهش نویز OEM نشان می‌دهد:

تصویر

این توالی زمانی شروع می‌شود که یک برنامه از طریق APIهای مدیریت صوتی عمومی، درخواست مدیریت فوکوس صوتی را می‌دهد. این درخواست برای تعیین نتایج به سرویس صوتی خودرو ارسال می‌شود. هنگامی که فوکوس صوتی تعیین شد، کاهش فاصله صوتی توسط سرویس صوتی خودرو که OemCarAudioDuckingService را فراخوانی می‌کند، ارزیابی می‌شود تا مشخص شود کدام ویژگی‌های صوتی باید کاهش فاصله داشته باشند. پس از بازگشت نتایج از API evaluateAttributesToDuck ، دستگاه‌های صوتی که باید کاهش فاصله داشته باشند محاسبه می‌شوند و در نهایت اطلاعات به AudioControl ارسال می‌شود تا کاهش فاصله را روی سخت‌افزار صوتی اعمال کند.

پیاده‌سازی مرجع خدمات صوتی خودرو OEM

AAOS یک پیاده‌سازی مرجع از سرویس OEM car در packages/services/Car/tests/OemCarServiceTestApp ارائه می‌دهد که OemCarService را به همراه OemCarAudioFocusService ، OemCarAudioDuckingService و OemCarAudioVolumeService پیاده‌سازی می‌کند. برای مورد دوم، هر سرویس از یک فایل XML برای بارگذاری یک رفتار استاتیک استفاده می‌کند. به عنوان مثال، OemCarAudioFocusServiceImp فایل oem_focus_config.xml را بارگذاری می‌کند که حاوی یک ماتریس تعامل است. این ماتریس برای ارزیابی درخواست focus هنگام فراخوانی evaluateAudioFocusRequest استفاده می‌شود.

اشکال‌زدایی برنامه تست مرجع

برنامه تست سرویس خودرو OEM بخشی از کد منبع AOSP است. OEMها می‌توانند بسته به نیاز خود تغییراتی در آن ایجاد کنند. برای اشکال‌زدایی، از پیکربندی config_oemCarService برای فعال کردن برنامه تست استفاده کنید.

<!-- This is the component name for the OEM customization service. OEM can choose to implement
this service to customize car service behavior for different policies. If OEMs choose to
implement it, they have to implement a service extending OemCarService exposed by car-lib,
and implement the required component services.
If the component name is invalid, CarService would not connect to any OEM service.
Component name can not be a third party package. It should be pre-installed -->
<string name="config_oemCarService" translatable="false">
com.android.car.oemcarservice.testapp/.OemCarServiceImpl
</string>

برای تأیید سرویس OEM car از دستور car service dump برای سرویس OEM استفاده کنید:

adb shell dumpsys car_service --oem-service

نتایج می‌تواند مشابه خروجی زیر باشد:

***CarOemProxyService dump***
  mIsFeatureEnabled: true
  mIsOemServiceBound: true
  mIsOemServiceReady: true
  mIsOemServiceConnected: true
  mInitComplete: true
  OEM_CAR_SERVICE_CONNECTED_TIMEOUT_MS: 5000
  OEM_CAR_SERVICE_READY_TIMEOUT_MS: 5000
  mComponentName: com.android.car.oemcarservice.testapp/.OemCarServiceImpl

هر مقدار بولی در هر دسته از اطلاعات dump وضعیت ویژگی و سرویس را تعیین می‌کند. برای مثال، dump info mIsOemServiceReady مشخص می‌کند که آیا سرویس آماده استفاده است یا خیر، که در آن true نشان دهنده آماده بودن و false نشان دهنده آماده نبودن است.