diff --git a/InCallUI/res/values-af/strings.xml b/InCallUI/res/values-af/strings.xml
deleted file mode 100644
index 181ffce66316248791764a92c81424ecb07ff6cb..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-af/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Foon"
- "Hou aan"
- "Onbekend"
- "Privaat nommer"
- "Telefoonhokkie"
- "Konferensie-oproep"
- "Oproep is ontkoppel"
- "Luidspreker"
- "Selfoonoorfoon"
- "Bedraade kopfoon"
- "Bluetooth"
- "Stuur die volgende luitone?\n"
- "Stuur luitone\n"
- "Stuur"
- "Ja"
- "Nee"
- "Vervang die plekhouerkarakter met"
- "Konferensie-oproep %s"
- "Stemboodskapnommer"
- "Bel"
- "Bel tans weer"
- "Konferensie-oproep"
- "Inkomende oproep"
- "Inkomende werkoproep"
- "Oproep beëindig"
- "Hou aan"
- "Lui af"
- "In oproep"
- "My nommer is %s"
- "Koppel tans video"
- "Video-oproep"
- "Versoek tans video"
- "Kan nie video-oproep koppel nie"
- "Videoversoek is verwerp"
- "Jou terugbelnommer\n %1$s"
- "Jou noodterugbelnommer\n %1$s"
- "Bel"
- "Gemiste oproep"
- "Gemiste oproepe"
- "%s gemiste oproepe"
- "Gemiste oproep vanaf %s"
- "Voortdurende oproep"
- "Voortdurende werkoproep"
- "Voortdurende Wi-Fi-oproep"
- "Voortdurende Wi-Fi-werkoproep"
- "Hou aan"
- "Inkomende oproep"
- "Inkomende werkoproep"
- "Inkomende Wi-Fi-oproep"
- "Inkomende Wi-Fi-werkoproep"
- "Inkomende video-oproep"
- "Inkomende verdagte strooipos-oproep"
- "Inkomende videoversoek"
- "Nuwe stemboodskap"
- "Nuwe stemboodskap (%d)"
- "Bel %s"
- "Stemboodskapnommer is onbekend"
- "Geen diens nie"
- "Gekose netwerk (%s) is nie beskikbaar nie"
- "Antwoord"
- "Lui af"
- "Video"
- "Stem"
- "Aanvaar"
- "Maak toe"
- "Bel terug"
- "Boodskap"
- "Voortgesette oproep op \'n ander toestel"
- "Sit oproep deur"
- "Skakel vliegtuigmodus eers af om \'n oproep te maak."
- "Nie geregistreer op netwerk nie."
- "Sellulêre netwerk is nie beskikbaar nie."
- "Voer \'n geldige nommer in om \'n oproep te maak."
- "Kan nie bel nie."
- "Begin tans MMI-volgorde …"
- "Diens word nie gesteun nie."
- "Kan nie oproepe wissel nie."
- "Kan nie oproep skei nie."
- "Kan nie deurskakel nie."
- "Kan nie konferensie-oproep maak nie."
- "Kan nie oproep weier nie."
- "Kan nie oproep(e) vrystel nie."
- "SIP-oproep"
- "Noodoproep"
- "Skakel tans radio aan …"
- "Geen sein nie. Probeer tans weer …"
- "Kan nie bel nie. %s is nie \'n noodnommer nie."
- "Kan nie bel nie. Bel \'n noodnommer."
- "Gebruik sleutelbord om te bel"
- "Hou oproep"
- "Hervat oproep"
- "Beëindig oproep"
- "Wys belblad"
- "Versteek belblad"
- "Demp"
- "Ontdemp"
- "Voeg oproep by"
- "Smelt oproepe saam"
- "Ruil"
- "Bestuur oproepe"
- "Bestuur konferensie-oproep"
- "Konferensie-oproep"
- "Bestuur"
- "Oudio"
- "Video-oproep"
- "Verander na stemoproep"
- "Wissel kamera"
- "Skakel kamera aan"
- "Skakel kamera af"
- "Nog opsies"
- "Speler het begin"
- "Speler het gestop"
- "Kamera is nie gereed nie"
- "Kamera is gereed"
- "Onbekende oproepsessiegebeurtenis"
- "Diens"
- "Opstelling"
- "<Nie gestel nie>"
- "Ander oproepinstellings"
- "Bel via %s"
- "Inkomend via %s"
- "kontakfoto"
- "gaan privaat"
- "kies kontak"
- "Skryf jou eie …"
- "Kanselleer"
- "Stuur"
- "Antwoord"
- "Stuur SMS"
- "Weier"
- "Antwoord as video-oproep"
- "Antwoord as oudio-oproep"
- "Aanvaar videoversoek"
- "Weier videoversoek"
- "Aanvaar videoversendversoek"
- "Weier videoversendversoek"
- "Aanvaar video-ontvangversoek"
- "Weier video-ontvangversoek"
- "Gly op vir %s."
- "Gly links vir %s."
- "Gly regs vir %s."
- "Gly af vir %s."
- "Vibreer"
- "Vibreer"
- "Klank"
- "Verstekklank (%1$s)"
- "Foonluitoon"
- "Vibreer wanneer dit lui"
- "Luitoon en vibreer"
- "Bestuur konferensie-oproep"
- "Noodnommer"
- "Profielfoto"
- "Kamera is af"
- "via %s"
- "Nota is gestuur"
- "Onlangse boodskappe"
- "Besigheidinligting"
- "%.1f myl ver"
- "%.1f km ver"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Maak môre om %s oop"
- "Maak vandag om %s oop"
- "Maak om %s toe"
- "Het vandag om %s toegemaak"
- "Nou oop"
- "Nou gesluit"
- "Verdagte strooiposbeller"
- "Oproep het geëindig %1$s"
- "Dit is die eerste keer wat hierdie nommer jou bel."
- "Ons vermoed dat hierdie oproep strooipos was."
- "Blokkeer/gee strooipos aan"
- "Voeg kontak by"
- "Nie strooipos nie"
-
diff --git a/InCallUI/res/values-am/strings.xml b/InCallUI/res/values-am/strings.xml
deleted file mode 100644
index 99516cfec17dd730b8c27cd4db6975afa7737d7f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-am/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ስልክ"
- "ያዝና ቆይ"
- "ያልታወቀ"
- "የግል ቁጥር"
- "የሕዝብ ስልክ"
- "የስብሰባ ጥሪ"
- "ጥሪው ተቋርጧል"
- "ድምፅ ማጉያ"
- "የስልክ ጆሮ ማዳመጫ"
- "ባለ ገመድ የጆሮ ማዳመጫ"
- "ብሉቱዝ"
- "የሚከተሉትን የጥሪ ድምፆች ላክ?\n"
- "የጥሪ ድምፆች በመላክ ላይ \n"
- "ላክ"
- "አዎ"
- "አይ"
- "የልቅ ምልክት ተካ በ"
- "የስብሰባ ጥሪ %s"
- "የድምፅ መልእክት ቁጥር"
- "በመደወል ላይ"
- "ዳግም በመደወል ላይ"
- "የስብሰባ ጥሪ"
- "ገቢ ጥሪ"
- "ገቢ የሥራ ጥሪ"
- "ጥሪ አብቅቷል"
- "ያዝና ቆይ"
- "በመዝጋት ላይ"
- "ጥሪ ላይ"
- "ቁጥሬ %s ነው"
- "ቪድዮ በማገናኘት ላይ"
- "የቪዲዮ ጥሪ"
- "ቪድዮ በመጠየቅ ላይ"
- "የቪዲዮ ጥሪን ማገናኘት አይቻልም"
- "የቪዲዮ ጥያቄ ውድቅ ተደርጓል"
- "የእርስዎ የመልሶ መደወያ ቁጥር\n%1$s"
- "የእርስዎ የድንገተኛ አደጋ መልሶ መደወያ ቁጥር\n%1$s"
- "በመደወል ላይ"
- "ያመለጠ ጥሪ"
- "ያመለጡ ጥሪዎች"
- "%s ያመለጡ ጥሪዎች"
- "ያልተመለሰ ጥሪ ከ%s"
- "በሂደት ላይ ያለ ጥሪ"
- "በሂደት ላይ ያለ የሥራ ጥሪ"
- "በሂደት ላይ ያለ የWi-Fi ጥሪ"
- "በሂደት ላይ ያለ የWi-Fi የሥራ ጥሪ"
- "ያዝና ቆይ"
- "ገቢ ጥሪ"
- "ገቢ የሥራ ጥሪ"
- "ገቢ የWi-Fi ጥሪ"
- "ገቢ የWi-Fi የሥራ ጥሪ"
- "ገቢ የቪዲዮ ጥሪ"
- "መጪ የተጠረጠረ የአይፈለጌ መልዕክት ጥሪ"
- "ገቢ የቪዲዮ ጥያቄ"
- "አዲስ የድምፅ መልእክት"
- "አዲስ የድምፅ መልእክት (%d)"
- "ደውል %s"
- "የማይታወቅ የድምፅ መልእክት ቁጥር"
- "ምንም አገልግሎት የለም"
- "የተመረጠ አውታረመረብ (%s) አይገኝም"
- "መልስ"
- "ዝጋ"
- "ቪዲዮ"
- "ድምፅ"
- "ተቀበል"
- "አስወግድ"
- "መልሰህ ደውል"
- "መልእክት"
- "በሌላ መሳሪያ ጥሪ በመካሄድ ላይ ነው"
- "ጥሪ አስተላልፍ"
- "ለመደወል፣ መጀመሪያ የአውሮፕላኑን ሁኔታ ያጥፉ።"
- "በአውታረ መረቡ ላይ አልተመዘገበም።"
- "የተንቀሳቃሽ ስልክ አውታረ መረብ አይገኝም።"
- "አንድ ጥሪ ለማድረግ የሚሠራ ቁጥር ያስገቡ።"
- "መደወል አይቻልም።"
- "የMMI ቅደመ ተከተል በማስጀመር ላይ…"
- "አገልግሎት አይደገፍም።"
- "ጥሪዎችን መቀያየር አይቻልም።"
- "ጥሪን መለየት አይቻልም።"
- "ማስተላለፍ አይቻልም።"
- "የጉባዔ ጥሪ ማድረግ አይቻልም።"
- "ጥሪውን መዝጋት አይቻልም።"
- "ጥሪ(ዎች)ን መልቀቅ አይቻልም።"
- "የSIP ጥሪ"
- "የአስቸኳይ ጊዜ ጥሪ"
- "ሬዲዮ በማብራት ላይ…"
- "ምንም አገልግሎት የለም። ዳግም በመሞከር ላይ…"
- "መደወል አይቻልም። %s የአስቸኳይ አደጋ ቁጥር አይደለም።"
- "መደወል አይቻልም። ወደ የአስቸኳይ አደጋ ቁጥር ይደውሉ።"
- "ለመደወል የሰሌዳ ቁልፍ ተጠቀም"
- "ጥሪ አቆይ"
- "ጥሪ ቀጥል"
- "ጥሪ ጨርስ"
- "የመደወያ ሰሌዳ አሳይ"
- "የመደወያ ሰሌዳ ደብቅ"
- "ድምፅ-ከል አድርግ"
- "ድምፅ አታጥፋ"
- "ጥሪ ያክሉ"
- "ጥሪዎችን አዋህድ"
- "በውዝ"
- "ጥሪዎችን አደራጅ"
- "የስብሰባ ስልክ ጥሪ አደራጅ"
- "የስብሰባ ጥሪ"
- "ያስተዳድሩ"
- "ኦዲዮ"
- "የቪዲዮ ጥሪ"
- "ወደ ድምፅ ጥሪ ይለውጡ"
- "ካሜራ ቀይር"
- "ካሜራ ያብሩ"
- "ካሜራ ያጥፉ"
- "ተጨማሪ አማራጮች"
- "አጫዋች ጀምሯል"
- "አጫዋች ቆሟል"
- "ካሜራ ዝግጁ አይደለም"
- "ካሜራ ዝግጁ ነው"
- "ያልታወቀ የጥሪ ክፍለጊዜ ክስተት"
- "አገልግሎት"
- "አዋቅር"
- "<አልተዘጋጀም>"
- "ሌሎች የጥሪ ቅንብሮች"
- "በ%s በኩል በመደወል ላይ"
- "በ%s በኩል የመጣ"
- "የዕውቂያ ፎቶ"
- "ወደ ግላዊነት ሂድ"
- "ዕውቂያ ይምረጡ"
- "የእራስዎን ይጻፉ..."
- "ተወው"
- "ላክ"
- "መልስ"
- "ኤስኤምኤስ ላክ"
- "ውድቅ አድርግ"
- "እንደ ቪድዮ ጥሪ ይመልሱ"
- "እንደ ድምፅ ጥሪ ይመልሱ"
- "የቪዲዮ ጥያቄ ተቀበል"
- "የቪዲዮ ጥያቄ ውድቅ አድርግ"
- "የቪዲዮ አስተላልፍ ጥያቄን ተቀበል"
- "የቪዲዮ አስተላልፍ ጥያቄን ውድቅ አድርግ"
- "የቪዲዮ ተቀበል ጥያቄን ተቀበል"
- "የቪዲዮ ተቀበል ጥያቄን ውድቅ አድርግ"
- "ለ%s ወደ ላይ ያንሸራትቱ።"
- "ለ%s ወደ ግራ ያንሸራትቱ።"
- "ለ%s ወደ ቀኝ ያንሸራትቱ።"
- "ለ%s ወደ ታች ያንሸራትቱ።"
- "ንዘር"
- "ንዘር"
- "ድምፅ"
- "ነባሪ ድምፅ (%1$s)"
- "የስልክ ጥሪ ቅላጼ"
- "በሚደወልበት ጊዜ ንዘር"
- "የጥሪ ቅላጼ እና ንዘረት"
- "የስብሰባ ስልክ ጥሪ አደራጅ"
- "የአደጋ ጊዜ ቁጥር"
- "የመገለጫ ፎቶ"
- "ካሜራ ጠፍቷል"
- "በ%s በኩል"
- "ማስታወሻ ተልኳል"
- "የቅርብ ጊዜ መልእክቶች"
- "የንግድ መረጃ"
- "%.1f ማይል ርቀት ላይ"
- "%.1f ኪሜ ርቀት ላይ"
- "%1$s፣ %2$s"
- "%1$s - %2$s"
- "%1$s፣ %2$s"
- "ነገ %s ላይ ይከፈታል"
- "ዛሬ %s ላይ ይከፈታል"
- "%s ላይ ይዘጋል"
- "ዛሬ %s ላይ ተዘግቷል"
- "አሁን ክፍት ነው"
- "አሁን ዝግ ነው"
- "የተጠረጠረ አይፈለጌ ጠሪ"
- "ጥሪው አብቅቷል %1$s"
- "ይህ ቁጥር ለእርስዎ ሲደውል ይህ የመጀመሪያው ነው።"
- "ይህ ቁጥር አይፈለጌ ላኪ ነው ብለን እንገምታለን።"
- "አይፈለጌ አግድ/ሪፖርት አድርግ"
- "እውቂያ ያክሉ"
- "አይፈለጌ አይደለም"
-
diff --git a/InCallUI/res/values-ar/strings.xml b/InCallUI/res/values-ar/strings.xml
deleted file mode 100644
index e89f026b6f5f510322eece286a28303d2ca9ae4d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ar/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "الهاتف"
- "معلقة"
- "غير معروف"
- "رقم خاص"
- "هاتف بالعملة"
- "مكالمة جماعية"
- "تم قطع المكالمة"
- "السماعة"
- "سماعة الأذن للهاتف"
- "سماعة رأس سلكية"
- "بلوتوث"
- "هل تريد إرسال النغمات التالية؟\n"
- "إرسال النغمات\n"
- "إرسال"
- "نعم"
- "لا"
- "استبدال حرف البدل بـ"
- "مكالمة جماعية %s"
- "رقم البريد الصوتي"
- "جارٍ الطلب"
- "جارٍ إعادة الطلب"
- "مكالمة جماعية"
- "مكالمة واردة"
- "مكالمة عمل واردة"
- "تم إنهاء الاتصال"
- "معلقة"
- "جارٍ وقف المكالمة"
- "بصدد مكالمة"
- "رقمي %s"
- "جارٍ الاتصال بالفيديو"
- "مكالمة فيديو"
- "جارٍ طلب الفيديو"
- "يتعذر الاتصال بمكالمة فيديو"
- "تم رفض طلب الفيديو"
- "رقم معاودة الاتصال\n %1$s"
- "رقم معاودة اتصال الطوارئ\n %1$s"
- "جارٍ الطلب"
- "مكالمة فائتة"
- "المكالمات الفائتة"
- "%s من المكالمات الفائتة"
- "مكالمة فائتة من %s"
- "مكالمة حالية"
- "مكالمة عمل جارية"
- "مكالمة جارية عبر Wi-Fi"
- "مكالمة عمل جارية عبر Wi-Fi"
- "معلقة"
- "مكالمة واردة"
- "مكالمة عمل واردة"
- "مكالمة واردة عبر Wi-Fi"
- "مكالمة عمل واردة عبر اتصال Wi-Fi"
- "مكالمة فيديو واردة"
- "مكالمة واردة يشتبه في كونها غير مرغوب فيها"
- "طلب فيديو وارد"
- "بريد صوتي جديد"
- "بريد صوتي جديد (%d)"
- "طلب %s"
- "رقم البريد الصوتي غير معروف"
- "لا تتوفر خدمة"
- "الشبكة المحددة (%s) غير متاحة"
- "رد"
- "قطع الاتصال"
- "فيديو"
- "صوت"
- "قبول"
- "تجاهل"
- "معاودة الاتصال"
- "رسالة"
- "مكالمة جارية على جهاز آخر"
- "تحويل الاتصال"
- "لإجراء مكالمة، أوقف تشغيل وضع الطائرة أولاً."
- "غير مسجل على الشبكة."
- "شبكة الجوّال غير متاحة."
- "لإجراء مكالمة، أدخل رقمًا صالحًا."
- "يتعذر الاتصال."
- "جارٍ بدء تسلسل MMI…"
- "الخدمة ليست متوفرة."
- "يتعذر تبديل المكالمات."
- "يتعذر فصل المكالمة."
- "يتعذر النقل."
- "يتعذر إجراء مكالمة جماعية."
- "يتعذر رفض المكالمة."
- "يتعذر تحرير المكالمات."
- "مكالمة SIP"
- "مكالمة طوارئ"
- "جارٍ تشغيل اللاسلكي..."
- "لا تتوفر خدمة. جارٍ إعادة المحاولة…"
- "يتعذر الاتصال. لا يعد %s رقم طوارئ."
- "يتعذر الاتصال. يمكنك طلب رقم طوارئ"
- "استخدام لوحة المفاتيح للطلب"
- "تعليق المكالمة"
- "استئناف المكالمة"
- "إنهاء المكالمة"
- "عرض لوحة الاتصال"
- "إخفاء لوحة الاتصال"
- "تجاهل"
- "إلغاء التجاهل"
- "إضافة مكالمة"
- "دمج المكالمات"
- "تبديل"
- "إدارة المكالمات"
- "إدارة مكالمة جماعية"
- "مكالمة جماعية"
- "إدارة"
- "صوت"
- "مكالمة فيديو"
- "التغيير إلى مكالمة صوتية"
- "تبديل الكاميرا"
- "تشغيل الكاميرا"
- "إيقاف الكاميرا"
- "خيارات أخرى"
- "تم بدء المشغّل"
- "تم إيقاف المشغّل"
- "الكاميرا غير جاهزة"
- "الكاميرا جاهزة"
- "حدث جلسة اتصال غير معروف"
- "الخدمة"
- "الإعداد"
- "<لم يتم التعيين>"
- "إعدادات الاتصال الأخرى"
- "الاتصال عبر %s"
- "واردة عبر %s"
- "صورة جهة الاتصال"
- "انتقال إلى مكالمة خاصة"
- "تحديد جهة اتصال"
- "اكتب ردك…"
- "إلغاء"
- "إرسال"
- "الرد"
- "إرسال رسالة قصيرة SMS"
- "الرفض"
- "الرد بمكالمة فيديو"
- "الرد بمكالمة صوتية"
- "قبول طلب الفيديو"
- "رفض طلب الفيديو"
- "قبول طلب بث الفيديو"
- "رفض طلب بث الفيديو"
- "قبول طلب استلام مكالمة الفيديو"
- "رفض طلب استلام مكالمة الفيديو"
- "تمرير لأعلى لـ %s."
- "تمرير لليسار لـ %s."
- "تمرير لليمين لـ %s."
- "تمرير لأسفل لـ %s."
- "اهتزاز"
- "اهتزاز"
- "الصوت"
- "الصوت الافتراضي (%1$s)"
- "نغمة رنين الهاتف"
- "اهتزاز عند الرنين"
- "نغمة الرنين والاهتزاز"
- "إدارة مكالمة جماعية"
- "رقم الطوارئ"
- "صورة الملف الشخصي"
- "تم إيقاف الكاميرا"
- "عبر %s"
- "تم إرسال الملاحظة"
- "الرسائل الأخيرة"
- "معلومات النشاط التجاري"
- "على بُعد %.1f ميل"
- "على بُعد %.1f كم"
- "%1$s، %2$s"
- "%1$s - %2$s"
- "%1$s، %2$s"
- "مفتوح غدًا في %s"
- "مفتوح اليوم في %s"
- "مغلق في %s"
- "مغلق اليوم في %s"
- "مفتوح الآن"
- "مغلق الآن"
- "اشتباه في متصل غير مرغوب فيه"
- "المكالمة انتهت %1$s"
- "هذه هي المرة الأولى التي تتلقى فيها اتصالاً من هذا الرقم."
- "لدينا شك أن هذه المكالمة واردة من متصل غير مرغوب فيه."
- "حظر/إبلاغ عن رقم غير مرغوب فيه"
- "إضافة جهة اتصال"
- "ليس رقمًا غير مرغوب فيه"
-
diff --git a/InCallUI/res/values-az/strings.xml b/InCallUI/res/values-az/strings.xml
deleted file mode 100644
index 4bb9652b92307208ad1229288f2e8dfa0063565c..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-az/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Gözləmə mövqeyində"
- "Naməlum"
- "Şəxsi nömrə"
- "Taksofon"
- "Konfrans zəngi"
- "Zəng bitdi"
- "Dinamik"
- "Dəstək qulaqlığı"
- "Simli qulaqlıq"
- "Bluetooth"
- "Aşağıdakı tonlar göndərilsin?\n"
- "Tonlar göndərilir\n"
- "Göndər"
- "Bəli"
- "Xeyr"
- "Joker simvolları əvəz edin"
- "Konfrans zəngi %s"
- "Səsli poçt nömrəsi"
- "Nömrə yığılır"
- "Yenidən yığır"
- "Konfrans zəngi"
- "Gələn zəng"
- "Daxil olan iş çağrısı"
- "Zəng sona çatdı"
- "Gözləmə mövqeyində"
- "Dəstək asılır"
- "Çağrıda"
- "Mənim nömrəm %s"
- "Video qoşulur"
- "Video zəng"
- "Video sorğusu göndərilir"
- "Video zəngə qoşulmaq mümkün deyil"
- "Video sorğusu rədd edildi"
- "Cavab zəngi nömrəniz\n %1$s"
- "Təcili cavab zəngi nömrəniz\n %1$s"
- "Nömrə yığılır"
- "Buraxılmış zəng"
- "Buraxılmış zənglər"
- "%s buraxılmış zənglər"
- "%s tərəfindən zəng buraxılıb"
- "Davam edən çağrı"
- "Davam edən iş çağrısı"
- "Davam edən Wi-Fi zəngi"
- "Davam edən Wi-Fi iş çağrısı"
- "Gözləmə mövqeyində"
- "Gələn zəng"
- "Daxil olan iş çağrısı"
- "Gələn Wi-Fi zəngi"
- "Daxil olan Wi-Fi iş çağrısı"
- "Gələn video zəng"
- "Şübhəli spam zəngi"
- "Gələn video çağrı"
- "Yeni səsli poçt"
- "Yeni səsli poçt (%d)"
- "Yığın %s"
- "Səsli poçt nömrəsi naməlumdur"
- "Xidmət yoxdur"
- "Seçilmiş (%s) şəbəkə əlçatmazdır"
- "Cavab"
- "Dəstəyi qoyun"
- "Videolar"
- "Səs"
- "Qəbul edin"
- "Rədd edin"
- "Geriyə zəng"
- "Mesaj"
- "Digər cihazda davam etməkdə olan zəng"
- "Zəngi Transfer edin"
- "Zəng etmək üçün ilk olaraq Uçuş Rejimini söndürün."
- "Şəbəkədə qeydə alınmayıb."
- "Mobil şəbəkə əlçatan deyil"
- "Zəngi yerləşdirmək üçün düzgün nömrə daxil edin."
- "Zəng etmək mümkün deyil."
- "MMI başlanma ardıcıllığı…"
- "Xidmət dəstəklənmir."
- "Zəngləri keçirmək mümkün deyil."
- "Zəngi ayırmaq mümkün deyil."
- "Ötürmək mümkün deyil."
- "Konfrans keçirmək mümkün deyil."
- "Zəngi rədd etmək mümkün deyil."
- "Zəngləri buraxmaq mümkün deyil."
- "SIP çağrısıs"
- "Təcili zəng"
- "Radio yandırılır ..."
- "Xidmət yoxdur. Yenidən cəhd edilir…"
- "Zəng etmək mümkün deyil. %s fövqəladə nömrə deyil."
- "Zəng etmək mümkün deyil. Fövqəladə nömrəni yı"
- "Nömrə yığmaq üçün klaviaturadan istifadə ediin"
- "Zəngi gözlədin"
- "Zəngə davam edin"
- "Zəngi bitirin"
- "Yığım düymələrini göstərin"
- "Yığım düymələrini gizlədin"
- "Susdurun"
- "Susdurmayın"
- "Zəng əlavə edin"
- "Zəngləri birləşdirin"
- "Dəyişdirin"
- "Zəngləri idarə edin"
- "Konfrans çağrısını idarə edin"
- "Konfrans zəngi"
- "İdarə edin"
- "Audio"
- "Video zəng"
- "Səsli çağrıya dəyişin"
- "Kameraya keçin"
- "Kameranı yandırın"
- "Kameranı söndürün"
- "Daha çox seçim"
- "Pleyer Başladıldı"
- "Pleyer Dayandırıldı"
- "Kamera hazır deyil"
- "Kamera hazırdır"
- "Naməlum zəng sessiyası"
- "Xidmət"
- "Quraşdırma"
- "<Təyin edilməyib>"
- "Digər zəng parametrləri"
- "%s vasitəsi ilə zəng edilir"
- "%s vasitəsilə gələn"
- "kontakt fotosu"
- "şəxsi rejimə keçin"
- "kontakt seçin"
- "Özünüzünkünü yazın"
- "Ləğv edin"
- "Göndər"
- "Cavab"
- "SMS göndərin"
- "İmtina edin"
- "Video çağrı olaraq cavab verin"
- "Audio çağrı olaraq cavab verin"
- "Video sorğusunu qəbul edin"
- "Video sorğusunu ləğv edin"
- "Video ötürmə sorğusunu qəbul edin"
- "Video ötürmə sorğusunu ləğv edin"
- "Video qəbuletmə sorğusunu qəbul edin"
- "Video qəbuletmə sorğusunu ləğv edin"
- "%s üçün yuxarı sürüşdürün."
- "%s üçün sola sürüşdürün."
- "%s üçün sağa sürüşdürün."
- "%s üçün aşağı sürüşdürün."
- "Vibrasiya"
- "Vibrasiya"
- "Səs"
- "Defolt səs (%1$s)"
- "Telefon zəng səsi"
- "Zəng çalanda vibrasiya olsun"
- "Zəng səsi & Vibrasiya"
- "Konfrans çağrısını idarə edin"
- "Təcili nömrə"
- "Profil fotosu"
- "Kamera deaktivdir"
- "%s vasitəsilə"
- "Qeyd göndərildi"
- "Son mesajlar"
- "Biznes məlumatı"
- "%.1f mil uzaqlıqda"
- "%.1f km uzaqlıqda"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Sabah saat %s açılır"
- "Bu gün saat %s açılır"
- "Saat %s bağlanır"
- "Bu gün saat %s bağlanıb"
- "İndi açın"
- "İndi bağlandı"
- "Şübhəli spam çağrıcısı"
- "Zəng bitdi %1$s"
- "Bu nömrə ilk dəfədir Sizə zəng edir."
- "Bu zəngin spam olduğundan şübhələnirik."
- "Spamı blok edin/bildirin"
- "Kontakt əlavə edin"
- "Spam deyil"
-
diff --git a/InCallUI/res/values-b+sr+Latn/strings.xml b/InCallUI/res/values-b+sr+Latn/strings.xml
deleted file mode 100644
index 9770f90a924a9f4c9c02cf8aa0d49cf660a9b64c..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-b+sr+Latn/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Na čekanju"
- "Nepoznat"
- "Privatan broj"
- "Telefonska govornica"
- "Konferencijski poziv"
- "Poziv je prekinut"
- "Zvučnik"
- "Slušalica telefona"
- "Žičane naglavne slušalice"
- "Bluetooth"
- "Želite li da pošaljete sledeće tonove?\n"
- "Tonovi se šalju\n"
- "Pošalji"
- "Da"
- "Ne"
- "Zamenite džoker znak sa"
- "Konferencijski poziv %s"
- "Broj govorne pošte"
- "Poziva se"
- "Ponovo se bira"
- "Konferencijski poziv"
- "Dolazni poziv"
- "Dolazni poziv za Work"
- "Poziv je završen"
- "Na čekanju"
- "Veza se prekida"
- "Poziv je u toku"
- "Moj broj je %s"
- "Povezuje se video poziv"
- "Video poziv"
- "Zahteva se video poziv"
- "Povezivanje video poziva nije uspelo"
- "Zahtev za video poziv je odbijen"
- "Broj za povratni poziv\n %1$s"
- "Broj za hitan povratni poziv\n %1$s"
- "Poziva se"
- "Propušten poziv"
- "Propušteni pozivi"
- "Broj propuštenih poziva: %s"
- "Propušten poziv od: %s"
- "Tekući poziv"
- "Tekući poziv za Work"
- "Tekući Wi-Fi poziv"
- "Tekući poziv za Work preko Wi-Fi-ja"
- "Na čekanju"
- "Dolazni poziv"
- "Dolazni poziv za Work"
- "Dolazni Wi-Fi poziv"
- "Dolazni poziv za Work preko Wi-Fi-ja"
- "Dolazni video poziv"
- "Sumnja na nepoželjan dolazni poziv"
- "Zahtev za dolazni video poziv"
- "Nova poruka govorne pošte"
- "Nova poruka govorne pošte (%d)"
- "Pozovi %s"
- "Nepoznat broj govorne pošte"
- "Mobilna mreža nije dostupna"
- "Izabrana mreža (%s) nije dostupna"
- "Odgovori"
- "Prekini vezu"
- "Video"
- "Glasovni"
- "Prihvatam"
- "Odbaci"
- "Uzvrati poziv"
- "Pošalji SMS"
- "Poziv je u toku na drugom uređaju"
- "Prebaci poziv"
- "Da biste uputili poziv, prvo isključite režim rada u avionu."
- "Nije registrovano na mreži."
- "Mobilna mreža nije dostupna."
- "Da biste uputili poziv, unesite važeći broj."
- "Poziv nije uspeo."
- "Pokreće se MMI sekvenca..."
- "Usluga nije podržana."
- "Zamena poziva nije uspela."
- "Razdvajanje poziva nije uspelo."
- "Prebacivanje nije uspelo."
- "Konferencijski poziv nije uspeo."
- "Odbijanje poziva nije uspelo."
- "Uspostavljanje poziva nije uspelo."
- "SIP poziv"
- "Hitni poziv"
- "Uključuje se radio…"
- "Mobilna mreža nije dostupna. Pokušavamo ponovo…"
- "Poziv nije uspeo. %s nije broj za hitne slučajeve."
- "Poziv nije uspeo. Pozovite broj za hitne slučajeve."
- "Koristite tastaturu za pozivanje"
- "Stavi poziv na čekanje"
- "Nastavi poziv"
- "Završi poziv"
- "Prikaži numeričku tastaturu"
- "Sakrij numeričku tastaturu"
- "Isključi zvuk"
- "Uključi zvuk"
- "Dodaj poziv"
- "Objedini pozive"
- "Zameni"
- "Upravljaj pozivima"
- "Upravljaj konferencijskim pozivom"
- "Konferencijski poziv"
- "Upravljaj"
- "Audio"
- "Video poziv"
- "Promeni u glasovni poziv"
- "Promeni kameru"
- "Uključi kameru"
- "Isključi kameru"
- "Još opcija"
- "Plejer je pokrenut"
- "Plejer je zaustavljen"
- "Kamera nije spremna"
- "Kamera je spremna"
- "Nepoznat događaj sesije poziva"
- "Usluga"
- "Podešavanje"
- "<Nije podešeno>"
- "Druga podešavanja poziva"
- "Poziva se preko dobavljača %s"
- "Dolazni poziv preko %s"
- "slika kontakta"
- "idi na privatno"
- "izaberite kontakt"
- "Napišite sami…"
- "Otkaži"
- "Pošalji"
- "Odgovori"
- "Pošalji SMS"
- "Odbij"
- "Odgovori video pozivom"
- "Odgovori audio-pozivom"
- "Prihvati zahtev za video"
- "Odbij zahtev za video"
- "Prihvati zahtev za odlazni video poziv"
- "Odbij zahtev za odlazni video poziv"
- "Prihvati zahtev za dolazni video poziv"
- "Odbij zahtev za dolazni video poziv"
- "Prevucite nagore za %s."
- "Prevucite ulevo za %s."
- "Prevucite udesno za %s."
- "Prevucite nadole za %s."
- "Vibracija"
- "Vibracija"
- "Zvuk"
- "Podrazumevani zvuk (%1$s)"
- "Melodija zvona telefona"
- "Vibriraj kada zvoni"
- "Melodija zvona i vibracija"
- "Upravljaj konferencijskim pozivom"
- "Broj za hitne slučajeve"
- "Slika profila"
- "Kamera je isključena"
- "na %s"
- "Beleška je poslata"
- "Nedavne poruke"
- "Informacije o preduzeću"
- "Udaljenost je %.1f mi"
- "Udaljenost je %.1f km"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Otvara se sutra u %s"
- "Otvara se danas u %s"
- "Zatvara se u %s"
- "Zatvorilo se danas u %s"
- "Trenutno otvoreno"
- "Trenutno zatvoreno"
- "Nepoželjan pozivalac"
- "Poziv se završio u %1$s"
- "Ovo je bio prvi poziv sa ovog broja."
- "Sumnjamo da je ovaj poziv nepoželjan."
- "Blokiraj/prijavi"
- "Dodaj kontakt"
- "Nije nepoželjan"
-
diff --git a/InCallUI/res/values-be/strings.xml b/InCallUI/res/values-be/strings.xml
deleted file mode 100644
index 70145fb7ce5727c10bb552354862ec15e6db88d9..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-be/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Тэлефон"
- "На ўтрыманні"
- "Невядомы"
- "Прыватны нумар"
- "Таксафон"
- "Канферэнц-выклік"
- "Выклік абарваўся"
- "Дынамік"
- "Дынамік тэлефона"
- "Правадная гарнітура"
- "Bluetooth"
- "Адправіць гэтыя тоны?\n"
- "Адпраўка тонаў\n"
- "Адправiць"
- "Так"
- "Не"
- "Замяніце знак падстаноўкі на"
- "Канферэнц-выклік у %s"
- "Нумар галасавой пошты"
- "Набор нумара"
- "Паўторны набор"
- "Канферэнц-выклік"
- "Уваходны выклік"
- "Уваходны выклік па працы"
- "Выклік скончаны"
- "На ўтрыманні"
- "Завяршэнне выкліку"
- "У выкліку"
- "Мой нумар - %s"
- "Падлучэнне відэа"
- "Відэавыклік"
- "Запыт на відэа"
- "Немагчыма падлучыць відэавыклік"
- "Запыт на відэа адхілены"
- "Ваш нумар зваротнага выкліку\n %1$s"
- "Ваш нумар экстраннага зваротнага выкліку\n %1$s"
- "Набор нумара"
- "Прапушчаны выклік"
- "Прапушчаныя выклікі"
- "Прапушчаных выклікаў: %s"
- "Прапушчаны выклiк ад %s"
- "Бягучы выклік"
- "Бягучы выклік па працы"
- "Бягучы выклік праз Wi-Fi"
- "Бягучы выклік па працы праз Wi-Fi"
- "На ўтрыманні"
- "Уваходны выклік"
- "Уваходны выклік па працы"
- "Уваходны выклік праз Wi-Fi"
- "Уваходны выклік па працы праз Wi-Fi"
- "Уваходны відэавыклік"
- "Уваходны выклiк ад абанента, якога падазраваюць у спаме"
- "Уваходны запыт на відэавыклік"
- "Новая галасавая пошта"
- "Новыя паведамленнi галасавой пошты (%d)"
- "Набраць %s"
- "Невядомы нумар галасавой пошты"
- "Не абслугоўваецца"
- "Выбраная сетка (%s) недаступная"
- "Адказ"
- "Сконч. разм."
- "Відэа"
- "Галасавы"
- "Прыняць"
- "Адхіліць"
- "Звар. выклік"
- "Паведамленне"
- "Бягучы выклік на іншай прыладзе"
- "Перадаць выклік"
- "Каб зрабіць выклік, спачатку выключыце рэжым палёту."
- "Не зарэгістраваны ў сетцы."
- "Мабільная сетка недаступная."
- "Каб зрабіць выклік, увядзіце сапраўдны нумар."
- "Выклік немагчымы."
- "Пачатак паслядоўнасці MMI…"
- "Служба не падтрымліваецца."
- "Немагчыма пераключыць выклікі."
- "Немагчыма аддзяліць выклік."
- "Немагчыма перадаць выклік."
- "Немагчыма зрабіць канферэнц-выклік."
- "Немагчыма адхіліць выклік."
- "Немагчыма скончыць выклік(і)."
- "SIP-выклік"
- "Экстранны выклік"
- "Уключэнне радыё…"
- "Не абслугоўваецца. Паўтор спробы…"
- "Выклік немагчымы. %s не з\'яўляецца нумарам экстраннай службы."
- "Выклік немагчымы. Набярыце нумар экстраннай службы."
- "Набраць нумар з клавіятуры"
- "Паставіць выклік на ўтрыманне"
- "Узнавіць выклік"
- "Завяршыць выклік"
- "Паказаць панэль набору"
- "Схаваць панэль набору"
- "Адключыць мікрафон"
- "Уключыць мікрафон"
- "Дадаць выклік"
- "Аб\'яднаць выклікі"
- "Пераключыць"
- "Кіраваць выклікамі"
- "Кіраванне канферэнц-выклікам"
- "Канферэнц-выклік"
- "Кіраванне"
- "Аўдыя"
- "Відэавыклік"
- "Змяніць на галасавы выклік"
- "Пераключыць камеру"
- "Уключыць камеру"
- "Адключыць камеру"
- "Дадатковыя параметры"
- "Прайгравальнік запушчаны"
- "Прайгравальнік спынены"
- "Камера не гатовая"
- "Камера гатовая"
- "Невядомая падзея сеансу выкліку"
- "Сэрвіс"
- "Наладка"
- "<Не зададзены>"
- "Іншыя налады выклікаў"
- "Выклікі праз правайдара %s"
- "Уваходны выклік праз %s"
- "фаіаграфія кантакту"
- "перайсці да прыватнай гаворкі"
- "выбраць кантакт"
- "Напiшыце сваё…"
- "Скасаваць"
- "Адправiць"
- "Адказ"
- "Адправiць SMS"
- "Адхіліць"
- "Адказаць відэавыклікам"
- "Адказаць аўдыявыклікам"
- "Прыняць запыт на відэа"
- "Адхіліць запыт на відэа"
- "Прыняць запыт на перадачу відэа"
- "Адхіліць запыт на перадачу відэа"
- "Прыняць запыт на атрыманне відэа"
- "Адхіліць запыт на атрыманне відэа"
- "Правядзіце пальцам уверх, каб %s."
- "Правядзіце пальцам улева, каб %s."
- "Правядзіце пальцам управа, каб %s."
- "Правядзіце пальцам уніз, каб %s."
- "Вібрацыя"
- "Вібрацыя"
- "Гук"
- "Стандартны гук (%1$s)"
- "Рынгтон тэлефона"
- "Вібрацыя падчас званка"
- "Рынгтон і вiбрацыя"
- "Кіраванне канферэнц-выклікам"
- "Нумар экстраннай службы"
- "Фота профілю"
- "Камера адключана"
- "праз %s"
- "Нататка адпраўлена"
- "Апошнія паведамленні"
- "Бізнес-інфармацыя"
- "Адлеглаць у мілях: %.1f"
- "Адлегласць %.1f км"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Адкрываецца заўтра ў %s"
- "Адкрываецца сёння ў %s"
- "Закрываецца ў %s"
- "Закрыта сёння ў %s"
- "Адкрыць зараз"
- "Зараз закрыта"
- "Падазраваецца ў спаме"
- "Выклік завершаны %1$s"
- "Вы атрымліваеце выклік з гэтага нумара ўпершыню."
- "Існуе падазрэнне, што гэты выклік – спамерскі."
- "Забл./павед.пра спам"
- "Дадаць кантакт"
- "Не спам"
-
diff --git a/InCallUI/res/values-bg/strings.xml b/InCallUI/res/values-bg/strings.xml
deleted file mode 100644
index adf504777d1a91e762f941f5c2bf35e8df02d9f2..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-bg/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Телефон"
- "Задържано"
- "Неизвестно лице"
- "Частен номер"
- "Обществен телефон"
- "Конферентно обаждане"
- "Обаждането бе прекъснато"
- "Високоговорител"
- "Телефонна слушалка"
- "Слушалки с кабел"
- "Bluetooth"
- "Да се изпратят ли следните мелодии? \n"
- "Мелодиите се изпращат\n"
- "Изпращане"
- "Да"
- "Не"
- "Замяна на заместващия символ със:"
- "Конферентно обаждане – %s"
- "Номер за гласова поща"
- "Набира се"
- "Набира се отново"
- "Конферентно обаждане"
- "Входящо обаждане"
- "Входящо служебно обаждане"
- "Обаждането завърши"
- "Задържано"
- "Разговорът се приключва"
- "Извършва се обаждане"
- "Номерът ми е %s"
- "Установява се видеовръзка"
- "Видеообаждане"
- "Заявява се видеовръзка"
- "Видеообаждането не може да се осъществи"
- "Заявката за видеовръзка е отхвърлена"
- "Номерът ви за обратно обаждане\n– %1$s"
- "Номерът ви за спешно обратно обаждане\n– %1$s"
- "Набиране"
- "Пропуснато обаждане"
- "Пропуснати обаждания"
- "%s пропуснати обаждания"
- "Пропуснато обаждане от %s"
- "Текущо обаждане"
- "Текущо служебно обаждане"
- "Текущо обаждане през Wi-Fi"
- "Текущо служебно обаждане през Wi-Fi"
- "Задържано"
- "Входящо обаждане"
- "Входящо служебно обаждане"
- "Входящо обаждане през Wi-Fi"
- "Входящо служебно обаждане през Wi-Fi"
- "Входящо видеообаждане"
- "Входящо обаждане – възможен спам"
- "Заявка за входящо видеообаждане"
- "Нова гласова поща"
- "Нова гласова поща (%d)"
- "Набиране на %s"
- "Неизвестен номер за гласова поща"
- "Няма покритие"
- "Избраната мрежа (%s) не е налице"
- "Приемане"
- "Затваряне"
- "Видеообажд."
- "Гл. обаждане"
- "Приемане"
- "Отхвърляне"
- "Обр. обажд."
- "Съобщение"
- "Текущо обаждане на друго устройство"
- "Прехвърляне на обаждането"
- "За да осъществите обаждане, първо изключете самолетния режим."
- "Няма регистрация в мрежата."
- "Няма достъп до клетъчната мрежа."
- "За да извършите обаждане, въведете валиден номер."
- "Не може да се извърши обаждане."
- "Стартира се последователността MMI…"
- "Услугата не се поддържа."
- "Обажданията не могат да се превключат."
- "Обаждането не може да се отдели."
- "Не може да се прехвърли."
- "Не може да се извърши конферентно обаждане."
- "Обаждането не може да се отхвърли."
- "Обаждането или съответно обажданията не могат да се освободят."
- "Обаждане чрез SIP"
- "Спешно обаждане"
- "Радиомодулът се включва…"
- "Няма услуга. Извършва се нов опит…"
- "Не може да се извърши обаждане. %s не е номер за спешни случаи."
- "Не може да се извърши обаждане. Наберете номер за спешни случаи."
- "Използвайте клавиатурата за набиране"
- "Задържане на обаждането"
- "Възобновяване на обаждането"
- "Край на обаждането"
- "Показване на клавиатурата за набиране"
- "Скриване на клавиатурата за набиране"
- "Заглушаване"
- "Пускане"
- "Добавяне на обаждане"
- "Обединяване на обаждания"
- "Размяна"
- "Управление на обажданията"
- "Управление на конф. обаждане"
- "Конферентно обаждане"
- "Управление"
- "Аудио"
- "Видеообажд."
- "Преминаване към гласово обаждане"
- "Превключване на камерата"
- "Включване на камерата"
- "Изключване на камерата"
- "Още опции"
- "Плейърът е стартиран"
- "Плейърът е спрян"
- "Камерата не е в готовност"
- "Камерата е в готовност"
- "Неизвестно събитие в сесията на обаждане"
- "Услуга"
- "Настройване"
- "<Не е зададено>"
- "Други настройки за обаждане"
- "Обаждане чрез %s"
- "Входящо обаждане чрез %s"
- "снимка на контакта"
- "превключване към частно обаждане"
- "избиране на контакта"
- "Напишете свой собствен..."
- "Отказ"
- "Изпращане"
- "Приемане"
- "Изпращане на SMS"
- "Отхвърляне"
- "Приемане като видеообаждане"
- "Приемане като аудиообаждане"
- "Приемане на заявката за видеовръзка"
- "Отхвърляне на заявката за видеовръзка"
- "Приемане на заявката за предаване на видео"
- "Отхвърляне на заявката за предаване на видео"
- "Приемане на заявката за получаване на видеообаждане"
- "Отхвърляне на заявката за получаване на видео"
- "Плъзнете нагоре за %s."
- "Плъзнете наляво за %s."
- "Плъзнете надясно за %s."
- "Плъзнете надолу за %s."
- "Вибриране"
- "Вибриране"
- "Звук"
- "Стандартен звук (%1$s)"
- "Мелодия на телефона"
- "Вибриране при звънене"
- "Мелодия и вибриране"
- "Управление на конферентното обаждане"
- "Спешен номер"
- "Снимка на потребителския профил"
- "Камерата е изключена"
- "чрез %s"
- "Бележката е изпратена"
- "Скорошни съобщения"
- "Бизнес информация"
- "На %.1f мили"
- "На %.1f км"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s; %2$s"
- "Отваря утре в %s"
- "Отваря днес в %s"
- "Затваря в %s"
- "Затворено днес в %s"
- "В момента работи"
- "В момента не работи"
- "Възможен спам"
- "Обаждането завърши %1$s"
- "За първи път ви се обаждат от този номер."
- "Подозирахме, че това обаждане може да е от разпространител на спам."
- "Блокиране/спам"
- "Добавяне на контакт"
- "Не е спам"
-
diff --git a/InCallUI/res/values-bn/strings.xml b/InCallUI/res/values-bn/strings.xml
deleted file mode 100644
index 2f561ce6e10b507f0706a6c3ca1de195d3e062d7..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-bn/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ফোন"
- "হোল্ডে রয়েছে"
- "অজানা"
- "ব্যক্তিগত নম্বর"
- "অর্থের বিনিময়ে কল করার ফোন"
- "কনফারেন্স কল"
- "কল সমাপ্ত হয়েছে"
- "স্পিকার"
- "হ্যান্ডসেট ইয়ারপিস"
- "তারযুক্ত হেডসেট"
- "ব্লুটুথ"
- "নিম্নলিখিত টোনগুলি পাঠাবেন?\n"
- "টোনগুলি পাঠানো হচ্ছে\n"
- "পাঠান"
- "হ্যাঁ"
- "না"
- "ওয়াইল্ড অক্ষরগুলিকে এর মাধ্যমে প্রতিস্থাপিত করুন"
- "কনফারেন্স কল %s"
- "ভয়েসমেল নম্বর"
- "ডায়াল করা হচ্ছে"
- "আবার ডায়াল করা হচ্ছে"
- "কনফারেন্স কল"
- "আগত কল"
- "আগত কাজের কল"
- "কল সমাপ্ত হয়েছে"
- "হোল্ডে রয়েছে"
- "কল নামিয়ে রাখা হচ্ছে"
- "কলের সময়ে"
- "আমার নম্বর হল %s"
- "ভিডিও সংযুক্ত করছে"
- "ভিডিও কল"
- "ভিডিওর অনুরোধ করছে"
- "ভিডিও কলে সংযোগ করা যাচ্ছে না"
- "ভিডিওর অনুরোধ প্রত্যাখ্যান করা হয়েছে"
- "আপনার কলব্যাক নম্বর\n%1$s"
- "আপনার জরুরী কলব্যাক নম্বর\n%1$s"
- "ডায়াল করা হচ্ছে"
- "মিসড কল"
- "মিসড কলগুলি"
- "%sটি মিসড কল"
- "%s এর থেকে মিসড কল"
- "চলমান কল"
- "চলমান কাজের কল"
- "চলমান ওয়াই-ফাই কল"
- "চলমান ওয়াই-ফাই কাজের কল"
- "হোল্ডে রয়েছে"
- "আগত কল"
- "আগত কাজের কল"
- "আগত ওয়াই-ফাই কল"
- "আগত ওয়াই-ফাই কাজের কল"
- "আগত ভিডিও কল"
- "আগত সন্দেহভাজন স্প্যাম কল"
- "আগত ভিডিও অনুরোধ"
- "নতুন ভয়েসমেল"
- "নতুন ভয়েসমেল (%dটি)"
- "%s ডায়াল করুন"
- "ভয়েসমেল নম্বর অজানা"
- "কোনো পরিষেবা নেই"
- "নির্বাচিত নেটওয়ার্ক (%s) অনুপলব্ধ"
- "উত্তর"
- "কল নামিয়ে রাখুন"
- "ভিডিও"
- "ভয়েস"
- "স্বীকার করুন"
- "খারিজ করুন"
- "ঘুরিয়ে কল করুন"
- "বার্তা"
- "অন্য ডিভাইসে চালু থাকা কল"
- "কল স্থানান্তর করুন"
- "একটি কল করতে, প্রথমে বিমানমোড বন্ধ করুন৷"
- "নেটওয়ার্কে নিবন্ধিত নয়৷"
- "সেলুলার নেটওয়ার্ক উপলব্ধ নয়।"
- "কোনো কল স্থাপন করতে, একটি বৈধ নম্বর লিখুন৷"
- "কল করা যাবে না৷"
- "MMI ক্রম চালু হচ্ছে…"
- "পরিষেবা সমর্থিত নয়৷"
- "কলগুলি স্যুইচ করা যাবে না৷"
- "কল আলাদা করা যাবে না৷"
- "হস্তান্তর করা যাবে না৷"
- "কনফারেন্স করা যাবে না৷"
- "কল প্রত্যাখ্যান কলা যাবে না৷"
- "কল(গুলি) কাটা যাবে না৷"
- "SIP কল"
- "জরুরি কল"
- "রেডিও চালু করা হচ্ছে…"
- "কোন পরিষেবা নেই৷ আবার চেষ্টা করা হচ্ছে..."
- "কল করা যাবে না৷ %s কোনো জরুরী নম্বর নয়৷"
- "কল করা যাবে না৷ কোনো জরুরী নম্বর ডায়াল করুন৷"
- "ডায়াল করতে কীবোর্ড ব্যবহার করুন"
- "কল হোল্ডে রাখুন"
- "কল আবার শুরু করুন"
- "কল শেষ করুন"
- "ডায়ালপ্যাড দেখান"
- "ডায়ালপ্যাড লুকান"
- "নিঃশব্দ করুন"
- "সশব্দ করুন"
- "কল যোগ করুন"
- "কলগুলি মার্জ করুন"
- "সোয়াপ করুন"
- "কলগুলি পরিচালনা করুন"
- "কনফারেন্স কল পরিচালনা করুন"
- "কনফারেন্স কল"
- "পরিচালনা করুন"
- "অডিও"
- "ভিডিও কল"
- "ভয়েস কলে পরিবর্তন করুন"
- "ক্যামেরা স্যুইচ করুন"
- "ক্যামেরা চালু করুন"
- "ক্যামেরা বন্ধ করুন"
- "আরো বিকল্প"
- "প্লেয়ার শুরু হয়েছে"
- "প্লেয়ার বন্ধ হয়ে গেছে"
- "ক্যামেরা রেডি নয়"
- "ক্যামেরা রেডি"
- "অজানা কল অধিবেশনের ইভেন্ট"
- "পরিষেবা"
- "সেটআপ"
- "<সেট করা নেই>"
- "অন্যান্য কল সেটিংস"
- "%s এর মাধ্যমে কল করা হচ্ছে"
- "%s এর মাধ্যমে ইনকামিং কল"
- "পরিচিতির ফটো"
- "ব্যক্তিগতভাবে কাজ করুন"
- "পরিচিতি নির্বাচন করুন"
- "আপনার নিজের পছন্দ মতো লিখুন…"
- "বাতিল করুন"
- "পাঠান"
- "উত্তর"
- "SMS পাঠান"
- "অস্বীকার করুন"
- "ভিডিও কল হিসেবে উত্তর দিন"
- "অডিও কল হিসেবে উত্তর দিন"
- "ভিডিওর অনুরোধ গ্রহণ করুন"
- "ভিডিওর অনুরোধ প্রত্যাখ্যান করুন"
- "ভিডিও প্রেরণ করার অনুরোধ স্বীকার করুন"
- "ভিডিও প্রেরণ করার অনুরোধ প্রত্যাখ্যান করুন"
- "ভিডিও গ্রহণ করার অনুরোধ স্বীকার করুন"
- "ভিডিও গ্রহণ করার অনুরোধ প্রত্যাখ্যান করুন"
- "%s এর জন্য উপরের দিকে স্লাইড করুন৷"
- "%s এর জন্য বাঁ দিকে স্লাইড করুন৷"
- "%s এর জন্য ডান দিকে স্লাইড করুন৷"
- "%s এর জন্য নীচের দিকে স্লাইড করুন৷"
- "কম্পন"
- "কম্পন"
- "শব্দ"
- "ডিফল্ট শব্দ (%1$s)"
- "ফোন রিংটোন"
- "রিং হওয়ার সময় কম্পন হবে"
- "রিংটোন ও কম্পন"
- "কনফারেন্স কল পরিচালনা করুন"
- "জরুরি নম্বর"
- "প্রোফাইল ফটো"
- "ক্যামেরা বন্ধ"
- "%s এর মাধ্যমে"
- "নোট পাঠানো হয়েছে"
- "সাম্প্রতিক বার্তাগুলি"
- "ব্যবসার তথ্য"
- "%.1f মাইল দূরে"
- "%.1f কিলোমিটার দূরে"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "আগামীকাল %s\'টায় খুলবে"
- "আজ %s\'টায় খুলবে"
- "%s\'টায় বন্ধ হয়"
- "আজ %s\'টায় বন্ধ হয়েছে"
- "এখন খোলা রয়েছে"
- "এখন বন্ধ রয়েছে"
- "সন্দেহভাজন স্প্যাম কলার"
- "কল সমাপ্ত হয়েছে %1$s"
- "এই প্রথমবার এই নম্বর থেকে আপনাকে কল করা হয়েছে৷"
- "এটি কোনো স্প্যামারের কল হতে পারে বলে আমাদের মনে হচ্ছে৷"
- "অবরুদ্ধ করুন/স্প্যাম হিসাবে অভিযোগ করুন"
- "পরিচিতি যোগ করুন"
- "স্প্যাম নয়"
-
diff --git a/InCallUI/res/values-bs/strings.xml b/InCallUI/res/values-bs/strings.xml
deleted file mode 100644
index 9db727c980306d09ff8b4baae042ca5c78e2659e..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-bs/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Na čekanju"
- "Nepoznato"
- "Privatni broj"
- "Telefonska govornica"
- "Konferencijski poziv"
- "Poziv je prekinut"
- "Zvučnik"
- "Slušalice telefona"
- "Žičane slušalice"
- "Bluetooth"
- "Poslati sljedeće tonove?\n"
- "Slanje tonova\n"
- "Pošalji"
- "Da"
- "Ne"
- "Zamijeni zamjenski znak sa"
- "Konferencijski poziv %s"
- "Broj govorne pošte"
- "Poziva se"
- "Ponovno pozivanje"
- "Konferencijski poziv"
- "Dolazni poziv"
- "Dolazni poslovni poziv"
- "Poziv je završen"
- "Na čekanju"
- "Prekid veze"
- "Poziv u toku"
- "Moj broj je %s"
- "Uspostavljanje videopoziva"
- "Videopoziv"
- "Zahtijevanje videopoziva"
- "Nije moguće uspostaviti videopoziv"
- "Zahtjev za videopoziv je odbijen"
- "Vaš broj za povratni poziv\n %1$s"
- "Vaš broj za hitni povratni poziv\n %1$s"
- "Poziva se"
- "Propušteni poziv"
- "Propušteni pozivi"
- "Propušteni pozivi: %s"
- "Propušteni poziv od kontakta %s"
- "Poziv u toku"
- "Poslovni poziv u toku"
- "Wi-Fi poziv u toku"
- "Wi-Fi poslovni poziv u toku"
- "Na čekanju"
- "Dolazni poziv"
- "Dolazni poslovni poziv"
- "Dolazni Wi-Fi poziv"
- "Dolazni Wi-Fi poslovni poziv"
- "Dolazni videopoziv"
- "Mogući neželjeni dolazni poziv"
- "Zahtjev za dolazni videopoziv"
- "Nova govorna pošta"
- "Nova govorna pošta (%d)"
- "Pozovi %s"
- "Nepoznat broj govorne pošte"
- "Nema mreže"
- "Odabrana mreža (%s) je nedostupna"
- "Odgovori"
- "Prekini vezu"
- "Videopoziv"
- "Glasovni poziv"
- "Prihvati"
- "Odbaci"
- "Povr. poziv"
- "Poruka"
- "Poziv u toku na drugom uređaju"
- "Prenesi poziv"
- "Da uputite poziv, isključite Način rada u avionu."
- "Nije registrirano na mreži."
- "Mobilna mreža nije dostupna."
- "Da uputite poziv, upišite važeći broj."
- "Nije moguće pozvati."
- "Pokretanje MMI sekvence u toku…"
- "Usluga nije podržana."
- "Nije moguće prebacivanje poziva."
- "Nije moguće odvojiti poziv."
- "Prijenos nije moguć."
- "Konferencijski poziv nije uspio."
- "Nije moguće odbiti poziv."
- "Nije moguće uputiti poziv(e)."
- "SIP poziv"
- "Hitni poziv"
- "Uključivanje radija u toku…"
- "Nema mreže. Ponovni pokušaj u toku…"
- "Nije moguće pozvati. %s nije broj za htine slučajeve."
- "Nije moguće pozvati. Pozovite broj za hitne slučajeve."
- "Koristi tastaturu za biranje"
- "Stavi poziv na čekanje"
- "Nastavi poziv"
- "Prekini poziv"
- "Prikaži telefonsku tipkovnicu"
- "Sakrij telefonsku tipkovnicu"
- "Isključi zvuk"
- "Uključi zvuk"
- "Dodaj poziv"
- "Spoji pozive"
- "Zamijeni"
- "Upravljaj pozivima"
- "Upravljaj konf. pozivom"
- "Konferencijski poziv"
- "Upravljaj"
- "Zvuk"
- "Videopoziv"
- "Promijeni na glasovni poziv"
- "Promijeni kameru"
- "Uključi kameru"
- "Isključi kameru"
- "Više opcija"
- "Plejer je pokrenut"
- "Plejer je zaustavljen"
- "Kamera nije spremna"
- "Kamera je spremna"
- "Nepoznati događaj sesije poziva"
- "Usluga"
- "Postavljanje"
- "<Nije postavljeno>"
- "Ostale postavke poziva"
- "Pozivanje putem %s"
- "Dolazni poziv putem %s"
- "fotografija kontakta"
- "idi na privatno"
- "odaberi kontakt"
- "Napišite svoj..."
- "Otkaži"
- "Pošalji"
- "Odgovori"
- "Pošalji SMS"
- "Odbij"
- "Odgovori videopozivom"
- "Prihvati kao audiopoziv"
- "Prihvati zahtjev za videopoziv"
- "Odbij zahtjev za videopoziv"
- "Prihvati zahtjev za slanje videopoziva"
- "Odbij zahtjev za slanje videopoziva"
- "Prihvati zahtjev za primanje videopoziva"
- "Odbij zahtjev za primanje videopoziva"
- "Kliznite nagore za %s."
- "Kliznite lijevo za %s."
- "Kliznite nadesno za %s."
- "Kliznite nadolje za %s."
- "Vibracija"
- "Vibracija"
- "Zvuk"
- "Zadani zvuk (%1$s)"
- "Melodija zvona telefona"
- "Vibriraj kada zvoni"
- "Melodija zvona i vibracija"
- "Upravljaj konferencijskim pozivom"
- "Broj za hitne slučajeve"
- "Fotografija profila"
- "Kamera je isključena"
- "putem %s"
- "Bilješka je poslana"
- "Nedavne poruke"
- "Informacije o preduzeću"
- "Udaljenost u miljama: %.1f"
- "Udaljenost u km: %.1f"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Otvara se sutra u %s"
- "Otvara se danas u %s"
- "Zatvara se u %s"
- "Zatvoreno danas u %s"
- "Otvori sad"
- "Zatvoreno sada"
- "Neželjeni pozivalac"
- "Poziv je završen %1$s"
- "Ovo je prvi poziv koji ste primili s ovog broja."
- "Sumnjamo da je ovaj poziv neželjen sadržaj."
- "Blokiraj/prijavi"
- "Dodaj kontakt"
- "Nije neželjeno"
-
diff --git a/InCallUI/res/values-ca/strings.xml b/InCallUI/res/values-ca/strings.xml
deleted file mode 100644
index 103f15b639e3edacb2af255fb5920e4a00f4c6c3..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ca/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telèfon"
- "En espera"
- "Desconegut"
- "Número privat"
- "Telèfon públic"
- "Conferència"
- "La trucada s\'ha interromput"
- "Altaveu"
- "Auricular"
- "Auricular amb cable"
- "Bluetooth"
- "Vols enviar els tons següents?\n"
- "S\'estan enviant els tons\n"
- "Envia"
- "Sí"
- "No"
- "Substitueix el caràcter comodí per"
- "Conferència, %s"
- "Número del missatge de veu"
- "S\'està marcant"
- "S\'està tornant a marcar"
- "Conferència"
- "Trucada entrant"
- "Trucada de feina entrant"
- "Ha finalitzat la trucada"
- "En espera"
- "S\'està penjant"
- "En una trucada"
- "El meu número és %s"
- "S\'està connectant el vídeo"
- "Videotrucada"
- "S\'està sol·licitant el vídeo"
- "No es pot connectar la videotrucada"
- "S\'ha rebutjat la sol·licitud de vídeo"
- "Número de devolució de trucada\n %1$s"
- "Número de devolució de trucada d\'emergència\n %1$s"
- "S\'està marcant"
- "Trucada perduda"
- "Trucades perdudes"
- "%s trucades perdudes"
- "Trucada perduda de %s"
- "Trucada en curs"
- "Trucada de feina en curs"
- "Trucada per Wi-Fi en curs"
- "Trucada de feina per Wi-Fi en curs"
- "En espera"
- "Trucada entrant"
- "Trucada de feina entrant"
- "Trucada per Wi-Fi entrant"
- "Trucada de feina per Wi-Fi entrant"
- "Videotrucada entrant"
- "Presumpta trucada brossa entrant"
- "Sol·licitud de vídeo entrant"
- "Missatge de veu nou"
- "Missatges de veu nous (%d)"
- "Marca %s"
- "Número del missatge de veu desconegut"
- "Sense servei"
- "La xarxa seleccionada (%s) no està disponible"
- "Respon"
- "Penja"
- "Vídeo"
- "Veu"
- "Accepta"
- "Ignora"
- "Torna trucada"
- "Missatge"
- "Trucada en curs en un altre dispositiu"
- "Transfereix la trucada"
- "Per fer una trucada, primer desactiva el mode d\'avió."
- "No s\'ha registrat a la xarxa."
- "La xarxa mòbil no està disponible."
- "Introdueix un número vàlid per fer una trucada."
- "No es pot trucar."
- "S\'està iniciant la seqüència MMI…"
- "El servei no és compatible."
- "No es pot canviar de trucada."
- "No es pot separar la trucada."
- "No es poden transferir trucades."
- "No es pot establir la conferència."
- "No es pot rebutjar la trucada."
- "No es poden alliberar trucades."
- "Trucada de SIP"
- "Trucada d\'emergència"
- "S\'està activant el senyal mòbil…"
- "No hi ha servei. S\'està tornant a provar…"
- "No es pot trucar. %s no és un número d\'emergència."
- "No es pot trucar. Marca un número d\'emergència."
- "Utilitza el teclat per marcar"
- "Posa la trucada en espera"
- "Reprèn la trucada"
- "Finalitza la trucada"
- "Mostra el teclat"
- "Amaga el teclat"
- "Silencia"
- "Activa el so"
- "Afegeix una trucada"
- "Combina les trucades"
- "Canvia"
- "Gestiona les trucades"
- "Gestiona la conferència"
- "conferència"
- "Gestiona"
- "Àudio"
- "Videotrucada"
- "Canvia a trucada de veu"
- "Canvia la càmera"
- "Activa la càmera"
- "Desactiva la càmera"
- "Més opcions"
- "S\'ha iniciat el reproductor"
- "S\'ha aturat el reproductor"
- "La càmera no està preparada"
- "La càmera està preparada"
- "Esdeveniment de sessió de trucada desconeguda"
- "Servei"
- "Configura"
- "<No definit>"
- "Altres opcions de configuració de les trucades"
- "S\'està trucant amb %s"
- "Trucada entrant mitjançant %s"
- "foto de contacte"
- "conferència privada"
- "selecciona el contacte"
- "Escriu la teva…"
- "Cancel·la"
- "Envia"
- "Respon"
- "Envia SMS"
- "Rebutja"
- "Respon amb una videotrucada"
- "Respon amb una trucada d\'àudio"
- "Accepta la sol·licitud de vídeo"
- "Rebutja la sol·licitud de vídeo"
- "Accepta la sol·licitud per transmetre vídeo"
- "Rebutja la sol·licitud per transmetre vídeo"
- "Accepta la sol·licitud per rebre vídeo"
- "Rebutja la sol·licitud per rebre vídeo"
- "Fes lliscar el dit cap amunt per %s."
- "Fes lliscar el dit cap a l\'esquerra per %s."
- "Fes lliscar el dit cap a la dreta per %s."
- "Fes lliscar el dit cap avall per %s."
- "Vibració"
- "Vibració"
- "So"
- "So predeterminat (%1$s)"
- "So de trucada"
- "Vibrar en sonar"
- "So de trucada i vibració"
- "Gestiona la conferència"
- "Número d\'emergència"
- "Foto de perfil"
- "La càmera està desactivada"
- "mitjançant %s"
- "S\'ha enviat la nota"
- "Missatges recents"
- "Informació de l\'empresa"
- "A %.1f mi de distància"
- "A %.1f km de distància"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Obre demà a les %s"
- "Obre avui a les %s"
- "Tanca a les %s"
- "Avui ha tancat a les %s"
- "Obert ara"
- "Ara és tancat"
- "Possible trucada brossa"
- "La trucada amb el número %1$s ha finalitzat"
- "És la primera vegada que aquest número t\'ha trucat."
- "Sospitem que aquesta trucada prové d\'un emissor de contingut brossa."
- "Bloqueja/marca brossa"
- "Afegeix un contacte"
- "No és brossa"
-
diff --git a/InCallUI/res/values-cs/strings.xml b/InCallUI/res/values-cs/strings.xml
deleted file mode 100644
index f3e4a5ed3fb2959fdd6cd337e9e9919b2533efbb..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-cs/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Přidržený hovor"
- "Neznámý volající"
- "Soukromé číslo"
- "Telefonní automat"
- "Konferenční hovor"
- "Volání zrušeno"
- "Reproduktor"
- "Sluchátko telefonu"
- "Kabelová náhlavní soupr."
- "Bluetooth"
- "Odeslat následující tóny?\n"
- "Odesílání tónů\n"
- "Odeslat"
- "Ano"
- "Ne"
- "Nahradit zástupné znaky jinými znaky"
- "Konferenční hovor %s"
- "Číslo hlasové schránky"
- "Vytáčení"
- "Opakované vytáčení"
- "Konferenční hovor"
- "Příchozí hovor"
- "Příchozí pracovní hovor"
- "Hovor ukončen"
- "Přidržený hovor"
- "Ukončování hovoru"
- "Probíhá hovor"
- "Moje číslo je %s"
- "Navazování spojení pro video"
- "Videohovor"
- "Požadování videa"
- "Videohovor nelze zahájit"
- "Žádost o video byla zamítnuta"
- "Vaše číslo pro zpětné volání\n%1$s"
- "Vaše číslo pro tísňové zpětné volání\n%1$s"
- "Vytáčení"
- "Zmeškaný hovor"
- "Zmeškané hovory"
- "Zmeškané hovory: %s"
- "Zmeškaný hovor od volajícího %s"
- "Probíhající hovor"
- "Probíhající pracovní hovor"
- "Probíhající hovor přes Wi-Fi"
- "Probíhající pracovní hovor přes Wi-Fi"
- "Přidržený hovor"
- "Příchozí hovor"
- "Příchozí pracovní hovor"
- "Příchozí hovor přes Wi-Fi"
- "Příchozí pracovní hovor přes Wi-Fi"
- "Příchozí videohovor"
- "U příchozího hovoru máme podezření, že se jedná o spam"
- "Příchozí žádost o videohovor"
- "Nová hlasová zpráva"
- "Nové hlasové zprávy (%d)"
- "Volat hlasovou schránku %s"
- "Číslo hlasové schránky není známé"
- "Žádný signál"
- "Vybraná síť (%s) není k dispozici"
- "Přijmout"
- "Zavěsit"
- "Videohovor"
- "Hlas. hovor"
- "Přijmout"
- "Odmítnout"
- "Zavolat zpět"
- "Posl. zprávu"
- "Probíhá hovor na jiném zařízení"
- "Převést hovor sem"
- "Chcete-li telefonovat, nejprve vypněte režim Letadlo."
- "Přihlášení k síti nebylo úspěšné."
- "Mobilní síť je nedostupná."
- "Chcete-li uskutečnit hovor, zadejte platné telefonní číslo."
- "Hovor nelze uskutečnit."
- "Spouštění sekvence MMI..."
- "Služba není podporována."
- "Hovory nelze přepnout."
- "Hovor nelze rozdělit."
- "Hovor nelze předat."
- "Konferenční hovor nelze uskutečnit."
- "Hovor nelze odmítnout."
- "Hovor nelze ukončit."
- "Volání SIP"
- "Tísňové volání"
- "Zapínání bezdrátového modulu..."
- "Žádný signál. Probíhá další pokus…"
- "Hovor nelze uskutečnit. %s není číslo tísňového volání."
- "Hovor nelze uskutečnit. Vytočte číslo tísňového volání."
- "Vytočte číslo pomocí klávesnice"
- "Podržet hovor"
- "Obnovit hovor"
- "Ukončit hovor"
- "Zobrazit číselník"
- "Skrýt číselník"
- "Vypnout zvuk"
- "Zapnout zvuk"
- "Přidat hovor"
- "Spojit hovory"
- "Zaměnit"
- "Spravovat hovory"
- "Spravovat konferenční hovor"
- "Konferenční hovor"
- "Spravovat"
- "Zvuk"
- "Videohovor"
- "Změnit na hlasové volání"
- "Přepnout kameru"
- "Zapnout kameru"
- "Vypnout kameru"
- "Další možnosti"
- "Přehrávač spuštěn"
- "Přehrávač zastaven"
- "Fotoaparát není připraven"
- "Fotoaparát je připraven"
- "Neznámá událost relace volání"
- "Služba"
- "Nastavení"
- "<Nenastaveno>"
- "Další nastavení hovorů"
- "Volání prostřednictvím poskytovatele %s"
- "Příchozí hovor přes poskytovatele %s"
- "fotografie kontaktu"
- "přepnout na soukromé"
- "vybrat kontakt"
- "Napsat vlastní odpověď..."
- "Zrušit"
- "Odeslat"
- "Přijmout"
- "Odeslat SMS"
- "Odmítnout"
- "Přijmout jako videohovor"
- "Přijmout jako hlasový hovor"
- "Přijmout žádost o videhovor"
- "Odmítnout žádost o videohovor"
- "Přijmout žádost o odesílání videa"
- "Odmítnout žádost o odesílání videa"
- "Přijmout žádost o příjem videa"
- "Odmítnout žádost o příjem videa"
- "%s – přejeďte prstem nahoru"
- "%s – přejeďte prstem doleva"
- "%s – přejeďte prstem doprava"
- "%s – přejeďte prstem dolů"
- "Vibrace"
- "Vibrace"
- "Zvuk"
- "Výchozí zvuk (%1$s)"
- "Vyzváněcí tón telefonu"
- "Vibrace při vyzvánění"
- "Vyzvánění a vibrace"
- "Správa konferenčního hovoru"
- "Číslo tísňové linky"
- "Profilová fotka"
- "Fotoaparát je vypnutý"
- "pomocí čísla %s"
- "Poznámka byla odeslána"
- "Nejnovější zprávy"
- "Informace o firmě"
- "Vzdálenost: %.1f mi"
- "Vzdálenost: %.1f km"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Zítra otevírá v %s"
- "Dnes otevírá v %s"
- "Zavírá v %s"
- "Dnes zavřeno od %s"
- "Otevřeno"
- "Nyní zavřeno"
- "Podezření na spam"
- "Hovor skončil v %1$s"
- "Toto číslo vám volalo poprvé."
- "Máme podezření, že tento hovor byl spam."
- "Blok./nahlásit spam"
- "Přidat kontakt"
- "Nešlo o spam"
-
diff --git a/InCallUI/res/values-da/strings.xml b/InCallUI/res/values-da/strings.xml
deleted file mode 100644
index 82d773c1c6197cca4c4b4273b88e2bb87597105b..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-da/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Afventer"
- "Ukendt"
- "Privat nummer"
- "Mønttelefon"
- "Telefonmøde"
- "Opkaldet blev afbrudt."
- "Højttaler"
- "Ørestykke til håndsæt"
- "Headset med ledning"
- "Bluetooth"
- "Vil du sende følgende toner?\n"
- "Sender toner\n"
- "Send"
- "Ja"
- "Nej"
- "Erstat jokertegnet med"
- "Telefonmøde %s"
- "Telefonsvarernummer"
- "Ringer op"
- "Ringer op igen"
- "Telefonmøde"
- "Indgående opkald"
- "Indgående arbejdsopkald"
- "Opkaldet er afsluttet"
- "Afventer"
- "Lægger på"
- "Opkald i gang"
- "Mit nummer er %s"
- "Opretter videoforbindelse"
- "Videoopkald"
- "Anmoder om video"
- "Kan ikke forbinde videoopkald"
- "Videoanmodningen blev afvist"
- "Dit tilbagekaldsnummer\n %1$s"
- "Dit tilbagekaldsnummer til nødopkald\n %1$s"
- "Ringer op"
- "Ubesvaret opkald"
- "Ubesvarede opkald"
- "%s ubesvarede opkald"
- "Ubesvaret opkald fra %s"
- "Igangværende opkald"
- "Igangværende opkald i forbindelse med arbejde"
- "Igangværende opkald via Wi-Fi"
- "Igangværende Wi-Fi-opkald i forbindelse med arbejde"
- "Afventer"
- "Indgående opkald"
- "Indgående arbejdsopkald"
- "Indgående Wi-Fi-opkald"
- "Indgående Wi-Fi-opkald i forbindelse med arbejde"
- "Indgående videoopkald"
- "Indgående formodet spamopkald"
- "Indgående videoanmodning"
- "Ny telefonsvarerbesked"
- "Nye telefonsvarerbeskeder (%d)"
- "Ring til %s"
- "Telefonsvarernummeret er ukendt"
- "Ingen dækning"
- "Det valgte netværk (%s) er ikke tilgængeligt"
- "Besvar"
- "Læg på"
- "Video"
- "Tale"
- "Acceptér"
- "Afvis"
- "Ring tilbage"
- "Besked"
- "Igangværende opkald på en anden enhed"
- "Overfør opkald"
- "Slå Flytilstand fra først for at foretage et opkald."
- "Ikke registreret på netværket."
- "Mobilnetværket er ikke tilgængeligt."
- "Indtast et gyldigt nummer for at foretage et opkald."
- "Der kan ikke ringes op."
- "Starter MMI-sekvens…"
- "Tjenesten er ikke understøttet."
- "Der kan ikke skiftes opkald."
- "Opkaldet kan ikke adskilles."
- "Der kan ikke viderestilles."
- "Der kan ikke oprettes telefonmøde."
- "Opkaldet kan ikke afvises."
- "Et eller flere opkald kan ikke frigives."
- "SIP-opkald"
- "Nødopkald"
- "Tænder for radio…"
- "Ingen tjeneste. Prøver igen…"
- "Der kan ikke ringes op. %s er ikke et alarmnummer."
- "Der kan ikke ringes op. Ring til et alarmnummer."
- "Brug tastaturet til at ringe op"
- "Sæt opkald i venteposition"
- "Genoptag opkald"
- "Afslut opkald"
- "Vis numerisk tastatur"
- "Skjul numerisk tastatur"
- "Slå lyden fra"
- "Slå lyden til"
- "Tilføj opkald"
- "Slå opkald sammen"
- "Skift"
- "Administrer opkald"
- "Administrer telefonmøde"
- "Telefonmøde"
- "Administrer"
- "Lyd"
- "Videoopkald"
- "Skift til taleopkald"
- "Skift kamera"
- "Slå kameraet til"
- "Slå kameraet fra"
- "Flere valgmuligheder"
- "Afspilleren er startet"
- "Afspilleren er stoppet"
- "Kameraet er ikke klar"
- "Kameraet er klar"
- "Ukendt opkaldsbegivenhed"
- "Tjeneste"
- "Konfiguration"
- "<Ikke angivet>"
- "Andre indstillinger for opkald"
- "Opkald via %s"
- "Indgående opkald via %s"
- "billede af kontaktperson"
- "gør privat"
- "vælg kontaktperson"
- "Skriv dit eget svar…"
- "Annuller"
- "Send"
- "Besvar"
- "Send sms"
- "Afvis"
- "Besvar som videoopkald"
- "Besvar som taleopkald"
- "Acceptér anmodning om video"
- "Afvis videoanmodning"
- "Acceptér anmodning om udgående video"
- "Afvis anmodning om udgående video"
- "Acceptér anmodning om indgående video"
- "Afvis anmodning om indgående video"
- "Skub op for at %s."
- "Skub til venstre for at %s."
- "Skub til højre for at %s."
- "Skub ned for at %s."
- "Vibration"
- "Vibration"
- "Lyd"
- "Standardlyd (%1$s)"
- "Ringetone ved opkald"
- "Vibrer ved opringning"
- "Ringetone og vibration"
- "Administrer telefonmøde"
- "Alarmnummer"
- "Profilbillede"
- "Kameraet er slukket"
- "via %s"
- "Noten er sendt"
- "Seneste beskeder"
- "Virksomhedsoplysninger"
- "%.1f mil væk"
- "%.1f km væk"
- "%1$s, %2$s"
- "%1$s-%2$s"
- "%1$s, %2$s"
- "Åbner i morgen kl. %s"
- "Åbner i dag kl. %s"
- "Lukker kl. %s"
- "Lukkede i dag kl. %s"
- "Åbent nu"
- "Lukket for i dag"
- "Formodet spammer"
- "Opkaldet blev afsluttet %1$s"
- "Dette er første gang, at dette nummer har ringet til dig."
- "Vi har mistanke om, at dette er et spamopkald."
- "Bloker/rap. spam"
- "Tilføj kontaktperson"
- "Ikke spam"
-
diff --git a/InCallUI/res/values-de/strings.xml b/InCallUI/res/values-de/strings.xml
deleted file mode 100644
index b3ecffc4c236de7218989b3e3aabd6e47634c733..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-de/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Gehaltener Anruf"
- "Unbekannt"
- "Private Nummer"
- "Münztelefon"
- "Telefonkonferenz"
- "Verbindung unterbrochen"
- "Lautsprecher"
- "Mobilgerät-Kopfhörer"
- "Kabelgebundenes Headset"
- "Bluetooth"
- "Folgende Töne senden?\n"
- "Töne werden gesendet\n"
- "Senden"
- "Ja"
- "Nein"
- "Platzhalter ersetzen durch"
- "Telefonkonferenz %s"
- "Mailboxnummer"
- "Rufaufbau"
- "Wahlwiederholung"
- "Telefonkonferenz"
- "Eingehender Anruf"
- "Eingeh. geschäftl. Anruf"
- "Anruf beendet"
- "Gehaltener Anruf"
- "Auflegen"
- "Im Gespräch"
- "Meine Nummer lautet %s"
- "Videoverbindung wird hergestellt"
- "Videoanruf"
- "Videoanfrage wird gesendet"
- "Videoanruf kann nicht verbunden werden"
- "Videoanfrage abgelehnt"
- "Deine Rückrufnummer lautet:\n %1$s"
- "Deine Notrufnummer lautet:\n %1$s"
- "Rufaufbau"
- "Verpasster Anruf"
- "Entgangene Anrufe"
- "%s entgangene Anrufe"
- "Verpasster Anruf von %s"
- "Aktiver Anruf"
- "Aktiver geschäftlicher Anruf"
- "Aktiver WLAN-Anruf"
- "Aktiver geschäftlicher WLAN-Anruf"
- "Gehaltener Anruf"
- "Eingehender Anruf"
- "Eingehender geschäftlicher Anruf"
- "Eingehender WLAN-Anruf"
- "Eingehender geschäftlicher WLAN-Anruf"
- "Eingehender Videoanruf"
- "Verdacht auf eingehenden Spam-Anruf"
- "Eingehende Videoanfrage"
- "Neue Mailbox-Nachricht"
- "Neue Mailbox-Nachricht (%d)"
- "%s wählen"
- "Mailboxnummer unbekannt"
- "Kein Service"
- "Ausgewähltes Netzwerk (%s) nicht verfügbar"
- "Annehmen"
- "Beenden"
- "Videoanruf"
- "Sprachanruf"
- "Akzeptieren"
- "Ablehnen"
- "Zurückrufen"
- "Nachricht"
- "Aktiver Anruf auf anderem Gerät"
- "Anruf übertragen"
- "Deaktiviere zunächst den Flugmodus, um einen Anruf zu tätigen."
- "Nicht in Netzwerk registriert."
- "Mobilfunknetz nicht verfügbar."
- "Gib eine gültige Nummer ein, um einen Anruf zu tätigen."
- "Anruf nicht möglich."
- "MMI-Sequenz wird gestartet…"
- "Dienst wird nicht unterstützt."
- "Anruf kann nicht gewechselt werden."
- "Anruf kann nicht getrennt werden."
- "Anruf kann nicht übergeben werden."
- "Konferenzschaltung nicht möglich."
- "Anruf kann nicht abgelehnt werden."
- "Anrufe können nicht freigegeben werden."
- "SIP-Anruf"
- "Notruf"
- "Mobilfunkverbindung wird aktiviert…"
- "Kein Service. Neuer Versuch…"
- "Anruf nicht möglich. %s ist keine Notrufnummer."
- "Anruf nicht möglich. Wähle eine Notrufnummer."
- "Zum Wählen Tastatur verwenden"
- "Anruf halten"
- "Anruf fortsetzen"
- "Anruf beenden"
- "Wähltasten einblenden"
- "Wähltasten ausblenden"
- "Stummschalten"
- "Stummschaltung aufheben"
- "Anruf hinzufügen"
- "Anrufe verbinden"
- "Wechseln"
- "Anrufe verwalten"
- "Telefonkonferenz verwalten"
- "Telefonkonferenz"
- "Verwalten"
- "Audio"
- "Videoanruf"
- "Zu Sprachanruf wechseln"
- "Kamera wechseln"
- "Kamera einschalten"
- "Kamera ausschalten"
- "Weitere Optionen"
- "Videoübertragung gestartet"
- "Videoübertragung gestoppt"
- "Kamera nicht bereit"
- "Kamera bereit"
- "Unbekanntes Ereignis während eines Anrufs"
- "Dienst"
- "Einrichtung"
- "<Nicht festgelegt>"
- "Sonstige Anrufeinstellungen"
- "Anruf über %s"
- "Eingehender Anruf über %s"
- "Kontaktbild"
- "privat sprechen"
- "Kontakt auswählen"
- "Eigene Antwort schreiben…"
- "Abbrechen"
- "Senden"
- "Annehmen"
- "SMS senden"
- "Ablehnen"
- "Als Videoanruf annehmen"
- "Als normalen Anruf annehmen"
- "Videoanfrage akzeptieren"
- "Videoanfrage ablehnen"
- "Anfrage für ausgehenden Videoanruf akzeptieren"
- "Anfrage für ausgehenden Videoanruf ablehnen"
- "Anfrage für eingehenden Videoanruf akzeptieren"
- "Anfrage für eingehenden Videoanruf ablehnen"
- "Zum %s nach oben schieben."
- "Zum %s nach links schieben."
- "Zum %s nach rechts schieben."
- "Zum %s nach unten schieben."
- "Vibrieren"
- "Vibrieren"
- "Ton"
- "Standardklingelton (%1$s)"
- "Klingelton"
- "Beim Klingeln vibrieren"
- "Klingelton & Vibration"
- "Telefonkonferenz verwalten"
- "Notrufnummer"
- "Profilbild"
- "Kamera aus"
- "über %s"
- "Notiz gesendet"
- "Zuletzt eingegangene Nachrichten"
- "Geschäftsinformationen"
- "%.1f Meilen entfernt"
- "%.1f Kilometer entfernt"
- "%1$s, %2$s"
- "%1$s bis %2$s"
- "%1$s, %2$s"
- "Öffnet morgen um %s"
- "Öffnet heute um %s"
- "Schließt um %s"
- "Hat heute um %s geschlossen"
- "Jetzt geöffnet"
- "Jetzt geschlossen"
- "Verdacht auf Spam"
- "Anruf beendet %1$s"
- "Du wurdest das erste Mal von dieser Nummer angerufen."
- "Dieser Anruf schien ein Spam-Anruf zu sein."
- "Blockieren/Spam melden"
- "Kontakt hinzufügen"
- "Kein Spam"
-
diff --git a/InCallUI/res/values-el/strings.xml b/InCallUI/res/values-el/strings.xml
deleted file mode 100644
index 99381329065a34a4ad0992a66717d84588ce478f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-el/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Τηλέφωνο"
- "Σε αναμονή"
- "Άγνωστος"
- "Απόκρυψη αριθμού"
- "Τηλέφωνο με χρέωση"
- "Κλήση συνδιάσκεψης"
- "Η κλήση απορρίφθηκε"
- "Ηχείο"
- "Ακουστικό"
- "Ενσύρματο ακουστικό"
- "Bluetooth"
- "Αποστολή των παρακάτω ήχων;\n"
- "Ήχοι αποστολής\n"
- "Αποστολή"
- "Ναι"
- "Όχι"
- "Αντικατάσταση του χαρακτήρα μπαλαντέρ με"
- "Κλήση συνδιάσκεψης %s"
- "Αριθμός αυτόματου τηλεφωνητή"
- "Κλήση"
- "Επανάκληση"
- "Κλήση συνδιάσκεψης"
- "Εισερχόμενη κλήση"
- "Εισερχόμ. κλήση εργασίας"
- "Η κλήση τερματίστηκε"
- "Σε αναμονή"
- "Κλείσιμο γραμμής"
- "Σε κλήση"
- "Ο αριθμός μου είναι %s"
- "Σύνδεση βίντεο"
- "Βιντεοκλήση"
- "Αίτημα βίντεο"
- "Δεν είναι δυνατή η σύνδεση βιντεοκλήσης"
- "Το αίτημα βίντεο απορρίφθηκε"
- "Αριθμός επανάκλησης\n %1$s"
- "Αριθμός επανάκλησης έκτακτης ανάγκης\n %1$s"
- "Κλήση"
- "Αναπάντητη κλήση"
- "Αναπάντητες κλήσεις"
- "%s αναπάντητες κλήσεις"
- "Αναπάντητη κλήση από %s"
- "Κλήση σε εξέλιξη"
- "Κλήση εργασίας σε εξέλιξη"
- "Κλήση Wi-Fi σε εξέλιξη"
- "Κλήση εργασίας μέσω Wi-Fi σε εξέλιξη"
- "Σε αναμονή"
- "Εισερχόμενη κλήση"
- "Εισερχόμενη κλήση εργασίας"
- "Εισερχόμενη κλήση μέσω Wi-Fi"
- "Εισερχόμενη κλήση εργασίας μέσω Wi-Fi"
- "Εισερχόμενη βιντεοκλήση"
- "Πιθανώς ανεπιθύμητη εισερχόμενη κλήση"
- "Αίτημα εισερχόμενου βίντεο"
- "Νέο μήνυμα στον αυτόματο τηλεφωνητή"
- "Νέο μήνυμα στον αυτόματο τηλεφωνητή (%d)"
- "Καλέστε στο %s"
- "Άγνωστος αριθμός αυτόματου τηλεφωνητή"
- "Δίκτυο μη διαθέσιμο"
- "Το επιλεγμένο δίκτυο (%s) δεν είναι διαθέσιμο"
- "Απάντηση"
- "Τερμ. κλήσης"
- "Βίντεο"
- "Φωνή"
- "Αποδοχή"
- "Παράβλεψη"
- "Επανάκληση"
- "Μήνυμα"
- "Κλήση σε εξέλιξη σε άλλη συσκευή"
- "Μεταφορά κλήσης"
- "Για να πραγματοποιήσετε μια κλήση, απενεργοποιήστε πρώτα τη λειτουργία πτήσης."
- "Δεν έχετε εγγραφεί στο δίκτυο."
- "Το δίκτυο κινητής τηλεφωνίας δεν είναι διαθέσιμο."
- "Για να πραγματοποιήσετε κλήση, εισαγάγετε έναν έγκυρο αριθμό."
- "Δεν είναι δυνατή η κλήση."
- "Έναρξη ακολουθίας MMI…"
- "Η υπηρεσία δεν υποστηρίζεται."
- "Δεν είναι δυνατή η εναλλαγή κλήσεων."
- "Δεν είναι δυνατός ο διαχωρισμός της κλήσης."
- "Δεν είναι δυνατή η μεταφορά."
- "Δεν είναι δυνατή η συνδιάσκεψη."
- "Δεν είναι δυνατή η απόρριψη της κλήσης."
- "Δεν είναι δυνατή η πραγματοποίηση κλήσεων."
- "Κλήση SIP"
- "Κλήση έκτακτης ανάγκης"
- "Ενεργοποίηση πομπού…"
- "Δεν υπάρχει υπηρεσία. Νέα προσπάθεια…"
- "Δεν είναι δυνατή η κλήση. Το %s δεν είναι αριθμός έκτακτης ανάγκης."
- "Δεν είναι δυνατή η κλήση. Πληκτρολογήστε έναν αριθμό έκτακτης ανάγκης."
- "Χρησιμοποιήστε το πληκτρολόγιο για να πραγματοποιήσετε μια κλήση"
- "Αναμονή κλήσης"
- "Συνέχιση κλήσης"
- "Τερματισμός κλήσης"
- "Εμφάνιση πληκτρολογίου κλήσης"
- "Απόκρυψη πληκτρολογίου κλήσης"
- "Σίγαση"
- "Κατάργηση σίγασης"
- "Προσθήκη κλήσης"
- "Συγχώνευση κλήσεων"
- "Ανταλλαγή"
- "Διαχείριση κλήσεων"
- "Διαχείριση κλήσης συνδιάσκεψης"
- "Κλήση διάσκεψης"
- "Διαχείριση"
- "Ήχος"
- "Βιντεοκλ."
- "Αλλαγή σε φωνητική κλήση"
- "Αλλαγή κάμερας"
- "Ενεργοποίηση κάμερας"
- "Απενεργοποίηση κάμερας"
- "Περισσότερες επιλογές"
- "Το πρόγραμμα αναπαραγωγής βίντεο ξεκίνησε"
- "Το πρόγραμμα αναπαραγωγής βίντεο διακόπηκε"
- "Η κάμερα δεν είναι έτοιμη"
- "Η κάμερα είναι έτοιμη"
- "Άγνωστο συμβάν περιόδου σύνδεσης κλήσης"
- "Υπηρεσία"
- "Ρύθμιση"
- "<Δεν έχει οριστεί>"
- "Άλλες ρυθμίσεις κλήσης"
- "Κλήση μέσω %s"
- "Εισερχόμενη κλήση μέσω %s"
- "φωτογραφία επαφής"
- "ιδιωτική χρήση"
- "επιλογή επαφής"
- "Συντάξτε τη δική σας…"
- "Ακύρωση"
- "Αποστολή"
- "Απάντηση"
- "Αποστολή SMS"
- "Απόρριψη"
- "Απάντηση ως βιντεοκλήση"
- "Απάντηση ως κλήση ήχου"
- "Αποδοχή αιτήματος βίντεο"
- "Απόρριψη αιτήματος βίντεο"
- "Αποδοχή αιτήματος μετάδοσης βίντεο"
- "Απόρριψη αιτήματος μετάδοσης βίντεο"
- "Αποδοχή αιτήματος λήψης βίντεο"
- "Απόρριψη αιτήματος λήψης βίντεο"
- "Κύλιση προς τα επάνω για %s."
- "Κύλιση προς τα αριστερά για %s."
- "Κύλιση προς τα δεξιά για %s."
- "Κύλιση προς τα κάτω για %s."
- "Δόνηση"
- "Δόνηση"
- "Ήχος"
- "Προεπιλεγμένος ήχος (%1$s)"
- "Ήχος κλήσης τηλεφώνου"
- "Δόνηση κατά το κουδούνισμα"
- "Ήχος κλήσης και δόνηση"
- "Διαχείριση κλήσης συνδιάσκεψης"
- "Αριθμός έκτακτης ανάγκης"
- "Φωτογραφία προφίλ"
- "Απενεργοποίηση κάμερας"
- "μέσω %s"
- "Η σημείωση εστάλη"
- "Πρόσφατα μηνύματα"
- "Πληροφορίες επιχείρησης"
- "%.1f μίλια μακριά"
- "%.1f χιλιόμετρα μακριά"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Ανοίγει αύριο στις %s"
- "Ανοίγει σήμερα στις %s"
- "Κλείνει στις %s"
- "Έκλεισε σήμερα στις %s"
- "Ανοιχτό τώρα"
- "Κλειστό τώρα"
- "Πιθανώς ανεπιθύμητος"
- "Η κλήση τερματίστηκε %1$s"
- "Αυτή είναι η πρώτη φορά που σας καλεί αυτός ο αριθμός."
- "Έχουμε υποψίες ότι αυτή κλήση είναι ανεπιθύμητη."
- "Αποκλ./αναφ. ανεπιθ."
- "Προσθήκη επαφής"
- "Μη ανεπιθύμητος"
-
diff --git a/InCallUI/res/values-en-rAU/strings.xml b/InCallUI/res/values-en-rAU/strings.xml
deleted file mode 100644
index 013aa9685eac96cb59b90617fdd2112c1adedca0..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-en-rAU/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Phone"
- "On hold"
- "unknown"
- "Private number"
- "Payphone"
- "Conference call"
- "Call cut off"
- "Speaker"
- "Handset earpiece"
- "Wired headset"
- "Bluetooth"
- "Send the following tones?\n"
- "Sending tones\n"
- "Send"
- "yes"
- "no"
- "Replace wild character with"
- "Conference call %s"
- "Voicemail number"
- "Dialling"
- "Redialling"
- "Conference call"
- "Incoming call"
- "Incoming work call"
- "Call ended"
- "On hold"
- "Hanging up"
- "In call"
- "My number is %s"
- "Connecting video"
- "Video call"
- "Requesting video"
- "Can\'t connect video call"
- "Video request rejected"
- "Your callback number\n %1$s"
- "Your emergency callback number\n %1$s"
- "Dialling"
- "Missed call"
- "Missed calls"
- "%s missed calls"
- "Missed call from %s"
- "On-going call"
- "Ongoing work call"
- "Ongoing Wi-Fi call"
- "Ongoing Wi-Fi work call"
- "On hold"
- "Incoming call"
- "Incoming work call"
- "Incoming Wi-Fi call"
- "Incoming Wi-Fi work call"
- "Incoming video call"
- "Incoming suspected spam call"
- "Incoming video request"
- "New voicemail"
- "New voicemail (%d)"
- "Dial %s"
- "Voicemail number unknown"
- "No service"
- "Selected network (%s) unavailable"
- "Answer"
- "Hang up"
- "In-stream video"
- "Voice"
- "Accept"
- "Dismiss"
- "Call back"
- "Message"
- "Ongoing call on another device"
- "Transfer call"
- "To place a call, first turn off Aeroplane mode."
- "Not registered on network."
- "Mobile network not available."
- "To place a call, enter a valid number."
- "Can\'t call."
- "Starting MMI sequence…"
- "Service not supported."
- "Can\'t switch calls."
- "Can\'t separate call."
- "Can\'t transfer."
- "Can\'t conference."
- "Can\'t reject call."
- "Can\'t release call(s)."
- "SIP call"
- "Emergency call"
- "Turning on radio…"
- "No network. Trying again…"
- "Can\'t call. %s is not an emergency number."
- "Can\'t call. Dial an emergency number."
- "Use keyboard to dial"
- "Hold Call"
- "Resume Call"
- "End Call"
- "Show dial pad"
- "Hide dial pad"
- "Mute"
- "Unmute"
- "Add call"
- "Merge calls"
- "Swap"
- "Manage calls"
- "Manage conference call"
- "Conference call"
- "Manage"
- "Audio"
- "Video call"
- "Change to voice call"
- "Switch camera"
- "Turn on camera"
- "Turn off camera"
- "More options"
- "Player Started"
- "Player Stopped"
- "Camera not ready"
- "Camera ready"
- "Unknown call session event"
- "Service"
- "Set up"
- "<Not set>"
- "Other call settings"
- "Calling via %s"
- "Incoming via %s"
- "contact photo"
- "go private"
- "select contact"
- "Write your own..."
- "cancel"
- "Send"
- "Answer"
- "Send SMS"
- "Decline"
- "Answer as video call"
- "Answer as audio call"
- "Accept video request"
- "Decline video request"
- "Accept video transmit request"
- "Decline video transmit request"
- "Accept video receive request"
- "Decline video receive request"
- "Slide up for %s."
- "Slide left for %s."
- "Slide right for %s."
- "Slide down for %s."
- "Vibrate"
- "Vibrate"
- "Sound"
- "Default sound (%1$s)"
- "Phone ringtone"
- "Vibrate when ringing"
- "Ringtone & Vibrate"
- "Manage conference call"
- "Emergency number"
- "Profile photo"
- "Camera off"
- "via %s"
- "Note sent"
- "Recent messages"
- "Business info"
- "%.1f mi away"
- "%.1f km away"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Opens tomorrow at %s"
- "Opens today at %s"
- "Closes at %s"
- "Closed today at %s"
- "Open now"
- "Closed now"
- "Suspected spam caller"
- "Call ended %1$s"
- "This is the first time that this number has called you."
- "We suspected that this call was from a spammer."
- "Block/report spam"
- "Add contact"
- "Not spam"
-
diff --git a/InCallUI/res/values-en-rGB/strings.xml b/InCallUI/res/values-en-rGB/strings.xml
deleted file mode 100644
index 013aa9685eac96cb59b90617fdd2112c1adedca0..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-en-rGB/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Phone"
- "On hold"
- "unknown"
- "Private number"
- "Payphone"
- "Conference call"
- "Call cut off"
- "Speaker"
- "Handset earpiece"
- "Wired headset"
- "Bluetooth"
- "Send the following tones?\n"
- "Sending tones\n"
- "Send"
- "yes"
- "no"
- "Replace wild character with"
- "Conference call %s"
- "Voicemail number"
- "Dialling"
- "Redialling"
- "Conference call"
- "Incoming call"
- "Incoming work call"
- "Call ended"
- "On hold"
- "Hanging up"
- "In call"
- "My number is %s"
- "Connecting video"
- "Video call"
- "Requesting video"
- "Can\'t connect video call"
- "Video request rejected"
- "Your callback number\n %1$s"
- "Your emergency callback number\n %1$s"
- "Dialling"
- "Missed call"
- "Missed calls"
- "%s missed calls"
- "Missed call from %s"
- "On-going call"
- "Ongoing work call"
- "Ongoing Wi-Fi call"
- "Ongoing Wi-Fi work call"
- "On hold"
- "Incoming call"
- "Incoming work call"
- "Incoming Wi-Fi call"
- "Incoming Wi-Fi work call"
- "Incoming video call"
- "Incoming suspected spam call"
- "Incoming video request"
- "New voicemail"
- "New voicemail (%d)"
- "Dial %s"
- "Voicemail number unknown"
- "No service"
- "Selected network (%s) unavailable"
- "Answer"
- "Hang up"
- "In-stream video"
- "Voice"
- "Accept"
- "Dismiss"
- "Call back"
- "Message"
- "Ongoing call on another device"
- "Transfer call"
- "To place a call, first turn off Aeroplane mode."
- "Not registered on network."
- "Mobile network not available."
- "To place a call, enter a valid number."
- "Can\'t call."
- "Starting MMI sequence…"
- "Service not supported."
- "Can\'t switch calls."
- "Can\'t separate call."
- "Can\'t transfer."
- "Can\'t conference."
- "Can\'t reject call."
- "Can\'t release call(s)."
- "SIP call"
- "Emergency call"
- "Turning on radio…"
- "No network. Trying again…"
- "Can\'t call. %s is not an emergency number."
- "Can\'t call. Dial an emergency number."
- "Use keyboard to dial"
- "Hold Call"
- "Resume Call"
- "End Call"
- "Show dial pad"
- "Hide dial pad"
- "Mute"
- "Unmute"
- "Add call"
- "Merge calls"
- "Swap"
- "Manage calls"
- "Manage conference call"
- "Conference call"
- "Manage"
- "Audio"
- "Video call"
- "Change to voice call"
- "Switch camera"
- "Turn on camera"
- "Turn off camera"
- "More options"
- "Player Started"
- "Player Stopped"
- "Camera not ready"
- "Camera ready"
- "Unknown call session event"
- "Service"
- "Set up"
- "<Not set>"
- "Other call settings"
- "Calling via %s"
- "Incoming via %s"
- "contact photo"
- "go private"
- "select contact"
- "Write your own..."
- "cancel"
- "Send"
- "Answer"
- "Send SMS"
- "Decline"
- "Answer as video call"
- "Answer as audio call"
- "Accept video request"
- "Decline video request"
- "Accept video transmit request"
- "Decline video transmit request"
- "Accept video receive request"
- "Decline video receive request"
- "Slide up for %s."
- "Slide left for %s."
- "Slide right for %s."
- "Slide down for %s."
- "Vibrate"
- "Vibrate"
- "Sound"
- "Default sound (%1$s)"
- "Phone ringtone"
- "Vibrate when ringing"
- "Ringtone & Vibrate"
- "Manage conference call"
- "Emergency number"
- "Profile photo"
- "Camera off"
- "via %s"
- "Note sent"
- "Recent messages"
- "Business info"
- "%.1f mi away"
- "%.1f km away"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Opens tomorrow at %s"
- "Opens today at %s"
- "Closes at %s"
- "Closed today at %s"
- "Open now"
- "Closed now"
- "Suspected spam caller"
- "Call ended %1$s"
- "This is the first time that this number has called you."
- "We suspected that this call was from a spammer."
- "Block/report spam"
- "Add contact"
- "Not spam"
-
diff --git a/InCallUI/res/values-en-rIN/strings.xml b/InCallUI/res/values-en-rIN/strings.xml
deleted file mode 100644
index 013aa9685eac96cb59b90617fdd2112c1adedca0..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-en-rIN/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Phone"
- "On hold"
- "unknown"
- "Private number"
- "Payphone"
- "Conference call"
- "Call cut off"
- "Speaker"
- "Handset earpiece"
- "Wired headset"
- "Bluetooth"
- "Send the following tones?\n"
- "Sending tones\n"
- "Send"
- "yes"
- "no"
- "Replace wild character with"
- "Conference call %s"
- "Voicemail number"
- "Dialling"
- "Redialling"
- "Conference call"
- "Incoming call"
- "Incoming work call"
- "Call ended"
- "On hold"
- "Hanging up"
- "In call"
- "My number is %s"
- "Connecting video"
- "Video call"
- "Requesting video"
- "Can\'t connect video call"
- "Video request rejected"
- "Your callback number\n %1$s"
- "Your emergency callback number\n %1$s"
- "Dialling"
- "Missed call"
- "Missed calls"
- "%s missed calls"
- "Missed call from %s"
- "On-going call"
- "Ongoing work call"
- "Ongoing Wi-Fi call"
- "Ongoing Wi-Fi work call"
- "On hold"
- "Incoming call"
- "Incoming work call"
- "Incoming Wi-Fi call"
- "Incoming Wi-Fi work call"
- "Incoming video call"
- "Incoming suspected spam call"
- "Incoming video request"
- "New voicemail"
- "New voicemail (%d)"
- "Dial %s"
- "Voicemail number unknown"
- "No service"
- "Selected network (%s) unavailable"
- "Answer"
- "Hang up"
- "In-stream video"
- "Voice"
- "Accept"
- "Dismiss"
- "Call back"
- "Message"
- "Ongoing call on another device"
- "Transfer call"
- "To place a call, first turn off Aeroplane mode."
- "Not registered on network."
- "Mobile network not available."
- "To place a call, enter a valid number."
- "Can\'t call."
- "Starting MMI sequence…"
- "Service not supported."
- "Can\'t switch calls."
- "Can\'t separate call."
- "Can\'t transfer."
- "Can\'t conference."
- "Can\'t reject call."
- "Can\'t release call(s)."
- "SIP call"
- "Emergency call"
- "Turning on radio…"
- "No network. Trying again…"
- "Can\'t call. %s is not an emergency number."
- "Can\'t call. Dial an emergency number."
- "Use keyboard to dial"
- "Hold Call"
- "Resume Call"
- "End Call"
- "Show dial pad"
- "Hide dial pad"
- "Mute"
- "Unmute"
- "Add call"
- "Merge calls"
- "Swap"
- "Manage calls"
- "Manage conference call"
- "Conference call"
- "Manage"
- "Audio"
- "Video call"
- "Change to voice call"
- "Switch camera"
- "Turn on camera"
- "Turn off camera"
- "More options"
- "Player Started"
- "Player Stopped"
- "Camera not ready"
- "Camera ready"
- "Unknown call session event"
- "Service"
- "Set up"
- "<Not set>"
- "Other call settings"
- "Calling via %s"
- "Incoming via %s"
- "contact photo"
- "go private"
- "select contact"
- "Write your own..."
- "cancel"
- "Send"
- "Answer"
- "Send SMS"
- "Decline"
- "Answer as video call"
- "Answer as audio call"
- "Accept video request"
- "Decline video request"
- "Accept video transmit request"
- "Decline video transmit request"
- "Accept video receive request"
- "Decline video receive request"
- "Slide up for %s."
- "Slide left for %s."
- "Slide right for %s."
- "Slide down for %s."
- "Vibrate"
- "Vibrate"
- "Sound"
- "Default sound (%1$s)"
- "Phone ringtone"
- "Vibrate when ringing"
- "Ringtone & Vibrate"
- "Manage conference call"
- "Emergency number"
- "Profile photo"
- "Camera off"
- "via %s"
- "Note sent"
- "Recent messages"
- "Business info"
- "%.1f mi away"
- "%.1f km away"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Opens tomorrow at %s"
- "Opens today at %s"
- "Closes at %s"
- "Closed today at %s"
- "Open now"
- "Closed now"
- "Suspected spam caller"
- "Call ended %1$s"
- "This is the first time that this number has called you."
- "We suspected that this call was from a spammer."
- "Block/report spam"
- "Add contact"
- "Not spam"
-
diff --git a/InCallUI/res/values-es-rUS/strings.xml b/InCallUI/res/values-es-rUS/strings.xml
deleted file mode 100644
index 915c90779e1dadf39f7282c3a736cbcec00b98f2..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-es-rUS/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Teléfono"
- "En espera"
- "Desconocido"
- "Número privado"
- "Teléfono pago"
- "Llamada en conferencia"
- "Se interrumpió la llamada"
- "Altavoz"
- "Auricular del dispositivo"
- "Auriculares con cable"
- "Bluetooth"
- "¿Deseas enviar los siguientes tonos?\n"
- "Enviando tonos\n"
- "Enviar"
- "Sí"
- "No"
- "Reemplazar el carácter comodín con"
- "Llamada en conferencia: %s"
- "Número de buzón de voz"
- "Marcando"
- "Volviendo a marcar"
- "Llamada en conferencia"
- "Llamada entrante"
- "Llamada entrante: trabajo"
- "Llamada finalizada"
- "En espera"
- "Colgando"
- "En llamada"
- "Mi número es %s"
- "Conectando video"
- "Videollamada"
- "Solicitando video"
- "No se puede conectar la videollamada"
- "Se rechazó la solicitud de videollamada"
- "Número de devolución de llamada\n %1$s"
- "Número de devolución de llamada de emergencia\n %1$s"
- "Marcando"
- "Llamada perdida"
- "Llamadas perdidas"
- "%s llamadas perdidas"
- "Llamada perdida de %s"
- "Llamada en curso"
- "Llamada en curso: trabajo"
- "Llamada Wi-Fi en curso"
- "Llamada Wi-Fi en curso: trabajo"
- "En espera"
- "Llamada entrante"
- "Llamada entrante: trabajo"
- "Llamada Wi-Fi entrante"
- "Llamada Wi-Fi entrante: trabajo"
- "Videollamada entrante"
- "Posible llamada entrante de spam"
- "Solicitud de videollamada entrante"
- "Nuevo mensaje de buzón de voz"
- "Buzón de voz nuevo (%d)"
- "Marcar %s"
- "Número de buzón de voz desconocido"
- "Sin servicio"
- "La red seleccionada (%s) no está disponible"
- "Responder"
- "Colgar"
- "Video"
- "Voz"
- "Aceptar"
- "Descartar"
- "Llamar"
- "Mensaje"
- "Llamada en curso en otro dispositivo"
- "Transferir llamada"
- "Para realizar una llamada, primero debes desactivar el modo de avión."
- "No está registrado en la red."
- "La red móvil no está disponible."
- "Para realizar una llamada, ingresa un número válido."
- "No se puede realizar la llamada."
- "Iniciando la secuencia de MMI…"
- "El servicio no es compatible."
- "No se pueden cambiar las llamadas."
- "No se puede desviar la llamada."
- "No se puede transferir."
- "No se puede realizar la conferencia."
- "No se puede rechazar la llamada."
- "No se pueden liberar las llamadas."
- "Llamada SIP"
- "Llamada de emergencia"
- "Encendiendo radio…"
- "No hay servicio. Vuelve a intentarlo…"
- "No se puede realizar la llamada. %s no es un número de emergencia."
- "No se puede realizar la llamada. Marca un número de emergencia."
- "Usar teclado para marcar"
- "Retener llamada"
- "Reanudar llamada"
- "Finalizar llamada"
- "Mostrar teclado"
- "Ocultar teclado"
- "Silenciar"
- "Dejar de silenciar"
- "Agregar llamada"
- "Combinar llamadas"
- "Cambiar"
- "Administrar llamadas"
- "Administrar conferencia"
- "Llamada en conferencia"
- "Administrar"
- "Audio"
- "Video"
- "Cambiar a llamada de voz"
- "Cambiar cámara"
- "Activar la cámara"
- "Desactivar la cámara"
- "Más opciones"
- "Se inició el reproductor"
- "Se detuvo el reproductor"
- "La cámara no está lista"
- "Cámara lista"
- "Evento de sesión de llamada desconocido"
- "Servicio"
- "Configuración"
- "<Sin configurar>"
- "Otras opciones de llamada"
- "Llamada por medio de %s"
- "Entrantes por medio de %s"
- "foto de contacto"
- "pasar a modo privado"
- "seleccionar contacto"
- "Escribe tu propia respuesta…"
- "Cancelar"
- "Enviar"
- "Responder"
- "Enviar SMS"
- "Rechazar"
- "Responder como videollamada"
- "Responder como llamada de audio"
- "Aceptar solicitud de videollamada"
- "Rechazar solicitud de videollamada"
- "Aceptar solicitud de transmisión de videollamada"
- "Rechazar solicitud de transmisión de videollamada"
- "Aceptar solicitud de recepción de videollamada"
- "Rechazar solicitud de recepción de videollamada"
- "Desliza el dedo hacia arriba para %s."
- "Desliza el dedo hacia la izquierda para %s."
- "Desliza el dedo hacia la derecha para %s."
- "Desliza el dedo hacia abajo para %s."
- "Vibrar"
- "Vibrar"
- "Sonido"
- "Sonido predeterminado (%1$s)"
- "Tono del teléfono"
- "Vibrar al sonar"
- "Tono y vibración"
- "Administrar llamada en conferencia"
- "Número de emergencia"
- "Foto de perfil"
- "Cámara desactivada"
- "del %s"
- "Se envió la nota"
- "Mensajes recientes"
- "Información de la empresa"
- "A %.1f mi"
- "A %.1f km"
- "%1$s, %2$s"
- "De %1$s a %2$s"
- "%1$s y %2$s"
- "Abre mañana a la hora %s"
- "Abre hoy a la hora %s"
- "Cierra a la hora %s"
- "Cerró hoy a la hora %s"
- "Abierto ahora"
- "Cerrado ahora"
- "Posible spam"
- "Llamada finalizada %1$s"
- "Es la primera vez que te llaman desde este número."
- "Sospechamos que esta llamada era spam."
- "Bloquear/denunciar"
- "Agregar contacto"
- "No es spam"
-
diff --git a/InCallUI/res/values-es/strings.xml b/InCallUI/res/values-es/strings.xml
deleted file mode 100644
index ab570d593b3628fa537bc2053024f3490835e376..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-es/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Teléfono"
- "En espera"
- "Desconocida"
- "Número privado"
- "Teléfono público"
- "Conferencia"
- "Llamada perdida"
- "Altavoz"
- "Auricular"
- "Auriculares con cable"
- "Bluetooth"
- "¿Quieres enviar los siguientes tonos?\n"
- "Enviando tonos\n"
- "Enviar"
- "Sí"
- "No"
- "Sustituir el carácter comodín por"
- "Conferencia %s"
- "Número del mensaje de voz"
- "Llamando"
- "Llamando otra vez"
- "Conferencia"
- "Llamada entrante"
- "Llamada trabajo entrante"
- "Llamada finalizada"
- "En espera"
- "Colgando"
- "Llamada entrante"
- "Mi número es el %s"
- "Conectando videollamada"
- "Videollamada"
- "Solicitando videollamada"
- "No se puede establecer la videollamada"
- "Solicitud de videollamada rechazada"
- "Tu número de devolución de llamada\n %1$s"
- "Tu número de devolución de llamada de emergencia\n %1$s"
- "Llamando"
- "Llamada perdida"
- "Llamadas perdidas"
- "%s llamadas perdidas"
- "Llamada perdida de %s"
- "Llamada en curso"
- "Llamada de trabajo en curso"
- "Llamada Wi-Fi en curso"
- "Llamada Wi-Fi de trabajo en curso"
- "En espera"
- "Llamada entrante"
- "Llamada de trabajo entrante"
- "Llamada Wi-Fi entrante"
- "Llamada Wi-Fi de trabajo entrante"
- "Videollamada entrante"
- "Llamada entrante sospechosa de spam"
- "Solicitud de videollamada entrante"
- "Nuevo mensaje de voz"
- "Nuevo mensaje de voz (%d)"
- "Marcar %s"
- "Número del mensaje de voz desconocido"
- "Sin servicio"
- "La red seleccionada (%s) no está disponible"
- "Responder"
- "Colgar"
- "Videollamada"
- "Voz"
- "Aceptar"
- "Rechazar"
- "Llamar"
- "Mensaje"
- "Llamada activa en otro dispositivo"
- "Transferir llamada"
- "Para realizar una llamada, primero debes desactivar el modo avión."
- "No estás registrado en la red."
- "La red móvil no está disponible."
- "Para realizar una llamada, introduce un número válido."
- "No se puede establecer la llamada."
- "Iniciando secuencia MMI..."
- "Servicio no admitido."
- "No se pueden intercambiar llamadas."
- "No se pueden separar llamadas."
- "No se puede transferir."
- "No se puede establecer la conferencia."
- "No se puede rechazar la llamada."
- "No se pueden hacer llamadas."
- "Llamada SIP"
- "Llamada de emergencia"
- "Activando señal móvil…"
- "Sin servicio. Reintentado…"
- "No se puede establecer la llamada. %s no es un número de emergencia."
- "No se puede establecer la llamada. Marca un número de emergencia."
- "Usa el teclado para marcar"
- "Retener llamada"
- "Seguir con la llamada"
- "Finalizar llamada"
- "Mostrar teclado"
- "Ocultar teclado"
- "Silenciar"
- "Activar sonido"
- "Añadir llamada"
- "Llamada a tres"
- "Cambiar"
- "Administrar llamadas"
- "Administrar conferencia"
- "Teleconferencia"
- "Gestionar"
- "Audio"
- "Videollamada"
- "Cambiar a llamada de voz"
- "Cambiar cámara"
- "Activar cámara"
- "Desactivar cámara"
- "Más opciones"
- "Reproductor iniciado"
- "Reproductor detenido"
- "Cámara no preparada"
- "Cámara preparada"
- "Evento de sesión de llamada desconocido"
- "Servicio"
- "Configuración"
- "<No definido>"
- "Otra configuración de llamada"
- "Llamada a través de %s"
- "Recibidas a través de %s"
- "foto de contacto"
- "llamada privada"
- "seleccionar contacto"
- "Escribe tu propia respuesta..."
- "Cancelar"
- "Enviar"
- "Responder"
- "Enviar SMS"
- "Rechazar"
- "Responder como videollamada"
- "Responder como llamada de audio"
- "Aceptar solicitud de videollamada"
- "Rechazar solicitud de videollamada"
- "Aceptar solicitud de transmisión de videollamada"
- "Rechazar solicitud de transmisión de videollamada"
- "Aceptar solicitud de recepción de videollamada"
- "Rechazar solicitud de recepción de videollamada"
- "Desliza el dedo hacia arriba para %s."
- "Desliza el dedo hacia la izquierda para %s."
- "Desliza el dedo hacia la derecha para %s."
- "Desliza el dedo hacia abajo para %s."
- "Vibrar"
- "Vibrar"
- "Sonido"
- "Sonido predeterminado (%1$s)"
- "Tono de llamada del teléfono"
- "Vibrar al sonar"
- "Tono de llamada y vibración"
- "Administrar videollamada"
- "Número de emergencia"
- "Foto de perfil"
- "Cámara apagada"
- "a través de %s"
- "Nota enviada"
- "Mensajes recientes"
- "Información de la empresa"
- "A %.1f mi"
- "A %.1f km"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Abre mañana a las %s"
- "Abre hoy a las %s"
- "Cierra a las %s"
- "Cerrado hoy a las %s"
- "Abierto ahora"
- "Cerrado ahora"
- "Sospechoso de spam"
- "Llamada de %1$s terminada"
- "Es la primera vez que recibes una llamada de este número."
- "Sospechábamos que esta llamada era de spam."
- "Bloquear / Marcar como spam"
- "Añadir contacto"
- "No es spam"
-
diff --git a/InCallUI/res/values-et/strings.xml b/InCallUI/res/values-et/strings.xml
deleted file mode 100644
index 5d2a0d8b0be89ad04dfb8fc8bec8818f2441385b..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-et/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Ootel"
- "Tundmatu"
- "Eranumber"
- "Telefoniautomaat"
- "Konverentskõne"
- "Kõne katkes"
- "Kõlar"
- "Käsitelefoni kuular"
- "Juhtmega peakomplekt"
- "Bluetooth"
- "Kas saata järgmised toonid?\n"
- "Toonide saatmine\n"
- "Saada"
- "Jah"
- "Ei"
- "Asenda metamärk üksusega"
- "Konverentskõne %s"
- "Kõneposti number"
- "Valimine"
- "Uuesti valimine"
- "Konverentskõne"
- "Sissetulev kõne"
- "Sissetulev töökõne"
- "Kõne lõpetati"
- "Ootel"
- "Lõpetamine"
- "Kõne on pooleli"
- "Minu number on %s"
- "Video ühendamine"
- "Videokõne"
- "Video taotlemine"
- "Videokõnet ei õnnestu ühendada"
- "Videokõne taotlus lükati tagasi"
- "Teie tagasihelistamise number\n%1$s"
- "Teie hädaabikõne tagasihelistamise number\n%1$s"
- "Valimine"
- "Vastamata kõne"
- "Vastamata kõned"
- "%s vastamata kõnet"
- "Vastamata kõne helistajalt %s"
- "Käimasolev kõne"
- "Käimasolev töökõne"
- "Käimasolev WiFi-kõne"
- "Käimasolev töökõne WiFi kaudu"
- "Ootel"
- "Sissetulev kõne"
- "Sissetulev töökõne"
- "Sissetulev WiFi-kõne"
- "Sissetulev töökõne WiFi kaudu"
- "Sissetulev videokõne"
- "Arvatav sissetulev rämpskõne"
- "Sissetulev videokõne taotlus"
- "Uus kõnepostisõnum"
- "Uus kõnepostisõnum (%d)"
- "Valige %s"
- "Kõnepostinumber on tundmatu"
- "Levi puudub"
- "Valitud võrk (%s) pole saadaval"
- "Vasta"
- "Lõpeta kõne"
- "Videokõne"
- "Häälkõne"
- "Nõustu"
- "Loobu"
- "Helista tagasi"
- "Saada sõnum"
- "Pooleliolev kõne teise seadmes"
- "Kõne ülekandmine"
- "Helistamiseks lülitage esmalt lennukirežiim välja."
- "Ei ole võrgus registreeritud."
- "Mobiilsidevõrk pole saadaval."
- "Helistamiseks sisestage kehtiv number."
- "Ei saa helistada."
- "MMI-jada alustamine …"
- "Teenust ei toetata."
- "Kõnesid ei saa vahetada."
- "Kõnet ei saa eraldada."
- "Ei saa üle kanda."
- "Konverentskõnet ei saa pidada."
- "Kõnet ei saa tagasi lükata."
- "Kõnesid ei saa vabastada."
- "SIP-kõne"
- "Hädaabikõne"
- "Raadioside sisselülitamine …"
- "Levi puudub. Uuesti proovimine …"
- "Ei saa helistada. %s ei ole hädaabinumber."
- "Ei saa helistada. Valige hädaabinumber."
- "Kasutage valimiseks klaviatuuri"
- "Kõne ootele"
- "Jätka kõnet"
- "Lõpeta kõne"
- "Kuva valimisklahvistik"
- "Peida valimisklahvistik"
- "Vaigista"
- "Tühista vaigistus"
- "Lisa kõne"
- "Ühenda kõned"
- "Vaheta"
- "Halda kõnesid"
- "Halda konverentskõnet"
- "Konverentskõne"
- "Halda"
- "Heli"
- "Videokõne"
- "Mine üle häälkõnele"
- "Vaheta kaamerat"
- "Lülita kaamera sisse"
- "Lülita kaamera välja"
- "Rohkem valikuid"
- "Pleier käivitati"
- "Pleier peatati"
- "Kaamera pole valmis"
- "Kaamera on valmis"
- "Tundmatu kõneseansisündmus"
- "Teenus"
- "Seadistamine"
- "<Määramata>"
- "Muud kõneseaded"
- "Kõne edastab %s"
- "Sissetulev kõne teenusepakkuja %s kaudu"
- "kontakti foto"
- "aktiveeri privaatne kõne"
- "vali kontakt"
- "Kirjutage ise …"
- "Tühista"
- "Saada"
- "Vastamine"
- "Saada SMS"
- "Tagasilükkamine"
- "Vastamine videokõnena"
- "Vastamine helikõnena"
- "Video taotluse aktsepteerimine"
- "Video taotluse tagasilükkamine"
- "Video edastamise taotluse aktsepteerimine"
- "Video edastamise taotluse tagasilükkamine"
- "Video vastuvõtmise taotluse aktsepteerimine"
- "Video vastuvõtmise taotluse tagasilükkamine"
- "Lohistage üles: %s."
- "Lohistage vasakule: %s."
- "Lohistage paremale: %s."
- "Lohistage alla: %s."
- "Vibreerimine"
- "Vibreerimine"
- "Heli"
- "Vaikeheli (%1$s)"
- "Telefonihelin"
- "Vibreerimine helina ajal"
- "Helin ja vibratsioon"
- "Konverentskõne haldamine"
- "Hädaabinumber"
- "Profiilifoto"
- "Kaamera on välja lülitatud"
- "numbri %s kaudu"
- "Märkus on saadetud"
- "Hiljutised sõnumid"
- "Ettevõtte teave"
- "%.1f miili kaugusel"
- "%.1f km kaugusel"
- "%1$s, %2$s"
- "%1$s kuni %2$s"
- "%1$s, %2$s"
- "Avatakse homme kell %s"
- "Avatakse täna kell %s"
- "Suletakse kell %s"
- "Suleti täna kell %s"
- "Praegu avatud"
- "Praegu suletud"
- "Arvatav rämpskõne"
- "Kõne lõppes: %1$s"
- "Teile helistati sellelt numbrilt esimest korda."
- "Kahtlustasime, et see võis olla rämpskõne."
- "Blokeeri / teavita rämpskõnest"
- "Lisa kontakt"
- "Pole rämpskõne"
-
diff --git a/InCallUI/res/values-eu/strings.xml b/InCallUI/res/values-eu/strings.xml
deleted file mode 100644
index c300c47cdb80f2573a508604ebd7e0a974b67bde..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-eu/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefonoa"
- "Zain"
- "Ezezaguna"
- "Zenbaki pribatua"
- "Telefono publikoa"
- "Konferentzia-deia"
- "Eten egin da deia"
- "Bozgorailua"
- "Aurikularrak"
- "Kabledun entzungailua"
- "Bluetooth konexioa"
- "Tonu hauek bidali nahi dituzu?\n"
- "Tonuak bidaltzen\n"
- "Bidali"
- "Bai"
- "Ez"
- "Ordeztu komodina honekin:"
- "Konferentzia-deiaren ordua: %s"
- "Erantzungailuaren zenbakia"
- "Deitzen"
- "Berriro markatzen"
- "Konferentzia-deia"
- "Dei bat jaso duzu"
- "Laneko dei bat jaso duzu"
- "Amaitu da deia"
- "Zain"
- "Deia amaitzen"
- "Deia abian"
- "Nire zenbakia %s da"
- "Bideoa konektatzen"
- "Bideo-deia"
- "Bideo-deia eskatzen"
- "Ezin da konektatu bideo-deia"
- "Baztertu egin da bideo-deia egiteko eskaera"
- "Dei-erantzunetarako zenbakia:\n %1$s"
- "Larrialdi-dei bidez erantzuteko zenbakia:\n %1$s"
- "Deitzen"
- "Dei bat galdu duzu"
- "Dei batzuk galdu dituzu"
- "%s dei galdu dituzu"
- "Deitzaile honen dei bat galdu duzu: %s"
- "Deia abian da"
- "Laneko dei bat abian da"
- "Wi-Fi bidezko deia abian da"
- "Wi-Fi bidezko laneko dei bat abian da"
- "Zain"
- "Dei bat jaso duzu"
- "Laneko dei bat jaso duzu"
- "Wi-Fi bidezko dei bat jaso duzu"
- "Wi-Fi bidezko laneko dei bat jaso duzu"
- "Bideo-dei bat jaso duzu"
- "Ustezko spam-deia jaso duzu"
- "Bideo-dei bat egiteko eskaera bat jaso duzu"
- "Ahots-mezu berria"
- "Ahots-mezu berriak (%d)"
- "Markatu %s"
- "Erantzungailuaren zenbakia ezezaguna da"
- "Ez dago zerbitzurik"
- "Hautatutako sarea (%s) ez dago erabilgarri"
- "Erantzun"
- "Amaitu deia"
- "Bideo-deia"
- "Ahots-deia"
- "Onartu"
- "Baztertu"
- "Itzuli deia"
- "Bidali SMSa"
- "Dei bat abian da beste gailu batean"
- "Transferitu deia"
- "Deitzeko, desaktibatu hegaldi modua."
- "Ez dago sarean erregistratuta."
- "Sare mugikorra ez dago erabilgarri."
- "Deitzeko, idatzi balio duen zenbaki bat."
- "Ezin da deitu."
- "MMI sekuentzia hasten…"
- "Ez da onartzen zerbitzua."
- "Ezin aldatu beste dei batera."
- "Ezin da bereizi deia."
- "Ezin da transferitu."
- "Ezin da egin konferentzia-deia."
- "Ezin da baztertu deia."
- "Ezin dira amaitu deiak."
- "SIP deia"
- "Larrialdi-deia"
- "Irratia pizten…"
- "Ez dago zerbitzurik. Berriro saiatzen…"
- "Ezin da deitu. %s ez da larrialdietarako zenbakia."
- "Ezin da deitu. Markatu larrialdietarako zenbakia."
- "Erabili teklatua markatzeko"
- "Utzi deia zain"
- "Berrekin deiari"
- "Amaitu deia"
- "Erakutsi markagailua"
- "Ezkutatu markagailua"
- "Desaktibatu audioa"
- "Aktibatu audioa"
- "Gehitu deia"
- "Bateratu deiak"
- "Aldatu"
- "Kudeatu deiak"
- "Kudeatu konferentzia-deia"
- "Konferentzia-deia"
- "Kudeatu"
- "Audioa"
- "Bideo-deia"
- "Aldatu ahots-deira"
- "Aldatu kamera"
- "Aktibatu kamera"
- "Desaktibatu kamera"
- "Aukera gehiago"
- "Abian da erreproduzigailua"
- "Gelditu da erreproduzigailua"
- "Ez dago prest kamera"
- "Prest dago kamera"
- "Dei-saioko gertaera ezezaguna"
- "Zerbitzua"
- "Konfigurazioa"
- "<Ezarri gabe>"
- "Deien beste ezarpen batzuk"
- "%s bidez deitzen"
- "%s bidez jasotzen"
- "kontaktuaren argazkia"
- "bihurtu pribatu"
- "hautatu kontaktua"
- "Idatzi zeure erantzuna…"
- "Utzi"
- "Bidali"
- "Erantzun"
- "Bidali SMS mezua"
- "Baztertu"
- "Erantzun bideo-dei moduan"
- "Erantzun audio-dei moduan"
- "Onartu bideo-deia egiteko eskaera"
- "Baztertu bideo-deia egiteko eskaera"
- "Onartu bideoa transmititzeko eskaera"
- "Baztertu bideoa transmititzeko eskaera"
- "Onartu bideo-deia jasotzeko eskaera"
- "Baztertu bideo-deia jasotzeko eskaera"
- "Lerratu gora hau egiteko: %s."
- "Lerratu ezkerrera hau egiteko: %s."
- "Lerratu eskuinera hau egiteko: %s."
- "Lerratu behera hau egiteko: %s."
- "Dardara"
- "Dardara"
- "Soinua"
- "Soinu lehenetsia (%1$s)"
- "Telefonoaren tonua"
- "Egin dar-dar tonuak jotzean"
- "Tonua eta dardara"
- "Kudeatu konferentzia-deia"
- "Larrialdietarako zenbakia"
- "Profileko argazkia"
- "Desaktibatuta dago kamera"
- "%s zenbakitik"
- "Bidali da oharra"
- "Azken mezuak"
- "Enpresaren informazioa"
- "Hemendik %.1f miliara"
- "Hemendik %.1f km-ra"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "%s da biharko irekitze-ordua"
- "%s da gaurko irekitze-ordua"
- "%s da ixte-ordua"
- "%s da gaurko itxiera-ordua"
- "Irekita dago"
- "Itxita dago"
- "Ustezko spam-deitzailea"
- "Deiaren amaiera: %1$s"
- "Zenbaki honek deitu dizun lehen aldia izan da."
- "Spam-igorle baten deia izan dela susmatu dugu."
- "Salatu spama dela"
- "Gehitu kontaktua"
- "Ez da spama"
-
diff --git a/InCallUI/res/values-fa/strings.xml b/InCallUI/res/values-fa/strings.xml
deleted file mode 100644
index f96b8956a170396affdada914b9a25faeac53c75..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-fa/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "تلفن"
- "در انتظار"
- "نامشخص"
- "شماره خصوصی"
- "تلفن عمومی"
- "تماس کنفرانسی"
- "تماس قطع شد"
- "بلندگو"
- "گوشی"
- "هدست سیمی"
- "بلوتوث"
- "شمارههای بعدی ارسال شود؟\n"
- "تونهای ارسالی\n"
- "ارسال"
- "بله"
- "نه"
- "جایگزینی نویسه عمومی با"
- "تماس کنفرانسی %s"
- "شماره پست صوتی"
- "شمارهگیری"
- "درحال شمارهگیری مجدد"
- "تماس کنفرانسی"
- "تماس ورودی"
- "تماس کاری ورودی"
- "تماس پایان یافت"
- "در انتظار"
- "قطع تماس"
- "درحال تماس"
- "شماره من %s است"
- "درحال برقراری تماس ویدئویی"
- "تماس ویدئویی"
- "درحال درخواست تماس ویدئویی"
- "برقراری تماس ویدئویی ممکن نیست"
- "درخواست تماس ویدئویی رد شد"
- "شماره پاسخ تماس شما\n %1$s"
- "شماره پاسخ تماس اضطراری شما\n %1$s"
- "شمارهگیری"
- "تماس بیپاسخ"
- "تماس بیپاسخ"
- "%s تماس بیپاسخ"
- "تماس بیپاسخ از %s"
- "تماس درحال انجام"
- "تماس کاری درحال انجام"
- "تماس درحال انجام ازطریق Wi-Fi"
- "تماس کاری Wi-Fi درحال انجام"
- "در انتظار"
- "تماس ورودی"
- "تماس کاری ورودی"
- "تماس Wi-Fi ورودی"
- "تماس کاری Wi-Fi ورودی"
- "تماس ویدئویی ورودی"
- "تماس هرزنامه احتمالی ورودی"
- "درخواست تماس ویدئویی ورودی"
- "پست صوتی جدید"
- "پست صوتی جدید (%d)"
- "شمارهگیری %s"
- "شماره پست صوتی ناشناس"
- "بدون سرویس"
- "شبکه انتخابی (%s) قابل دسترس نیست"
- "پاسخ"
- "پایان تماس"
- "ویدئو"
- "صدا"
- "پذیرفتن"
- "نپذیرفتن"
- "پاسخ تماس"
- "پیام"
- "تماس در حال انجام در دستگاهی دیگر"
- "انتقال تماس"
- "برای برقراری تماس، ابتدا حالت هواپیما را خاموش کنید."
- "در شبکه ثبت نشده است."
- "شبکه تلفن همراه در دسترس نیست."
- "برای برقراری تماس، شماره معتبری وارد کنید."
- "تماس ممکن نیست."
- "شروع ترتیب MMI…"
- "سرویس پشتیبانی نمیشود."
- "جابهجایی بین تماسها ممکن نیست."
- "جدا کردن تماس ممکن نیست."
- "انتقال ممکن نیست."
- "تماس کنفرانسی ممکن نیست."
- "رد کردن تماس ممکن نیست."
- "آزاد کردن تماس(ها) ممکن نیست."
- "تماس SIP"
- "تماس اضطراری"
- "درحال روشن کردن رادیو…"
- "سرویسی در دسترس نیست. درحال تلاش مجدد…"
- "تماس ممکن نیست. %s شماره اضطراری نیست."
- "تماس ممکن نیست. فقط شماره اضطراری."
- "استفاده از صفحهکلید برای شمارهگیری"
- "در انتظار گذاشتن تماس"
- "ازسرگیری تماس"
- "پایان تماس"
- "نمایش صفحه شمارهگیری"
- "پنهان کردن صفحه شمارهگیری"
- "بیصدا کردن"
- "لغو نادیده گرفتن"
- "افزودن تماس"
- "ادغام تماسها"
- "تعویض"
- "مدیریت تماسها"
- "مدیریت تماس کنفرانسی"
- "تماس کنفرانسی"
- "مدیریت"
- "صوتی"
- "تماس ویدئویی"
- "تغییر به تماس صوتی"
- "تعویض دوربین"
- "روشن کردن دوربین"
- "خاموش کردن دوربین"
- "گزینههای بیشتر"
- "پخشکننده راهاندازی شد"
- "پخشکننده متوقف شد"
- "دوربین آماده نیست"
- "دوربین آماده است"
- "رویداد جلسه تماس ناشناس"
- "سرویس"
- "راهاندازی"
- "<تنظیم نشده>"
- "سایر تنظیمات تماس"
- "تماس با %s"
- "تماسهای ورودی ازطریق %s"
- "عکس مخاطب"
- "رفتن به حالت خصوصی"
- "انتخاب مخاطب"
- "پیام خودتان را بنویسید..."
- "لغو"
- "ارسال"
- "پاسخ"
- "ارسال پیامک"
- "رد کردن"
- "پاسخ بهصورت تماس ویدئویی"
- "پاسخ بهصورت تماس صوتی"
- "پذیرفتن درخواست تماس ویدئویی"
- "نپذیرفتن درخواست تماس ویدئویی"
- "پذیرفتن درخواست مخابره ویدئویی"
- "نپذیرفتن درخواست مخابره ویدئویی"
- "پذیرفتن درخواست دریافت ویدئویی"
- "نپذیرفتن درخواست دریافت ویدئویی"
- "برای %s به بالا بلغزانید."
- "برای %s به چپ بلغزانید."
- "برای %s به راست بلغزانید."
- "برای %s به پایین بلغزانید."
- "لرزش"
- "لرزش"
- "صدا"
- "صدای پیشفرض (%1$s)"
- "آهنگ زنگ تلفن"
- "لرزش هنگام زنگ زدن"
- "آهنگ زنگ و لرزش"
- "مدیریت تماس کنفرانسی"
- "شماره اضطراری"
- "عکس نمایه"
- "دوربین خاموش"
- "ازطریق %s"
- "یادداشت ارسال شد"
- "پیامهای جدید"
- "اطلاعات کسب و کار"
- "%.1f مایل فاصله"
- "%.1f کیلومتر فاصله"
- "%1$s، %2$s"
- "%1$s تا %2$s"
- "%1$s، %2$s"
- "فردا ساعت %s باز میشود"
- "امروز ساعت %s باز میشود"
- "ساعت %s بسته میشود"
- "امروز ساعت %s بسته شد"
- "اکنون باز است"
- "اکنون بسته است"
- "تماسگیرنده هرزنامه احتمالی"
- "تماس به پایان رسید %1$s"
- "این اولین بار است که این شماره با شما تماس گرفته است."
- "ما به این تماس شک کردیم و احساس کردیم که ممکن است کلاهبردار باشد."
- "مسدود کردن/گزارش دادن هرزنامه"
- "افزودن مخاطب"
- "هرزنامه نیست"
-
diff --git a/InCallUI/res/values-fi/strings.xml b/InCallUI/res/values-fi/strings.xml
deleted file mode 100644
index 7553e7c251acdd4d4998601b63ae3ba310d17f0f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-fi/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Puhelin"
- "Pidossa"
- "Tuntematon"
- "Yksityinen numero"
- "Maksupuhelin"
- "Puhelinneuvottelu"
- "Puhelu katkaistiin."
- "Kaiutin"
- "Puhelimen kaiutin"
- "Kuulokemikrofoni"
- "Bluetooth"
- "Lähetetäänkö seuraavat äänet?\n"
- "Lähetetään ääniä\n"
- "Lähetä"
- "Kyllä"
- "Ei"
- "Muuta jokerimerkiksi"
- "Puhelinneuvottelu %s"
- "Puhelinvastaajan numero"
- "Soitetaan"
- "Soitetaan uudelleen"
- "Puhelinneuvottelu"
- "Saapuva puhelu"
- "Saapuva työpuhelu"
- "Puhelu päättyi"
- "Pidossa"
- "Katkaistaan"
- "Puhelu käynnissä"
- "Numeroni on %s"
- "Avataan videoyhteys"
- "Videopuhelu"
- "Videota pyydetään"
- "Videopuhelua ei voi soittaa"
- "Videopyyntö hylättiin"
- "Takaisinsoittonumero:\n %1$s"
- "Hätäpuhelujen takaisinsoittonumero:\n %1$s"
- "Soitetaan"
- "Vastaamaton puhelu"
- "Vastaamattomia puheluita"
- "%s vastaamatonta puhelua"
- "Vastaamaton puhelu: %s"
- "Käynnissä oleva puhelu"
- "Käynnissä oleva työpuhelu"
- "Käynnissä oleva Wi-Fi-puhelu"
- "Käynnissä oleva Wi-Fi-työpuhelu"
- "Pidossa"
- "Saapuva puhelu"
- "Saapuva työpuhelu"
- "Saapuva Wi-Fi-puhelu"
- "Saapuva Wi-Fi-työpuhelu"
- "Saapuva videopuhelu"
- "Tämä puhelu saattaa olla häirikköpuhelu."
- "Saapuva videopyyntö"
- "Uusi vastaajaviesti"
- "Uusia vastaajaviestejä (%d)"
- "Soita: %s"
- "Puhelinvastaajan numero on tuntematon."
- "Ei yhteyttä"
- "Valittu verkko (%s) ei ole käytettävissä."
- "Vastaa"
- "Katkaise"
- "Videopuhelu"
- "Äänipuhelu"
- "Hyväksy"
- "Hylkää"
- "Soita"
- "Viesti"
- "Puhelu on kesken toisella laitteella."
- "Siirrä puhelu"
- "Poista lentokonetila käytöstä ennen puhelun soittamista."
- "Ei rekisteröity verkkoon"
- "Matkapuhelinverkko ei ole käytettävissä."
- "Soita antamalla kelvollinen numero."
- "Puhelua ei voi soittaa."
- "Aloitetaan MMI-koodisekvenssiä…"
- "Yhteyttä ei tueta."
- "Puhelua ei voi vaihtaa."
- "Puhelua ei voi erottaa."
- "Puhelua ei voi siirtää."
- "Puheluja ei voi yhdistää."
- "Puhelua ei voi hylätä."
- "Puheluja ei voi katkaista."
- "SIP-puhelu"
- "Hätäpuhelu"
- "Käynnistetään radiota…"
- "Ei yhteyttä. Yritetään uudelleen…"
- "Puhelua ei voi soittaa. %s ei ole hätänumero."
- "Puhelua ei voi soittaa. Valitse hätänumero."
- "Valitse numero näppäimistöllä."
- "Aseta puhelu pitoon"
- "Jatka puhelua"
- "Lopeta puhelu"
- "Avaa näppäimistö"
- "Piilota näppäimistö"
- "Mykistä"
- "Poista mykistys"
- "Lisää puhelu"
- "Yhdistä puhelut"
- "Vaihda"
- "Hallinnoi puheluja"
- "Hallinnoi puhelinneuvottelua"
- "Puhelinneuvottelu"
- "Hallinnoi"
- "Ääni"
- "Video"
- "Muuta äänipuheluksi"
- "Vaihda kameraa"
- "Käynnistä kamera"
- "Sammuta kamera"
- "Lisäasetukset"
- "Soitin käynnistettiin."
- "Soitin pysäytettiin."
- "Kamera ei ole valmis."
- "Kamera on valmis."
- "Tuntematon puheluistunnon tapahtuma"
- "Palveluntarjoaja"
- "Määritys"
- "<Ei määritetty>"
- "Muut puheluasetukset"
- "Käytetään operaattoria %s"
- "Saapuva puhelu (%s)"
- "Yhteystiedon kuva"
- "Muuta yksityiseksi."
- "Valitse yhteystieto."
- "Kirjoita oma…"
- "Peruuta"
- "Lähetä"
- "Vastaa."
- "Lähetä tekstiviesti."
- "Hylkää."
- "Vastaa ja aloita videopuhelu."
- "Vastaa ja aloita äänipuhelu."
- "Hyväksy videopyyntö."
- "Hylkää videopyyntö."
- "Hyväksy videon lähetyspyyntö."
- "Hylkää videon lähetyspyyntö."
- "Hyväksy videon vastaanottopyyntö."
- "Hylkää videon vastaanottopyyntö."
- "Valitse %s liu\'uttamalla ylös."
- "Valitse %s liu\'uttamalla vasemmalle."
- "Valitse %s liu\'uttamalla oikealle."
- "Valitse %s liu\'uttamalla alas."
- "Värinä"
- "Värinä"
- "Ääni"
- "Oletusääni (%1$s)"
- "Puhelimen soittoääni"
- "Käytä värinää, kun puhelin soi"
- "Soittoääni ja värinä"
- "Hallinnoi puhelinneuvottelua"
- "Hätänumero"
- "Profiilikuva"
- "Kamera on pois käytöstä."
- "nron %s kautta"
- "Muistiinpano lähetettiin."
- "Viimeisimmät viestit"
- "Yrityksen tiedot"
- "Etäisyys: %.1f mailia"
- "Etäisyys: %.1f kilometriä"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Avataan huomenna kello %s"
- "Avataan tänään kello %s"
- "Suljetaan tänään kello %s"
- "Suljettiin tänään kello %s"
- "Avoinna nyt"
- "Suljettu nyt"
- "Häirikkösoittaja"
- "Puhelu loppui %1$s"
- "Tämä oli ensimmäinen kerta, kun tästä numerosta soitettiin sinulle."
- "Epäilemme, että tämä puhelu tuli häirikkösoittajalta."
- "Estä / ilmoita"
- "Lisää yhteystieto"
- "Ei häirikkösoittaja"
-
diff --git a/InCallUI/res/values-fr-rCA/strings.xml b/InCallUI/res/values-fr-rCA/strings.xml
deleted file mode 100644
index 2980646e884eeb72851649526a1c05b569f7e94f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-fr-rCA/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Téléphone"
- "En attente"
- "Inconnue"
- "Numéro privé"
- "Cabine téléphonique"
- "Conférence téléphonique"
- "L\'appel a été interrompu"
- "Haut-parleur"
- "Écouteur du combiné"
- "Écouteurs à fil"
- "Bluetooth"
- "Envoyer les tonalités suivantes?\n"
- "Envoi des tonalités\n"
- "Envoyer"
- "Oui"
- "Non"
- "Remplacer le caractère générique par"
- "Conférence téléphonique %s"
- "Numéro de messagerie vocale"
- "Composition..."
- "Recomposition en cours..."
- "Conférence téléphonique"
- "Appel entrant"
- "Appel entrant - travail"
- "Appel terminé"
- "En attente"
- "Fin de l\'appel"
- "En cours d\'appel"
- "Mon numéro est le %s"
- "Connexion de la vidéo en cours…"
- "Appel vidéo"
- "Demande de vidéo en cours"
- "Impossible de connecter l\'appel vidéo"
- "Demande vidéo refusée"
- "Votre numéro de rappel :\n %1$s"
- "Votre numéro de rappel d\'urgence :\n %1$s"
- "Composition en cours..."
- "Appel manqué"
- "Appels manqués"
- "%s appels manqués"
- "Appel manqué de %s"
- "Appel en cours"
- "Appel en cours - travail"
- "Appel Wi-Fi en cours"
- "Appel Wi-Fi en cours - travail"
- "En attente"
- "Appel entrant"
- "Appel entrant - travail"
- "Appel Wi-Fi entrant"
- "Appel Wi-Fi entrant - travail"
- "Appel vidéo entrant"
- "L\'appel entrant est suspect"
- "Demande de vidéo reçue"
- "Nouveau message vocal"
- "Nouveaux messages vocaux (%d)"
- "Composer le %s"
- "Numéro de messagerie vocale inconnu"
- "Aucun service"
- "Réseau sélectionné (%s) non disponible"
- "Répondre"
- "Raccrocher"
- "Vidéo"
- "Voix"
- "Accepter"
- "Fermer"
- "Rappeler"
- "Message"
- "Appel en cours sur un autre appareil"
- "Transférer l\'appel"
- "Pour faire un appel, d\'abord désactiver le mode Avion."
- "Non enregistré sur le réseau."
- "Réseau cellulaire non disponible."
- "Pour faire un appel, entrez un numéro valide."
- "Impossible d\'appeler."
- "Lancement de la séquence IHM en cours…"
- "Service non pris en charge."
- "Impossible de faire des appels."
- "Impossible de séparer les appels."
- "Impossible de transférer."
- "Impossible de créer la conférence."
- "Impossible de refuser l\'appel."
- "Impossible de libérer l\'appel ou les appels."
- "Appel SIP"
- "Appel d\'urgence"
- "Activation du signal radio…"
- "Aucun service. Nouvel essai en cours..."
- "Appel impossible. %s n\'est pas un numéro d\'urgence."
- "Appel impossible. Composez un numéro d\'urgence."
- "Utilisez le clavier pour composer un numéro"
- "Mettre l\'appel en attente"
- "Reprendre l\'appel"
- "Mettre fin à l\'appel"
- "Afficher le clavier numérique"
- "Masquer le clavier numérique"
- "Désactiver le son"
- "Réactiver le son"
- "Ajouter un appel"
- "Fusionner les appels"
- "Permuter"
- "Gérer les appels"
- "Gérer la conférence"
- "Conférence téléphonique"
- "Gérer"
- "Audio"
- "Appel vidéo"
- "Passer à un appel vocal"
- "Changer d\'appareil photo"
- "Activer la caméra"
- "Désactiver la caméra"
- "Plus d\'options"
- "Le lecteur a démarré"
- "Le lecteur a arrêté"
- "L\'appareil photo n\'est pas prêt"
- "L\'appareil photo est prêt"
- "Événement inconnu de séance d\'appel"
- "Service"
- "Configuration"
- "<Non défini>"
- "Autres paramètres d\'appel"
- "Appel par %s"
- "Appel entrant par %s"
- "photo du contact"
- "mode privé"
- "sélectionner un contact"
- "Réponse personnalisée..."
- "Annuler"
- "Envoyer"
- "Répondre"
- "Envoyer un texto"
- "Refuser"
- "Répondre comme appel vidéo"
- "Répondre comme appel audio"
- "Accepter la demande vidéo"
- "Refuser la demande vidéo"
- "Accepter la demande de transmission vidéo"
- "Refuser la demande de transmission vidéo"
- "Accepter la demande de réception vidéo"
- "Refuser la demande de réception vidéo"
- "Faites glisser votre doigt vers le haut pour %s."
- "Faites glisser votre doigt vers la gauche pour %s."
- "Faites glisser votre doigt vers la droite pour %s."
- "Faire glisser le doigt vers le bas : %s"
- "Vibration"
- "Vibration"
- "Son"
- "Son par défaut (%1$s)"
- "Sonnerie du téléphone"
- "Vibrer lorsque téléphone sonne"
- "Sonnerie et vibreur"
- "Gérer la conférence"
- "Numéro d\'urgence"
- "Photo de profil"
- "Appareil photo désactivé"
- "au moyen du %s"
- "Note envoyée"
- "Messages récents"
- "Renseignements sur l\'entreprise"
- "À %.1f mi"
- "À %.1f km"
- "%1$s, %2$s"
- "De %1$s à %2$s"
- "%1$s, %2$s"
- "Ouvre demain à %s"
- "Ouvre aujourd\'hui à %s"
- "Ferme à %s"
- "A fermé aujourd\'hui à %s"
- "Ouvert"
- "Fermé"
- "Appel suspect"
- "Appel terminé %1$s"
- "C\'est la première fois que ce numéro vous appelle."
- "Cet appel nous semblait suspect."
- "Sign. appel suspect"
- "Ajouter un contact"
- "N\'est pas suspect"
-
diff --git a/InCallUI/res/values-fr/strings.xml b/InCallUI/res/values-fr/strings.xml
deleted file mode 100644
index 521fedb64470893d2030a193fcf640f243c72ef3..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-fr/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Téléphone"
- "En attente"
- "Inconnu"
- "Numéro privé"
- "Cabine téléphonique"
- "Conférence téléphonique"
- "Appel interrompu"
- "Haut-parleur"
- "Écouteur du combiné"
- "Casque filaire"
- "Bluetooth"
- "Envoyer les tonalités suivantes ?\n"
- "Envoi des tonalités…\n"
- "Envoyer"
- "Oui"
- "Non"
- "Remplacer le caractère générique par"
- "Conférence téléphonique à %s"
- "N° de la messagerie vocale"
- "Appel…"
- "Rappel…"
- "Conférence téléphonique"
- "Appel entrant"
- "Appel profession. entrant"
- "Appel terminé"
- "En attente"
- "Fin de l\'appel…"
- "Appel en cours"
- "Mon numéro est le %s"
- "Connexion de la vidéo…"
- "Appel vidéo"
- "Demande de vidéo…"
- "Impossible d\'établir la connexion de l\'appel vidéo."
- "Demande d\'appel vidéo refusée"
- "Votre numéro de rappel\n %1$s"
- "Votre numéro de rappel d\'urgence\n %1$s"
- "Appel…"
- "Appel manqué"
- "Appels manqués"
- "%s appels manqués"
- "Appel manqué de %s"
- "Appel en cours"
- "Appel professionnel en cours"
- "Appel Wi-Fi en cours"
- "Appel Wi-Fi professionnel en cours"
- "En attente"
- "Appel entrant"
- "Appel professionnel entrant"
- "Appel Wi-Fi entrant"
- "Appel Wi-Fi professionnel entrant"
- "Appel vidéo entrant"
- "Appel entrant indésirable suspecté"
- "Demande de vidéo reçue"
- "Nouveau message vocal"
- "Nouveaux messages vocaux (%d)"
- "Composer le %s"
- "Numéro de messagerie vocale inconnu"
- "Aucun service"
- "Réseau sélectionné (%s) non disponible"
- "Répondre"
- "Raccrocher"
- "Vidéo"
- "Appel vocal"
- "Accepter"
- "Fermer"
- "Rappeler"
- "Envoyer SMS"
- "Appel en cours sur un autre appareil"
- "Transférer l\'appel"
- "Veuillez désactiver le mode Avion avant de passer un appel."
- "Non enregistré sur le réseau."
- "Réseau mobile indisponible."
- "Pour émettre un appel, veuillez saisir un numéro valide."
- "Impossible d\'émettre l\'appel."
- "Lancement de la séquence IHM…"
- "Service non compatible."
- "Impossible de changer d\'appel."
- "Impossible d\'isoler l\'appel."
- "Transfert impossible."
- "Impossible de lancer une conférence téléphonique."
- "Impossible de refuser l\'appel."
- "Impossible de lancer les appels."
- "Appel SIP"
- "Appel d\'urgence"
- "Activation du signal radio…"
- "Aucun service disponible. Nouvelle tentative…"
- "Impossible d\'émettre l\'appel. %s n\'est pas un numéro d\'urgence."
- "Impossible d\'émettre l\'appel. Veuillez composer un numéro d\'urgence."
- "Utilisez le clavier pour composer un numéro."
- "Mettre l\'appel en attente"
- "Reprendre l\'appel"
- "Mettre fin à l\'appel"
- "Afficher le clavier"
- "Masquer le clavier"
- "Couper le son"
- "Réactiver le son"
- "Ajouter un appel"
- "Fusionner les appels"
- "Permuter"
- "Gérer les appels"
- "Gérer conférence téléphonique"
- "Conférence téléphonique"
- "Gérer"
- "Audio"
- "Appel vidéo"
- "Passer à un appel vocal"
- "Changer de caméra"
- "Activer la caméra"
- "Désactiver la caméra"
- "Plus d\'options"
- "Le lecteur a démarré."
- "Le lecteur s\'est arrêté."
- "La caméra n\'est pas prête"
- "La caméra est prête"
- "Événement de session d\'appel inconnu"
- "Service"
- "Configuration"
- "<Non défini>"
- "Autres paramètres d\'appel"
- "Appel via %s"
- "Appel entrant via %s"
- "photo du contact"
- "mode privé"
- "sélectionner un contact"
- "Réponse personnalisée…"
- "Annuler"
- "Envoyer"
- "Répondre"
- "Envoyer un SMS"
- "Refuser"
- "Répondre via un appel vidéo"
- "Répondre via un appel audio"
- "Accepter la demande d\'appel vidéo"
- "Refuser la demande d\'appel vidéo"
- "Accepter la demande de transmission d\'appel vidéo"
- "Refuser la demande de transmission d\'appel vidéo"
- "Accepter la demande de réception d\'appel vidéo"
- "Refuser la demande de réception d\'appel vidéo"
- "Faites glisser vers le haut pour %s"
- "Faites glisser vers la gauche pour %s."
- "Faites glisser vers la droite pour %s."
- "Faites glisser vers le bas pour %s."
- "Vibreur"
- "Vibreur"
- "Sonnerie"
- "Sonnerie par défaut (%1$s)"
- "Sonnerie du téléphone"
- "Vibreur lorsque le tél. sonne"
- "Sonnerie et vibreur"
- "Gérer la conférence téléphonique"
- "Numéro d\'urgence"
- "Photo du profil"
- "Caméra désactivée"
- "via le %s"
- "La note a bien été envoyée."
- "Messages récents"
- "Informations sur l\'établissement"
- "À %.1f mi"
- "À %.1f km"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Ouvre demain à %s"
- "Ouvre aujourd\'hui à %s"
- "Ferme à %s"
- "Fermé aujourd\'hui à %s"
- "Ouvert"
- "Fermé"
- "Appel indésirable suspecté"
- "Appel terminé %1$s"
- "C\'est la première fois que vous recevez un appel de ce numéro."
- "Nous suspectons cet appel de provenir d\'un spammeur."
- "Bloquer/Signaler spam"
- "Ajouter un contact"
- "Numéro fiable"
-
diff --git a/InCallUI/res/values-gl/strings.xml b/InCallUI/res/values-gl/strings.xml
deleted file mode 100644
index 8968946e634123a2c1f20494fcea147409ac8dbc..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-gl/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Teléfono"
- "En espera"
- "Descoñecido"
- "Número privado"
- "Teléfono público"
- "Conferencia telefónica"
- "Chamada interrompida"
- "Altofalante"
- "Auricular do teléfono"
- "Auriculares con cable"
- "Bluetooth"
- "Queres enviar os seguintes tons?\n"
- "Enviando tons\n"
- "Enviar"
- "Si"
- "Non"
- "Substituír carácter comodín por"
- "Conferencia telefónica ás %s"
- "Número de correo de voz"
- "Marcando"
- "Marcando de novo"
- "Conferencia telefónica"
- "Chamada entrante"
- "Chamada traballo entrante"
- "Chamada finalizada"
- "En espera"
- "Desconectando"
- "Chamada entrante"
- "O meu número é o %s"
- "Conectando vídeo"
- "Videochamada"
- "Solicitando vídeo"
- "Non se pode conectar a videochamada"
- "Rexeitouse a solicitude de vídeo"
- "O teu número de devolución de chamada\n %1$s"
- "O teu número de devolución de chamada de emerxencia\n %1$s"
- "Marcando"
- "Chamada perdida"
- "Chamadas perdidas"
- "%s chamadas perdidas"
- "Chamada perdida de %s"
- "Chamada en curso"
- "Chamada de traballo saínte"
- "Chamada por wifi saínte"
- "Chamada por wifi de traballo saínte"
- "En espera"
- "Chamada entrante"
- "Chamada de traballo entrante"
- "Chamada por wifi entrante"
- "Chamada wifi de traballo entrante"
- "Videochamada entrante"
- "Chamada entrante sospeitosa de spam"
- "Solicitude de vídeo entrante"
- "Correo de voz novo"
- "Correo de voz novo (%d)"
- "Marcar o %s"
- "Número de correo de voz descoñecido"
- "Sen servizo"
- "A rede seleccionada (%s) non está dispoñible"
- "Responder"
- "Colgar"
- "Vídeo"
- "Voz"
- "Aceptar"
- "Ignorar"
- "Dev. chamada"
- "Mensaxe"
- "Chamada en curso noutro dispositivo"
- "Transferir chamada"
- "Para realizar unha chamada, primeiro desactiva o modo avión."
- "Sen rexistro na rede."
- "Rede móbil non dispoñible."
- "Para realizar unha chamada, introduce un número válido."
- "Non se pode realizar a chamada."
- "Iniciando secuencia MMI..."
- "Servizo non compatible."
- "Non se poden cambiar as chamadas."
- "Non se pode separar a chamada."
- "Non se pode transferir."
- "Non se pode realizar a conferencia."
- "Non se pode rexeitar a chamada."
- "Non se poden desconectar as chamadas."
- "Chamada SIP"
- "Chamada de emerxencia"
- "Activando radio..."
- "Sen servizo. Tentándoo de novo…"
- "Non se pode realizar a chamada. %s non é un número de emerxencia."
- "Non se pode realizar a chamada. Marca un número de emerxencia."
- "Utiliza o teclado para marcar"
- "Poñer a chamada en espera"
- "Retomar chamada"
- "Finalizar chamada"
- "Mostrar teclado de marcación"
- "Ocultar teclado de marcación"
- "Silenciar"
- "Activar o son"
- "Engadir chamada"
- "Combinar chamadas"
- "Cambiar"
- "Xestionar chamadas"
- "Xestionar confer. telefónica"
- "Conferencia telefónica"
- "Xestionar"
- "Audio"
- "Videocham."
- "Cambiar para chamada de voz"
- "Cambiar cámara"
- "Acender cámara"
- "Apagar cámara"
- "Máis opcións"
- "Iniciouse o reprodutor"
- "Detívose o reprodutor"
- "A cámara non está preparada"
- "A cámara está preparada"
- "Evento de sesión de chamada descoñecido"
- "Servizo"
- "Configuración"
- "<Sen configurar>"
- "Outras configuracións de chamada"
- "Chamando a través de %s"
- "Chamadas entrantes a través de %s"
- "foto do contacto"
- "activar o modo privado"
- "seleccionar contacto"
- "Escribe a túa propia..."
- "Cancelar"
- "Enviar"
- "Responder"
- "Enviar SMS"
- "Rexeitar"
- "Responde como videochamada"
- "Responde como chamada de audio"
- "Acepta a solicitude de vídeo"
- "Rexeita a solicitude de vídeo"
- "Acepta a solicitude de transmisión de vídeo"
- "Rexeita a solicitude de transmisión de vídeo"
- "Acepta a solicitude de recepción de vídeo"
- "Rexeita a solicitude de recepción de vídeo"
- "Pasa o dedo cara a arriba para %s."
- "Pasa o dedo cara a esquerda para %s."
- "Pasa o dedo cara a dereita para %s."
- "Pasa o dedo cara a abaixo para %s."
- "Vibrar"
- "Vibrar"
- "Son"
- "Son predeterminado (%1$s)"
- "Ton de chamada do teléfono"
- "Vibrar ao soar"
- "Ton de chamada e vibración"
- "Xestionar conferencia telefónica"
- "Número de emerxencia"
- "Foto do perfil"
- "A cámara está desactivada"
- "a través do %s"
- "Enviouse a nota"
- "Mensaxes recentes"
- "Información da empresa"
- "A %.1f mi de distancia"
- "A %.1f km de distancia"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Abre mañá ás %s"
- "Abre hoxe ás %s"
- "Pecha ás %s"
- "Pechou hoxe ás %s"
- "Aberto agora"
- "Pechado agora"
- "Chamada sospeitosa"
- "Finalizouse a chamada %1$s"
- "É a primeira vez que te chama este número."
- "Sospeitamos que esta chamada era un xerador de spam."
- "Bloquear/marcar spam"
- "Engadir contacto"
- "Non é spam"
-
diff --git a/InCallUI/res/values-gu/strings.xml b/InCallUI/res/values-gu/strings.xml
deleted file mode 100644
index 017ccb691f7cee6cd401208ed218427a68a337cd..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-gu/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ફોન"
- "હોલ્ડ પર"
- "અજાણ્યો"
- "ખાનગી નંબર"
- "પેફોન"
- "કોન્ફરન્સ કૉલ"
- "કૉલ કપાઇ ગયો"
- "સ્પીકર"
- "હેન્ડસેટ ઇયરપીસ"
- "વાયર્ડ હેડસેટ"
- "Bluetooth"
- "નીચે આપેલ ટોન્સ મોકલીએ?\n"
- "ટોન્સ મોકલી રહ્યાં છે\n"
- "મોકલો"
- "હા"
- "નહીં"
- "વાઇલ્ડ અક્ષરને આની સાથે બદલો"
- "કોન્ફરન્સ કૉલ %s"
- "વૉઇસમેઇલ નંબર"
- "ડાયલ કરી રહ્યાં છે"
- "ફરી ડાયલ કરી રહ્યાં છે"
- "કોન્ફરન્સ કૉલ"
- "ઇનકમિંગ કૉલ"
- "ઇનકમિંગ કાર્ય કૉલ"
- "કૉલ સમાપ્ત થયો"
- "હોલ્ડ પર"
- "સમાપ્ત કરી રહ્યાં છે"
- "કૉલમાં"
- "મારો નંબર %s છે"
- "વિડિઓ કનેક્ટ કરી રહ્યાં છે"
- "વિડિઓ કૉલ"
- "વિડિઓની વિનંતી કરી રહ્યાં છે"
- "વિડિઓ કૉલ કનેક્ટ કરી શકાતો નથી"
- "વિડિઓ વિનંતી નકારી"
- "તમારો કૉલબેક નંબર\n %1$s"
- "તમારો કટોકટીનો કૉલબેક નંબર\n %1$s"
- "ડાયલ કરી રહ્યાં છે"
- "છૂટેલો કૉલ"
- "છૂટેલા કૉલ્સ"
- "%s છૂટેલા કૉલ"
- "%s નો કૉલ ચૂકી ગયાં"
- "ચાલી રહેલ કૉલ"
- "ચાલી રહેલ કાર્ય કૉલ"
- "ચાલી રહેલ Wi-Fi કૉલ"
- "ચાલી રહેલ Wi-Fi કાર્ય કૉલ"
- "હોલ્ડ પર"
- "ઇનકમિંગ કૉલ"
- "ઇનકમિંગ કાર્ય કૉલ"
- "ઇનકમિંગ Wi-Fi કૉલ"
- "ઇનકમિંગ Wi-Fi કાર્ય કૉલ"
- "ઇનકમિંગ વિડિઓ કૉલ"
- "ઇનકમિંગ શંકાસ્પદ સ્પામ કૉલ"
- "ઇનકમિંગ વિડિઓ વિનંતી"
- "નવો વૉઇસમેઇલ"
- "નવો વૉઇસમેઇલ (%d)"
- "%s ડાયલ કરો"
- "વૉઇસમેઇલ નંબર અજાણ"
- "કોઈ સેવા નથી"
- "પસંદ કરેલ નેટવર્ક (%s) અનુપલબ્ધ"
- "જવાબ"
- "સમાપ્ત કરો"
- "વિડિઓ"
- "વૉઇસ"
- "સ્વીકારો"
- "છોડી દો"
- "કૉલ બૅક કરો"
- "સંદેશ"
- "અન્ય ઉપકરણ પર ચાલી રહેલ કૉલ"
- "કૉલ સ્થાનાંતરિત કરો"
- "કૉલ કરવા માટે, પહેલા એરપ્લેન મોડને બંધ કરો."
- "નેટવર્ક પર નોંધણી કરાયેલ નથી."
- "સેલ્યુલર નેટવર્ક ઉપલબ્ધ નથી."
- "કૉલ કરવા માટે, માન્ય નંબર દાખલ કરો."
- "કૉલ કરી શકાતો નથી."
- "MMI અનુક્રમ પ્રારંભ કરી રહ્યાં છે…"
- "સેવા સમર્થિત નથી."
- "કૉલ્સ સ્વિચ કરી શકાતાં નથી."
- "અલગ કૉલ કરી શકાતો નથી."
- "ટ્રાંસ્ફર કરી શકાતો નથી."
- "કોન્ફરન્સ કરી શકાતી નથી."
- "કૉલ નકારી શકાતો નથી."
- "કૉલ(કૉલ્સ) રિલીઝ કરી શકતાં નથી."
- "SIP કૉલ"
- "કટોકટીનો કૉલ"
- "રેડિઓ ચાલુ કરી રહ્યાં છે…"
- "કોઈ સેવા નથી. ફરી પ્રયાસ કરી રહ્યાં છે…"
- "કૉલ કરી શકાતો નથી. %s એ કટોકટીનો નંબર નથી."
- "કૉલ કરી શકાતો નથી. કટોકટીનો નંબર ડાયલ કરો."
- "ડાયલ કરવા માટે કીબોર્ડનો ઉપયોગ કરો"
- "કૉલ હોલ્ડ કરો"
- "કૉલ ફરી શરૂ કરો"
- "કૉલ સમાપ્ત કરો"
- "ડાયલપેડ બતાવો"
- "ડાયલપેડ છુપાવો"
- "મ્યૂટ કરો"
- "અનમ્યૂટ કરો"
- "કૉલ ઉમેરો"
- "કૉલ્સ મર્જ કરો"
- "સ્વેપ કરો"
- "કૉલ્સ સંચાલિત કરો"
- "કોન્ફરન્સ કૉલ સંચાલિત કરો"
- "કોન્ફરન્સ કૉલ"
- "સંચાલિત કરો"
- "ઑડિઓ"
- "વિડિઓ કૉલ"
- "વૉઇસ કૉલ પર બદલો"
- "કૅમેરા પર સ્વિચ કરો"
- "કૅમેરો ચાલુ કરો"
- "કૅમેરો બંધ કરો"
- "વધુ વિકલ્પો"
- "પ્લેયર પ્રારંભ કર્યું"
- "પ્લેયર બંધ કર્યું"
- "કૅમેરો તૈયાર નથી"
- "કૅમેરો તૈયાર"
- "અજાણી કૉલ સત્ર ઇવેન્ટ"
- "સેવા"
- "સેટઅપ"
- "<સેટ કરેલ નથી>"
- "અન્ય કૉલ સેટિંગ્સ"
- "%s મારફતે કૉલ કરે છે"
- "%s મારફતે ઇનકમિંગ"
- "સંપર્ક ફોટો"
- "ખાનગી થાઓ"
- "સંપર્ક પસંદ કરો"
- "તમારો પોતાનો લખો…"
- "રદ કરો"
- "મોકલો"
- "જવાબ"
- "SMS મોકલો"
- "નકારો"
- "વિડિઓ કૉલ તરીકે જવાબ આપો"
- "ઑડિઓ કૉલ તરીકે જવાબ આપો"
- "વિડિઓ વિનંતી સ્વીકારો"
- "વિડિઓ વિનંતી નકારો"
- "વિડિઓ ટ્રાંસ્મિટ વિનંતી સ્વીકારો"
- "વિડિઓ ટ્રાંસ્મિટ વિનંતી નકારો"
- "વિડિઓ પ્રાપ્તિ વિનંતી સ્વીકારો"
- "વિડિઓ પ્રાપ્તિ વિનંતી નકારો"
- "%s માટે ઉપર સ્લાઇડ કરો."
- "%s માટે ડાબે સ્લાઇડ કરો."
- "%s માટે જમણે સ્લાઇડ કરો."
- "%s માટે નીચે સ્લાઇડ કરો."
- "વાઇબ્રેટ"
- "વાઇબ્રેટ"
- "ધ્વનિ"
- "ડિફોલ્ટ ધ્વનિ (%1$s)"
- "ફોન રિંગટોન"
- "જ્યારે રિંગ કરે ત્યારે વાઇબ્રેટ કરો"
- "રિંગટોન અને વાઇબ્રેટ"
- "કોન્ફરન્સ કૉલ સંચાલિત કરો"
- "કટોકટીનો નંબર"
- "પ્રોફાઇલ ફોટો"
- "કૅમેરો બંધ"
- "%s મારફતે"
- "નોંધ મોકલી"
- "તાજેતરનાં સંદેશા"
- "વ્યવસાયની માહિતી"
- "%.1f માઇલ દૂર"
- "%.1f કિમી દૂર"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "આવતીકાલે %s વાગ્યે ખુલશે"
- "આજે %s વાગ્યે ખુલશે"
- "%s વાગ્યે બંધ થશે"
- "આજે %s વાગ્યે બંધ થયેલું"
- "હમણાં ખુલ્લું"
- "હમણાં બંધ છે"
- "શંકાસ્પદ સ્પામ કૉલર"
- "%1$s નો કૉલ સમાપ્ત થયો"
- "આ નંબરથી તમને પહેલી વાર કૉલ કરવામાં આવ્યો છે."
- "આ કૉલ કોઈ સ્પામર હોવાની અમને શંકા છે."
- "સ્પામની જાણ/અવરોધિત કરો"
- "સંપર્ક ઉમેરો"
- "સ્પામ નથી"
-
diff --git a/InCallUI/res/values-h400dp/dimens.xml b/InCallUI/res/values-h400dp/dimens.xml
deleted file mode 100644
index dda755a3ea8d49b5148a8f3560ea44dd9fa13be7..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-h400dp/dimens.xml
+++ /dev/null
@@ -1,31 +0,0 @@
-
-
-
-
-
- true
-
- 90dp
-
- 15dp
-
- -24dp
-
- 2dp
-
- 20dp
-
diff --git a/InCallUI/res/values-hi/strings.xml b/InCallUI/res/values-hi/strings.xml
deleted file mode 100644
index dee8f464d59b9611848841734e7f4059bb9ad815..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-hi/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "फ़ोन"
- "होल्ड पर"
- "अज्ञात"
- "निजी नंबर"
- "पे-फ़ोन"
- "कॉन्फ़्रेंस कॉल"
- "कॉल कट गया"
- "स्पीकर"
- "हैंडसेट इयरपीस"
- "वायर वाला हैडसेट"
- "ब्लूटूथ"
- "निम्न टोन भेजें?\n"
- "भेजने वाली टोन\n"
- "भेजें"
- "हां"
- "नहीं"
- "वाइल्ड वर्ण को इससे बदलें:"
- "कॉन्फ़्रेंस कॉल %s"
- "वॉइसमेल नबंर"
- "डायल किया जा रहा है"
- "पुन: डायल हो रहा है"
- "कॉन्फ़्रेंस कॉल"
- "इनकमिंग कॉल"
- "कार्यस्थल का इनकमिंग कॉल"
- "कॉल समाप्त"
- "होल्ड पर"
- "कॉल समाप्त हो रहा है"
- "कॉल में"
- "मेरा नंबर %s है"
- "वीडियो कनेक्ट हो रहा है"
- "वीडियो कॉल"
- "वीडियो का अनुरोध किया जा रहा है"
- "वीडियो कॉल कनेक्ट नहीं किया जा सकता"
- "वीडियो अनुरोध अस्वीकार किया गया"
- "आपका कॉलबैक नंबर\n %1$s"
- "आपका आपातकालीन कॉलबैक नंबर\n %1$s"
- "डायल किया जा रहा है"
- "छूटा कॉल"
- "छूटे कॉल"
- "%s छूटे कॉल"
- "%s के छूटे कॉल"
- "चल रहा कॉल"
- "कार्यस्थल का जारी कॉल"
- "चल रहा वाई-फ़ाई कॉल"
- "कार्यस्थल का जारी वाई-फ़ाई कॉल"
- "होल्ड पर"
- "इनकमिंग कॉल"
- "कार्यस्थल का इनकमिंग कॉल"
- "इनकमिंग वाई-फ़ाई कॉल"
- "कार्यस्थल का वाई-फ़ाई इनकमिंग कॉल"
- "इनकमिंग वीडियो कॉल"
- "संदिग्ध आवक स्पैम कॉल"
- "इनकमिंग वीडियो अनुरोध"
- "नया वॉइसमेल"
- "नया वॉइसमेल (%d)"
- "%s डायल करें"
- "वॉइसमेल नंबर अज्ञात"
- "कोई सेवा नहीं"
- "चयनित नेटवर्क (%s) अनुपलब्ध"
- "उत्तर दें"
- "समाप्त करें"
- "वीडियो"
- "ध्वनि"
- "स्वीकार करें"
- "ख़ारिज करें"
- "कॉल बैक करें"
- "संदेश"
- "दूसरे डिवाइस पर चल रहा कॉल"
- "कॉल स्थानान्तरित करें"
- "कॉल करने के लिए, पहले हवाई जहाज़ मोड बंद करें."
- "नेटवर्क पर पंजीकृत नहीं."
- "सेल्युलर नेटवर्क उपलब्ध नहीं."
- "कॉल करने के लिए, मान्य नंबर डालें."
- "कॉल नहीं किया जा सकता."
- "MMI अनुक्रम प्रारंभ हो रहा है…"
- "सेवा समर्थित नहीं है."
- "कॉल स्विच नहीं किए जा सकते."
- "कॉल अलग नहीं किया जा सकता."
- "स्थानान्तरित नहीं किया जा सकता."
- "कॉन्फ़्रेंस नहीं की जा सकती."
- "कॉल अस्वीकार नहीं किया जा सकता."
- "कॉल रिलीज़ नहीं किया जा सकता (किए जा सकते)."
- "SIP कॉल"
- "आपातकालीन कॉल"
- "रेडियो चालू कर रहा है..."
- "कोई सेवा नहीं. पुन: प्रयास किया जा रहा है…"
- "कॉल नहीं किया जा सकता. %s एक आपातकालीन नंबर नहीं है."
- "कॉल नहीं किया जा सकता. आपातकालीन नबर डायल करें."
- "डायल करने के लिए कीबोर्ड का उपयोग करें"
- "कॉल होल्ड करें"
- "कॉल फिर से शुरू करें"
- "कॉल समाप्त करें"
- "डायलपैड दिखाएं"
- "डायलपैड छिपाएं"
- "म्यूट करें"
- "अनम्यूट करें"
- "कॉल जोड़ें"
- "कॉल मर्ज करें"
- "स्वैप करें"
- "कॉल प्रबंधित करें"
- "कॉन्फ़्रेंस कॉल प्रबंधित करें"
- "कॉन्फ़्रेंस कॉल"
- "प्रबंधित करें"
- "ऑडियो"
- "वीडियो कॉल"
- "वॉइस कॉल में बदलें"
- "कैमरा स्विच करें"
- "कैमरा चालू करें"
- "कैमरा बंद करें"
- "अधिक विकल्प"
- "प्लेयर प्रारंभ हो गया"
- "प्लेयर रुक गया"
- "कैमरा तैयार नहीं है"
- "कैमरा तैयार है"
- "अज्ञात कॉल सत्र इवेंट"
- "सेवा"
- "सेटअप"
- "<सेट नहीं है>"
- "अन्य कॉल सेटिंग"
- "%s के माध्यम से कॉल किया जा रहा है"
- "%s की ओर से इनकमिंग"
- "संपर्क का फ़ोटो"
- "निजी हो जाएं"
- "संपर्क को चुनें"
- "अपना स्वयं का लिखें..."
- "अभी नहीं"
- "भेजें"
- "उत्तर दें"
- "SMS भेजें"
- "अस्वीकार करें"
- "वीडियो कॉल के रूप में उत्तर दें"
- "ऑडियो कॉल के रूप में उत्तर दें"
- "वीडियो अनुरोध स्वीकार करें"
- "वीडियो अनुरोध अस्वीकार करें"
- "वीडियो प्रसारण अनुरोध स्वीकार करें"
- "वीडियो प्रसारण अनुरोध अस्वीकार करें"
- "वीडियो प्राप्ति अनुरोध स्वीकार करें"
- "वीडियो प्राप्ति अनुरोध अस्वीकार करें"
- "%s करने के लिए ऊपर स्लाइड करें."
- "%s करने के लिए बाएं स्लाइड करें."
- "%s करने के लिए दाएं स्लाइड करें."
- "%s करने के लिए नीचे स्लाइड करें."
- "कंपन"
- "कंपन"
- "ध्वनि"
- "डिफ़ॉल्ट ध्वनि (%1$s)"
- "फ़ोन रिंगटोन"
- "रिंग आने पर कंपन करें"
- "रिंगटोन और कंपन"
- "कॉन्फ़्रेंस कॉल प्रबंधित करें"
- "आपातकालीन नंबर"
- "प्रोफ़ाइल फ़ोटो"
- "कैमरा बंद है"
- "%s के द्वारा"
- "नोट भेज दिया गया है"
- "हाल ही के संदेश"
- "व्यवसाय जानकारी"
- "%.1f मील दूर"
- "%.1f किमी दूर"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "कल %s बजे खुलेगा"
- "आज %s बजे खुलता है"
- "%s बजे बंद होता है"
- "आज %s बजे बंद हो गया"
- "अभी खुला है"
- "अभी बंद है"
- "संदिग्ध स्पैम कॉलर"
- "%1$s का कॉल समाप्त हो गया"
- "इस नंबर से आपको पहली बार कॉल किया गया है."
- "हमें आशंका है कि कॉल स्पैमकर्ता का हो सकता है."
- "अवरुद्ध करें/स्पैम रिपोर्ट करें"
- "संपर्क जोड़ें"
- "स्पैम नहीं है"
-
diff --git a/InCallUI/res/values-hr/strings.xml b/InCallUI/res/values-hr/strings.xml
deleted file mode 100644
index 9c11644c4ccb3bba99b027abd6070ed9475f807c..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-hr/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Na čekanju"
- "Nepoznato"
- "Privatni broj"
- "Javna telefonska govornica"
- "Konferencijski poziv"
- "Poziv je prekinut"
- "Zvučnik"
- "Slušalice"
- "Žičane slušalice"
- "Bluetooth"
- "Poslati sljedeće tonove?\n"
- "Slanje tonova\n"
- "Pošalji"
- "Da"
- "Ne"
- "Zamijeni zamjenski znak znakom"
- "Konferencijski poziv %s"
- "Broj govorne pošte"
- "Biranje broja"
- "Ponovno biranje"
- "Konferencijski poziv"
- "Dolazni poziv"
- "Dolazni poslovni poziv"
- "Poziv je završio"
- "Na čekanju"
- "Prekidanje veze"
- "Poziv u tijeku"
- "Moj je broj %s"
- "Uspostavljanje videopoziva"
- "Videopoziv"
- "Zahtijevanje videopoziva"
- "Videopoziv nije uspostavljen"
- "Zahtjev za videopoziv odbijen"
- "Vaš broj za povratni poziv\n %1$s"
- "Vaš broj za povratni poziv za hitne službe\n %1$s"
- "Biranje broja"
- "Propušteni poziv"
- "Propušteni pozivi"
- "Propušteni pozivi (%s)"
- "Propušten poziv kontakta %s"
- "Poziv u tijeku"
- "Poslovni poziv u tijeku"
- "Wi-Fi poziv u tijeku"
- "Poslovni Wi-Fi poziv u tijeku"
- "Na čekanju"
- "Dolazni poziv"
- "Dolazni poslovni poziv"
- "Dolazni Wi-Fi poziv"
- "Dolazni poslovni Wi-Fi poziv"
- "Dolazni videopoziv"
- "Mogući neželjeni dolazni poziv"
- "Dolazni zahtjev za videopoziv"
- "Nova govorna pošta"
- "Nova govorna pošta (%d)"
- "Biraj %s"
- "Nepoznat broj govorne pošte"
- "Nema usluge"
- "Odabrana mreža (%s) nije dostupna"
- "Odgovori"
- "Prekini vezu"
- "Videopoziv"
- "Glasovni poziv"
- "Prihvati"
- "Odbaci"
- "Uzvrati"
- "Poruka"
- "Poziv u tijeku na drugom uređaju"
- "Prijenos poziva"
- "Da biste uspostavili poziv, isključite način rada u zrakoplovu."
- "Nije registrirano na mreži."
- "Mobilna mreža nije dostupna."
- "Unesite važeći broj da biste uspostavili poziv."
- "Pozivanje nije moguće."
- "Pokretanje MMI sekvence…"
- "Usluga nije podržana."
- "Prebacivanje poziva nije moguće."
- "Odvajanje poziva nije moguće."
- "Prijenos nije moguć."
- "Konferencijski poziv nije moguć."
- "Odbijanje poziva nije moguće."
- "Prekidanje poziva nije moguće."
- "SIP poziv"
- "Hitni poziv"
- "Uključivanje radija…"
- "Nema usluge. Pokušavamo ponovo…"
- "Pozivanje nije moguće. %s nije broj hitne službe."
- "Pozivanje nije moguće. Nazovite broj hitne službe."
- "Upotrijebite tipkovnicu"
- "Stavi poziv na čekanje"
- "Nastavi poziv"
- "Završi poziv"
- "Prikaži površinu za biranje brojeva"
- "Sakrij površinu za biranje brojeva"
- "Zanemari"
- "Prestani zanemarivati"
- "Dodaj poziv"
- "Spoji pozive"
- "Zamijeni"
- "Upravljaj pozivima"
- "Upravljaj konf. pozivom"
- "Konferencijski poziv"
- "Upravljanje"
- "Audio"
- "Videopoziv"
- "Prijeđi na glasovni poziv"
- "Promijeni kameru"
- "Uključivanje kamere"
- "Isključivanje kamere"
- "Više opcija"
- "Player je pokrenut"
- "Player je prekinut"
- "Fotoaparat nije spreman"
- "Fotoaparat je spreman"
- "Nepoznati događaj sesije poziva"
- "Usluga"
- "Postavljanje"
- "<Nije postavljeno>"
- "Ostale postavke poziva"
- "Pozivanje putem operatera %s"
- "Dolazni pozivi putem usluge %s"
- "fotografija kontakta"
- "uputi na privatno"
- "odabir kontakta"
- "Napišite odgovor..."
- "Odustani"
- "Pošalji"
- "Odgovori"
- "Pošalji SMS"
- "Odbij"
- "Prihvati kao videopoziv"
- "Prihvati kao audiopoziv"
- "Prihvati zahtjev za videopoziv"
- "Odbij zahtjev za videopoziv"
- "Prihvati zahtjev za slanje videopoziva"
- "Odbij zahtjev za slanje videopoziva"
- "Prihvati zahtjev za primanje videopoziva"
- "Odbij zahtjev za primanje videopoziva"
- "Kliznite prema gore za %s."
- "Kliznite lijevo za %s."
- "Kliznite desno za %s."
- "Kliznite prema dolje za %s."
- "Vibriranje"
- "Vibriranje"
- "Zvuk"
- "Zadani zvuk (%1$s)"
- "Melodija zvona telefona"
- "Vibracija tijekom zvonjenja"
- "Melodija zvona i vibracija"
- "Upravljaj konferencijskim pozivom"
- "Broj hitne službe"
- "Fotografija profila"
- "Fotoaparat je isključen"
- "putem broja %s"
- "Bilješka je poslana"
- "Nedavne poruke"
- "Informacije o tvrtki"
- "%.1f mi udaljenosti"
- "%.1f km udaljenosti"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Otvara se sutra u %s"
- "Otvara se danas u %s"
- "Zatvara se u %s"
- "Zatvoreno danas u %s"
- "Trenutačno otvoreno"
- "Trenutačno zatvoreno"
- "Neželjeni pozivatelj"
- "Poziv je završio %1$s"
- "Prvi ste put primili poziv s tog broja."
- "Sumnjamo da vas zove pošiljatelj neželjenih sadržaja."
- "Blokiranje/prijava neželjenog broja"
- "Dodavanje kontakta"
- "Nije neželjeni broj"
-
diff --git a/InCallUI/res/values-hu/strings.xml b/InCallUI/res/values-hu/strings.xml
deleted file mode 100644
index 81694260105fca642342cf822092462292409876..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-hu/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Tartásban"
- "Ismeretlen"
- "Magántelefonszám"
- "Nyilvános telefon"
- "Konferenciahívás"
- "A hívás megszakadt"
- "Hangszóró"
- "Kézibeszélő fülhallgatója"
- "Vezetékes fülhallgató"
- "Bluetooth"
- "Elküldi a következő hangjelzéseket?\n"
- "Hangjelzések küldése\n"
- "Küldés"
- "Igen"
- "Nem"
- "Helyettesítő karakter lecserélése a következőre:"
- "Konferenciahívás – %s"
- "Hangposta száma"
- "Tárcsázás"
- "Újratárcsázás"
- "Konferenciahívás"
- "Bejövő hívás"
- "Bejövő munkahelyi hívás"
- "A hívás befejeződött"
- "Tartásban"
- "Megszakítás"
- "Hívásban"
- "A számom: %s"
- "Videókapcsolat létrehozása"
- "Videóhívás"
- "Videóhívást kér"
- "A videóhívás létesítése sikertelen"
- "Videókérelem elutasítva"
- "Visszahívható telefonszáma:\n %1$s"
- "Vészhelyzet esetén visszahívható telefonszáma:\n %1$s"
- "Tárcsázás"
- "Nem fogadott hívás"
- "Nem fogadott hívások"
- "%s nem fogadott hívás"
- "Nem fogadott hívás: %s"
- "Hívás folyamatban"
- "Folyamatban lévő munkahelyi hívás"
- "Folyamatban lévő Wi-Fi-hívás"
- "Folyamatban lévő munkahelyi hívás Wi-Fi-hálózaton keresztül"
- "Tartásban"
- "Bejövő hívás"
- "Bejövő munkahelyi hívás"
- "Bejövő Wi-Fi-hívás"
- "Bejövő munkahelyi hívás Wi-Fi-hálózaton keresztül"
- "Bejövő videóhívás"
- "Bejövő gyanús spamhívás"
- "Bejövő videókérés"
- "Új hangpostaüzenet"
- "Új hangpostaüzenet (%d)"
- "%s tárcsázása"
- "A hangposta száma ismeretlen"
- "Nincs szolgáltatás"
- "A kiválasztott hálózat (%s) nem áll rendelkezésre"
- "Fogadás"
- "Hívás bontása"
- "Videó"
- "Hang"
- "Elfogadás"
- "Elvetés"
- "Visszahívás"
- "Üzenet"
- "Folyamatban lévő hívás egy másik eszközön"
- "Hívásátirányítás"
- "Hívásindításhoz kapcsolja ki a Repülős üzemmódot."
- "Nincs regisztrálva a hálózaton."
- "A mobilhálózat nem áll rendelkezésre."
- "Hívásindításhoz adjon meg egy érvényes számot."
- "A hívás sikertelen."
- "MMI-sorozat indítása…"
- "A szolgáltatás nem támogatott."
- "A hívások közötti váltás sikertelen."
- "A híváselkülönítés sikertelen."
- "Az átirányítás sikertelen."
- "A konferenciahívás sikertelen."
- "A híváselutasítás sikertelen."
- "A tartásban lévő hívás(ok) folytatása sikertelen."
- "SIP-hívás"
- "Segélyhívás"
- "Rádió bekapcsolása…"
- "Nincs szolgáltatás. Újrapróbálkozás folyamatban…"
- "A hívás sikertelen. A(z) %s szám nem segélyhívószám."
- "A hívás sikertelen. Tárcsázzon segélyhívószámot."
- "A tárcsázáshoz használja a billentyűzetet"
- "Hívás tartása"
- "Hívás folytatása"
- "Hívás befejezése"
- "Tárcsázó megjelenítése"
- "Tárcsázó elrejtése"
- "Némítás"
- "Némítás feloldása"
- "Hívás hozzáadása"
- "Hívások egyesítése"
- "Csere"
- "Hívások kezelése"
- "Konferenciahívás kezelése"
- "Konferenciahívás"
- "Kezelés"
- "Hang"
- "Videóhívás"
- "Váltás hanghívásra"
- "Váltás a kamerák között"
- "Kamera bekapcsolása"
- "Kamera kikapcsolása"
- "További lehetőségek"
- "A lejátszó elindult"
- "A lejátszó leállt"
- "A kamera nem áll készen"
- "A kamera készen áll"
- "Ismeretlen hívási esemény"
- "Szolgáltatás"
- "Beállítás"
- "<Nincs megadva>"
- "Egyéb hívásbeállítások"
- "Hívás a(z) %s szolgáltatón keresztül"
- "Bejövő hívás a következőn keresztül: %s"
- "fotó a névjegyhez"
- "magánbeszélgetés"
- "névjegy kiválasztása"
- "Saját válasz írása…"
- "Mégse"
- "Küldés"
- "Fogadás"
- "SMS küldése"
- "Elutasítás"
- "Fogadás videóhívásként"
- "Fogadás hanghívásként"
- "Videó kérésének elfogadása"
- "Videó kérésének elutasítása"
- "Videóküldési kérés elfogadása"
- "Videóküldési kérés elutasítása"
- "Videófogadási kérés elfogadása"
- "Videófogadási kérés elutasítása"
- "A(z) %s művelethez csúsztassa felfelé."
- "A(z) %s művelethez csúsztassa balra."
- "A(z) %s művelethez csúsztassa jobbra."
- "A(z) %s művelethez csúsztassa lefelé."
- "Rezgés"
- "Rezgés"
- "Hang"
- "Alapértelmezett hang (%1$s)"
- "Telefon csengőhangja"
- "Csörgéskor rezegjen"
- "Csengőhang és rezgés"
- "Konferenciahívás kezelése"
- "Segélyhívó szám"
- "Profilfotó"
- "Kamera ki"
- "a következő számon keresztül: %s"
- "Üzenet elküldve"
- "Legutóbbi üzenetek"
- "Cég adatai"
- "%.1f mérföldre"
- "%.1f kilométerre"
- "%2$s, %1$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Holnap ekkor nyit: %s"
- "Ma ekkor nyit: %s"
- "Ekkor zár: %s"
- "Ma ekkor zárt: %s"
- "Jelenleg nyitva van"
- "Jelenleg zárva van"
- "Gyanús spamhívó"
- "Hívás befejezve: %1$s"
- "Ez az első alkalom, hogy erről a számról hívása érkezett."
- "Azt gyanítjuk, hogy ez egy spamhívás."
- "Letiltás/spam bejel."
- "Névjegy hozzáadása"
- "Nem spam"
-
diff --git a/InCallUI/res/values-hy/strings.xml b/InCallUI/res/values-hy/strings.xml
deleted file mode 100644
index 899262432edd89786d38da9ee81d835b0dd4e134..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-hy/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Հեռախոս"
- "Սպասում"
- "Անհայտ"
- "Գաղտնի համար"
- "Հանրային հեռախոս"
- "Կոնֆերանս զանգ"
- "Զանգն ընդհատվեց"
- "Բարձրախոս"
- "Հեռախոսի ականջակալ"
- "Լարային ականջակալ"
- "Bluetooth"
- "Ուղարկե՞լ հետևյալ ձայներանգները:\n"
- "Ձայներանգների ուղարկում\n"
- "Ուղարկել"
- "Այո"
- "Ոչ"
- "Փոխարինել կոպիտ գրանշանը"
- "Կոնֆերանս զանգ %s"
- "Ձայնային փոստի համարը"
- "Համարը հավաքվում է"
- "Վերահամարարկում"
- "Կոնֆերանս զանգ"
- "Մուտքային զանգ"
- "Մուտքային աշխատանքային զանգ"
- "Զանգն ավարտվեց"
- "Սպասում"
- "Անջատում"
- "Զանգը միացված է"
- "Իմ համարը՝ %s"
- "Տեսակապը միանում է"
- "Տեսազանգ"
- "Տեսակապի հայցում"
- "Հնարավոր չէ միացնել տեսազանգը"
- "Տեսազանգի հարցումը մերժվել է"
- "Հետադարձ զանգի համարը՝\n%1$s"
- "Արտակարգ իրավիճակների հետադարձ զանգի համարը՝\n%1$s"
- "Համարը հավաքվում է"
- "Բաց թողնված զանգ"
- "Բաց թողնված զանգեր"
- "%s բաց թողնված զանգ"
- "Բաց թողնված զանգ %s-ից"
- "Ընթացիկ զանգ"
- "Ընթացիկ աշխատանքային զանգ"
- "Ընթացիկ Wi-Fi զանգ"
- "Ընթացիկ աշխատանքային Wi-Fi զանգ"
- "Սպասում"
- "Մուտքային զանգ"
- "Մուտքային աշխատանքային զանգ"
- "Մուտքային Wi-Fi զանգ"
- "Մուտքային աշխատանքային Wi-Fi զանգ"
- "Մուտքային տեսազանգ"
- "Մուտքային զանգը հավանաբար լցոն է"
- "Մուտքային տեսազանգի հայցում"
- "Նոր ձայնային հաղորդագրություն"
- "Նոր ձայնային հաղորդագրություն (%d)"
- "Զանգել %s համարին"
- "Ձայնային փոստի համարն անհայտ է"
- "Ծառայություն չկա"
- "Ընտրված ցանցը (%s) անհասանելի է"
- "Պատասխանել"
- "Անջատել"
- "Տեսազանգ"
- "Ձայնային"
- "Ընդունել"
- "Մերժել"
- "Հետ զանգել"
- "Հաղորդագրություն"
- "Ընթացիկ զանգ այլ սարքում"
- "Փոխանցել զանգը"
- "Զանգ կատարելու համար նախ անջատեք Ինքնաթիռի ռեժիմը:"
- "Ցանցում գրանցված չէ:"
- "Բջջային ցանցն անհասանելի է:"
- "Զանգ կատարելու համար մուտքագրեք ճիշտ համար:"
- "Հնարավոր չէ զանգել:"
- "Մեկնարկում է MMI հաջորդականությունը…"
- "Ծառայությունը չի աջակցվում:"
- "Հնարավոր չէ փոխարկել զանգերը:"
- "Հնարավոր չէ առանձնացնել զանգը:"
- "Հնարավոր չէ փոխանցել:"
- "Հնարավոր չէ կոնֆերանս զանգ կատարել:"
- "Հնարավոր չէ մերժել զանգը:"
- "Հնարավոր չէ անջատել զանգ(եր)ը:"
- "SIP զանգ"
- "Շտապ կանչ"
- "Ռադիոն միացվում է…"
- "Ծառայությունը մատչելի չէ: Փորձը կրկնվում է…"
- "Հնարավոր չէ զանգել: %s համարը արտակարգ իրավիճակի համար չէ:"
- "Հնարավոր չէ զանգել: Հավաքեք արտակարգ իրավիճակի որևէ համար:"
- "Օգտագործել ստեղնաշարը համար հավաքելու համար"
- "Հետաձգել զանգը"
- "Վերսկսել զանգը"
- "Ավարտել զանգը"
- "Ցուցադրել թվաշարը"
- "Թաքցնել թվաշարը"
- "Անջատել ձայնը"
- "Չանտեսել"
- "Ավելացնել զանգ"
- "Միացնել զանգերը"
- "Փոխանակել"
- "Կառավարել զանգերը"
- "Կառավարել կոնֆերանս զանգը"
- "Կոնֆերանս զանգ"
- "Կառավարել"
- "Ձայնային"
- "Տեսազանգ"
- "Փոխարկել ձայնային կանչի"
- "Փոխարկել խցիկը"
- "Միացնել տեսախցիկը"
- "Անջատել տեսախցիկը"
- "Այլ ընտրանքներ"
- "Նվագարկիչը մեկնարկել է"
- "Նվագարկիչը դադարեցվել է"
- "Տեսախցիկը պատրաստ չէ"
- "Տեսախցիկը պատրաստ է"
- "Զանգի աշխատաշրջանի անհայտ իրադարձություն"
- "Ծառայություն"
- "Կարգավորում"
- "<Կարգավորված չէ>"
- "Զանգերի այլ կարգավորումներ"
- "Զանգում է %s-ի միջոցով"
- "Մուտքային զանգ %s-ի միջոցով"
- "կոնտակտի լուսանկարը"
- "անցնել անձնականի"
- "ընտրել կոնտակտ"
- "Գրեք ձեր սեփականը…"
- "Չեղարկել"
- "Ուղարկել"
- "Պատասխանել"
- "Ուղարկել SMS"
- "Մերժել"
- "Պատասխանել տեսազանգով"
- "Պատասխանել ձայնային զանգով"
- "Ընդունել տեսազանգի հարցումը"
- "Մերժել տեսազանգի հարցումը"
- "Ընդունել տեսափոխանցման հարցումը"
- "Մերժել տեսափոխանցման հարցումը"
- "Ընդունել տեսազանգ ստանալու հարցումը"
- "Մերժել տեսազանգ ստանալու հարցումը"
- "Սահեցրեք վերև` %s գործառույթի համար:"
- "Սահեցրեք ձախ` %s գործառույթի համար:"
- "Սահեցրեք աջ` %s գործառույթի համար:"
- "Սահեցրեք ցած՝ %s գործառույթի համար:"
- "Թրթռոց"
- "Թրթռոց"
- "Ձայն"
- "Կանխադրված ձայնը (%1$s)"
- "Հեռախոսի զանգերանգ"
- "Թրթռալ զանգի ժամանակ"
- "Ձայներանգ և թրթռոց"
- "Կառավարել կոնֆերանս զանգը"
- "Արտակարգ իրավիճակի համար"
- "Պրոֆիլի լուսանկար"
- "Տեսախցիկն անջատված"
- "%s-ի միջոցով"
- "Գրառումն ուղարկվեց"
- "Վերջին հաղորդագրությունները"
- "Բիզնես տեղեկատվություն"
- "%.1f մղոն հեռու"
- "%.1f կմ հեռու"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Բացվում է վաղը ժամը %s-ին"
- "Բացվում է այսօր ժամը %s-ին"
- "Փակվում է ժամը %s-ին"
- "Փակվել է այսօր ժամը %s-ին"
- "Հիմա բաց է"
- "Հիմա փակ է"
- "Հավանաբար լցոն է"
- "Զանգն ավարտվեց %1$s"
- "Այս համարից առաջին անգամ եք զանգ ստանում:"
- "Կասկածներ կային, որ այս զանգը լցոնողից է:"
- "Արգելափակել/Նշել լցոն"
- "Ավելացնել կոնտակտ"
- "Լցոն չէ"
-
diff --git a/InCallUI/res/values-in/strings.xml b/InCallUI/res/values-in/strings.xml
deleted file mode 100644
index a2cd31dc7f6048481089e4b385216ccabfd29b36..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-in/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telepon"
- "Ditahan"
- "Tidak dikenal"
- "Nomor pribadi"
- "Telepon Umum"
- "Telewicara"
- "Panggilan terputus"
- "Pengeras suara"
- "Earpiece handset"
- "Headset berkabel"
- "Bluetooth"
- "Kirim nada berikut?\n"
- "Mengirim nada\n"
- "Kirim"
- "Ya"
- "Tidak"
- "Ganti karakter acak dengan"
- "Telewicara %s"
- "Nomor pesan suara"
- "Memanggil"
- "Memanggil ulang"
- "Telewicara"
- "Panggilan masuk"
- "Panggilan masuk di telepon kerja"
- "Panggilan diakhiri"
- "Ditahan"
- "Menutup panggilan"
- "Sedang dalam panggilan"
- "Nomor saya %s"
- "Menyambungkan video"
- "Video call"
- "Meminta video"
- "Tidak dapat menyambungkan video call"
- "Permintaan video ditolak"
- "Nomor panggilan balik Anda\n %1$s"
- "Nomor panggilan balik darurat Anda\n %1$s"
- "Memanggil"
- "Panggilan tak terjawab"
- "Panggilan tak terjawab"
- "%s panggilan tak terjawab"
- "Panggilan tak terjawab dari %s"
- "Panggilan yang berlangsung"
- "Panggilan telepon kerja yang sedang berlangsung"
- "Panggilan Wi-Fi keluar"
- "Panggilan Wi-Fi kerja yang sedang berlangsung"
- "Ditahan"
- "Panggilan masuk"
- "Panggilan masuk di telepon kerja"
- "Panggilan Wi-Fi masuk"
- "Panggilan Wi-Fi masuk di telepon kerja"
- "Video call masuk"
- "Panggilan masuk yang diduga spam"
- "Permintaan video masuk"
- "Pesan suara baru"
- "Pesan suara baru (%d)"
- "Telepon %s"
- "Nomor pesan suara tidak dikenal"
- "Tidak ada layanan"
- "Jaringan yang dipilih (%s) tidak tersedia"
- "Jawab"
- "Akhiri"
- "Video"
- "Suara"
- "Terima"
- "Tutup"
- "Telepon balik"
- "Pesan"
- "Panggilan yang berlangsung di perangkat lain"
- "Transfer Panggilan"
- "Untuk melakukan panggilan, terlebih dahulu nonaktifkan mode Pesawat."
- "Tidak terdaftar pada jaringan."
- "Jaringan seluler tidak tersedia."
- "Untuk melakukan panggilan telepon, masukkan nomor yang valid."
- "Tidak dapat menelepon."
- "Memulai urutan MMI..."
- "Layanan tidak didukung."
- "Tidak dapat beralih panggilan."
- "Tidak dapat memisahkan panggilan."
- "Tidak dapat mentransfer."
- "Tidak dapat melakukan telewicara."
- "Tidak dapat menolak panggilan."
- "Tidak dapat melepas panggilan."
- "Panggilan SIP"
- "Panggilan darurat"
- "Menghidupkan radio..."
- "Tidak ada layanan. Mencoba lagi…"
- "Tidak dapat menelepon. %s bukan nomor darurat."
- "Tidak dapat menelepon. Panggil nomor darurat."
- "Gunakan keyboard untuk memanggil"
- "Tahan Panggilan"
- "Mulai Kembali Panggilan"
- "Akhiri Panggilan"
- "Tampilkan tombol nomor"
- "Sembunyikan tombol nomor"
- "Bisukan"
- "Suarakan"
- "Tambahkan panggilan"
- "Gabungkan panggilan"
- "Tukar"
- "Kelola panggilan"
- "Kelola telewicara"
- "Konferensi telepon"
- "Kelola"
- "Audio"
- "Video call"
- "Ubah ke panggilan suara"
- "Beralih kamera"
- "Nyalakan kamera"
- "Matikan kamera"
- "Opsi lainnya"
- "Pemutar Dimulai"
- "Pemutar Dihentikan"
- "Kamera tidak siap"
- "Kamera siap"
- "Sesi panggilan tidak dikenal"
- "Layanan"
- "Siapkan"
- "<Tidak disetel>"
- "Setelan panggilan lainnya"
- "Memanggil via %s"
- "Masuk melalui %s"
- "foto kontak"
- "aktifkan pribadi"
- "pilih kontak"
- "Tulis respons Anda sendiri…"
- "Batal"
- "Kirim"
- "Jawab"
- "Kirim SMS"
- "Tolak"
- "Jawab sebagai video call"
- "Jawab sebagai panggilan audio"
- "Terima permintaan video"
- "Tolak permintaan video"
- "Terima permintaan transmisi video"
- "Tolak permintaan transmisi video"
- "Terima permintaan menerima video"
- "Tolak permintaan menerima video"
- "Geser ke atas untuk %s."
- "Geser ke kiri untuk %s."
- "Geser ke kanan untuk %s."
- "Geser ke bawah untuk %s."
- "Getar"
- "Getar"
- "Suara"
- "Suara default (%1$s)"
- "Nada dering ponsel"
- "Bergetar saat berdering"
- "Nada dering & Getar"
- "Kelola telewicara"
- "Nomor darurat"
- "Foto profil"
- "Kamera tidak aktif"
- "melalui %s"
- "Catatan telah dikirim"
- "Pesan terbaru"
- "Info bisnis"
- "%.1f mil"
- "%.1f km"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Buka jam %s"
- "Hari ini buka jam %s"
- "Tutup pukul %s"
- "Hari ini tutup pukul %s"
- "Buka sekarang"
- "Sekarang tutup"
- "Diduga telepon spam"
- "Panggilan diakhiri %1$s"
- "Nomor ini baru pertama kali menghubungi Anda."
- "Kami menduga panggilan ini dari pelaku spam."
- "Blokir/laporkan spam"
- "Tambahkan kontak"
- "Bukan spam"
-
diff --git a/InCallUI/res/values-is/strings.xml b/InCallUI/res/values-is/strings.xml
deleted file mode 100644
index 480fd6eaadb1a9d17dff2f687444250058d84cf5..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-is/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Sími"
- "Í bið"
- "Óþekkt"
- "Óþekkt númer"
- "Símasjálfsali"
- "Símafundur"
- "Símtali slitið"
- "Hátalari"
- "Símahátalari"
- "Höfuðtól með snúru"
- "Bluetooth"
- "Senda eftirfarandi tóna?\n"
- "Sendir tóna\n"
- "Senda"
- "Já"
- "Nei"
- "Skipta algildisstaf út fyrir"
- "Símafundur %s"
- "Talhólfsnúmer"
- "Hringir"
- "Hringir aftur"
- "Símafundur"
- "Móttekið símtal"
- "Vinnusímtal berst"
- "Lagt á"
- "Í bið"
- "Leggur"
- "Í símtali"
- "Númerið mitt er %s"
- "Tengir myndskeið"
- "Myndsímtal"
- "Biður um myndskeið"
- "Ekki tókst að tengja myndsímtal"
- "Myndsímtalsbeiðni hafnað"
- "Svarhringingarnúmer þitt\n %1$s"
- "Svarhringingarnúmer þitt í neyðartilvikum\n %1$s"
- "Hringir"
- "Ósvarað símtal"
- "Ósvöruð símtöl"
- "%s ósvöruð símtöl"
- "Ósvarað símtal frá %s"
- "Samtal í gangi"
- "Vinnusímtal í gangi"
- "Wi-Fi símtal stendur yfir"
- "Vinnusímtal í gangi um Wi-Fi"
- "Í bið"
- "Móttekið símtal"
- "Vinnusímtal berst"
- "Wi-Fi símtal berst"
- "Vinnusímtal berst um Wi-Fi"
- "Myndsímtal berst"
- "Símtal sem berst er hugsanlega úr ruslnúmeri"
- "Myndbeiðni berst"
- "Ný skilaboð í talhólfinu"
- "Ný skilaboð í talhólfinu (%d)"
- "Hringja í %s"
- "Talhólfsnúmer ekki þekkt"
- "Ekkert símasamband"
- "Valið símkerfi (%s) er ekki tiltækt"
- "Svara"
- "Leggja á"
- "Myndskeið"
- "Tal"
- "Samþykkja"
- "Hunsa"
- "Hringja til baka"
- "Skilaboð"
- "Símtal í gangi í öðru tæki"
- "Flytja símtal"
- "Til að hringja símtal þarftu fyrst að slökkva á flugstillingu."
- "Ekki skráð á símkerfi."
- "Farsímakerfi ekki til staðar."
- "Sláðu inn gilt númer til að hringja símtal."
- "Ekki hægt að hringja."
- "Ræsir MMI-runu…"
- "Þjónustan er ekki studd."
- "Ekki hægt að skipta milli símtala."
- "Ekki hægt að aðskilja símtal."
- "Ekki hægt að flytja."
- "Ekki hægt að halda símafund."
- "Ekki hægt að hafna símtali."
- "Ekki hægt að leggja á."
- "SIP-símtal"
- "Neyðarsímtal"
- "Kveikir á loftneti…"
- "Ekkert samband. Reynir aftur…"
- "Getur ekki hringt. %s er ekki neyðarsímanúmer."
- "Ekki hægt að hringja. Hringdu í neyðarnúmer"
- "Notaðu lyklaborðið til að hringja"
- "Setja símtal í bið"
- "Halda símtali áfram"
- "Leggja á"
- "Sýna símatakkaborð"
- "Fela símatakkaborð"
- "Slökkva á hljóði"
- "Kveikja á hljóði"
- "Bæta við símtali"
- "Sameina símtöl"
- "Skipta milli"
- "Stjórna símtölum"
- "Stjórna símafundi"
- "Símafundur"
- "Stjórna"
- "Hljóð"
- "Myndsímtal"
- "Breyta í símtal"
- "Skipta um myndavél"
- "Kveikja á myndavél"
- "Slökkva á myndavél"
- "Fleiri valkostir"
- "Spilari ræstur"
- "Spilari stöðvaður"
- "Myndavél ekki tilbúin"
- "Myndavél tilbúin"
- "Óþekkt atvik símtalslotu"
- "Þjónusta"
- "Uppsetning"
- "<Ekki valið>"
- "Aðrar símtalsstillingar"
- "Hringt í gegnum %s"
- "Berst í gegnum %s"
- "mynd tengiliðar"
- "tala í einrúmi"
- "velja tengilið"
- "Skrifaðu eigið svar…"
- "Hætta við"
- "Senda"
- "Svara"
- "Senda SMS-skilaboð"
- "Hafna"
- "Svara sem myndsímtali"
- "Svara sem símtali"
- "Samþykkja beiðni um myndsímtal"
- "Hafna beiðni um myndsímtal"
- "Samþykkja beiðni um sendingu myndsímtals"
- "Hafna beiðni um sendingu myndsímtals"
- "Samþykkja beiðni um móttöku myndsímtals"
- "Hafna beiðni um móttöku myndsímtals"
- "Strjúktu upp til að %s."
- "Strjúktu til vinstri til að %s."
- "Strjúktu til hægri til að %s."
- "Strjúktu niður til að %s."
- "Titra"
- "Titra"
- "Hljóð"
- "Sjálfgefið hljóð (%1$s)"
- "Hringitónn síma"
- "Titra við hringingu"
- "Hringitónn og titringur"
- "Stjórna símafundi"
- "Neyðarnúmer"
- "Prófílmynd"
- "Slökkt á myndavél"
- "úr %s"
- "Glósa send"
- "Nýleg skilaboð"
- "Fyrirtækjaupplýsingar"
- "í %.1f míl. fjarlægð"
- "í %.1f km fjarlægð"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Opið á morgun frá kl. %s"
- "Opið í dag frá kl. %s"
- "Lokað kl. %s"
- "Var lokað í dag kl. %s"
- "Opið núna"
- "Lokað núna"
- "Grunur um svikasímtal"
- "Símtali lokið %1$s"
- "Þetta er í fyrsta sinn sem hringt er í þig úr þessu númeri."
- "Okkur grunaði að þetta símtal væri úr ruslnúmeri."
- "Bannlisti/tilkynna"
- "Bæta tengilið við"
- "Ekki ruslnúmer"
-
diff --git a/InCallUI/res/values-it/strings.xml b/InCallUI/res/values-it/strings.xml
deleted file mode 100644
index c9b49501b919a4987ff662438466de1e825bd5bd..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-it/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefono"
- "In attesa"
- "Sconosciuto"
- "Numero privato"
- "Telefono pubblico"
- "Audioconferenza"
- "Chiamata persa"
- "Altoparlante"
- "Auricolare telefono"
- "Auricolare con cavo"
- "Bluetooth"
- "Inviare i numeri successivi?\n"
- "Invio toni\n"
- "Invia"
- "Sì"
- "No"
- "Sostituisci carattere jolly con"
- "Audioconferenza: %s"
- "Numero segreteria"
- "Chiamata in corso"
- "Ricomposizione"
- "Audioconferenza"
- "Chiamata in arrivo"
- "Chiamata lavoro in arrivo"
- "Chiamata terminata"
- "In attesa"
- "In fase di chiusura"
- "Chiamata in corso"
- "Il mio numero è: %s"
- "Collegamento video"
- "Videochiamata"
- "Richiesta video in corso"
- "Impossibile effettuare una videochiamata"
- "Richiesta video rifiutata"
- "Numero da richiamare:\n %1$s"
- "Numero da richiamare in caso di emergenza:\n %1$s"
- "Composizione in corso"
- "Chiamata persa"
- "Chiamate perse"
- "%s chiamate perse"
- "Chiamata senza risposta da %s"
- "Chiamata in corso"
- "Chiamata di lavoro in corso"
- "Chiamata Wi-Fi in corso"
- "Chiamata di lavoro tramite Wi-Fi in corso"
- "In attesa"
- "Chiamata in arrivo"
- "Chiamata di lavoro in arrivo"
- "Chiamata Wi-Fi in arrivo"
- "Chiamata di lavoro in arrivo tramite Wi-Fi"
- "Videochiamata in arrivo"
- "Chiamata di presunto spam in arrivo"
- "Richiesta video in arrivo"
- "Nuovo messaggio vocale"
- "Nuovo messaggio vocale (%d)"
- "Componi %s"
- "Numero segreteria sconosciuto"
- "Nessun servizio"
- "Rete selezionata (%s) non disponibile"
- "Rispondi"
- "Riaggancia"
- "Video"
- "Voce"
- "Accetta"
- "Ignora"
- "Richiama"
- "Messaggio"
- "Chiamata in corso su un altro dispositivo"
- "Trasferisci chiamata"
- "Per fare una chiamata, disattiva la modalità aereo."
- "Non registrato sulla rete."
- "Rete dati non disponibile."
- "Per fare una chiamata, inserisci un numero valido."
- "Impossibile chiamare."
- "Avvio sequenza MMI..."
- "Servizio non supportato."
- "Impossibile cambiare chiamata."
- "Impossibile separare la chiamata."
- "Impossibile trasferire."
- "Impossibile fare una chiamata in conferenza."
- "Impossibile rifiutare la chiamata."
- "Impossibile riagganciare."
- "Chiamata SIP"
- "Chiamata di emergenza"
- "Attivazione segnale cellulare..."
- "Nessun servizio. Nuovo tentativo…"
- "Impossibile chiamare. %s non è un numero di emergenza."
- "Impossibile chiamare. Componi un numero di emergenza."
- "Usa tastiera"
- "Metti in attesa la chiamata"
- "Riprendi chiamata"
- "Termina chiamata"
- "Mostra tastierino"
- "Nascondi tastierino"
- "Disattiva audio"
- "Riattiva audio"
- "Aggiungi chiamata"
- "Unisci chiamate"
- "Scambia"
- "Gestisci chiamate"
- "Gestisci audioconferenza"
- "Audioconferenza"
- "Gestisci"
- "Audio"
- "Videochiam"
- "Passa a chiamata vocale"
- "Cambia fotocamera"
- "Attiva fotocamera"
- "Disattiva fotocamera"
- "Altre opzioni"
- "Player avviato"
- "Player interrotto"
- "La fotocamera non è pronta"
- "Fotocamera pronta"
- "Evento sessione chiamata sconosciuto"
- "Servizio"
- "Configura"
- "<Non impostato>"
- "Altre impostazioni di chiamata"
- "Chiamate tramite %s"
- "In arrivo tramite %s"
- "foto contatto"
- "Privato"
- "seleziona contatto"
- "Scrivi risposta personale..."
- "Annulla"
- "Invia"
- "Rispondi"
- "Invia SMS"
- "Rifiuta"
- "Rispondi con videochiamata"
- "Rispondi con chiamata audio"
- "Accetta richiesta video"
- "Rifiuta richiesta video"
- "Accetta richiesta di trasmissione video"
- "Rifiuta richiesta di trasmissione video"
- "Accetta richiesta di ricevimento video"
- "Rifiuta richiesta di ricevimento video"
- "Scorri verso l\'alto per %s."
- "Scorri verso sinistra per %s."
- "Scorri verso destra per %s."
- "Scorri verso il basso per %s."
- "Vibrazione"
- "Vibrazione"
- "Suono"
- "Suono predefinito (%1$s)"
- "Suoneria telefono"
- "Vibrazione quando squilla"
- "Suoneria e vibrazione"
- "Gestisci audioconferenza"
- "Numero di emergenza"
- "Foto del profilo"
- "Fotocamera disattivata"
- "tramite %s"
- "Nota inviata"
- "Messaggi recenti"
- "Informazioni sull\'attività"
- "Distante %.1f mi"
- "Distante %.1f km"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Apre domani alle ore %s"
- "Apre oggi alle ore %s"
- "Chiude alle ore %s"
- "Ha chiuso oggi alle ore %s"
- "Aperto ora"
- "Ora chiuso"
- "Presunto spammer"
- "Chiamata terminata %1$s"
- "È la prima volta che questo numero ti chiama."
- "Sospettavamo che questa chiamata provenisse da uno spammer."
- "Blocca/Segnala spam"
- "Aggiungi contatto"
- "Non spam"
-
diff --git a/InCallUI/res/values-iw/strings.xml b/InCallUI/res/values-iw/strings.xml
deleted file mode 100644
index c75c8da0d88b92fc534529ec82a24c7ac91fb6a4..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-iw/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "טלפון"
- "בהמתנה"
- "לא ידוע"
- "מספר פרטי"
- "טלפון ציבורי"
- "שיחת ועידה"
- "השיחה נותקה"
- "רמקול"
- "אוזנייה"
- "אוזניות עם חיבור חוטי"
- "Bluetooth"
- "האם לשלוח את הצלילים הבאים?\n"
- "שולח צלילים\n"
- "שלח"
- "כן"
- "לא"
- "החלף את התו הכללי ב"
- "שיחת ועידה %s"
- "המספר של הדואר הקולי"
- "מחייג"
- "מחייג שוב"
- "שיחת ועידה"
- "שיחה נכנסת"
- "שיחת עבודה נכנסת"
- "השיחה הסתיימה"
- "בהמתנה"
- "מנתק"
- "בשיחה"
- "המספר שלי הוא %s"
- "מחבר וידאו"
- "שיחת וידאו"
- "מבקש וידאו"
- "לא ניתן לחבר שיחת וידאו"
- "בקשת וידאו נדחתה"
- "המספר שלך להתקשרות חזרה\n %1$s"
- "המספר שלך להתקשרות חזרה במצב חירום\n %1$s"
- "מחייג"
- "שיחה שלא נענתה"
- "שיחות שלא נענו"
- "%s שיחות שלא נענו"
- "שיחה שלא נענתה מאת %s"
- "שיחה פעילה"
- "שיחת עבודה פעילה"
- "שיחת Wi-Fi פעילה"
- "שיחת עבודה פעילה ברשת WiFi"
- "בהמתנה"
- "שיחה נכנסת"
- "שיחת עבודה נכנסת"
- "שיחת Wi-Fi נכנסת"
- "שיחת עבודה נכנסת ברשת WiFi"
- "שיחת וידאו נכנסת"
- "השיחה הנכנסת חשודה כספאם"
- "בקשת וידאו נכנסת"
- "דואר קולי חדש"
- "דואר קולי חדש (%d)"
- "חייג %s"
- "המספר של הדואר הקולי אינו ידוע"
- "אין שירות"
- "הרשת שנבחרה (%s) לא זמינה"
- "ענה"
- "נתק"
- "וידאו"
- "קול"
- "אשר"
- "בטל"
- "התקשר חזרה"
- "שלח הודעה"
- "באחד מהמכשירים האחרים מתבצעת שיחה"
- "העבר את השיחה"
- "כדי להתקשר, כבה תחילה את מצב טיסה."
- "לא רשום ברשת."
- "רשת סלולרית אינה זמינה."
- "כדי להתקשר, הזן מספר טלפון חוקי."
- "לא ניתן להתקשר."
- "מתחיל רצף MMI…"
- "שירות לא נתמך."
- "לא ניתן לעבור בין שיחות."
- "לא ניתן להפריד שיחה."
- "לא ניתן להעביר."
- "לא ניתן לבצע שיחת ועידה."
- "לא ניתן לדחות שיחה."
- "לא ניתן להתקשר."
- "שיחת SIP"
- "שיחת חירום"
- "מפעיל את הרדיו…"
- "אין שירות. מנסה שוב..."
- "לא ניתן להתקשר. %s אינו מספר חירום."
- "לא ניתן להתקשר. חייג למספר חירום."
- "השתמש במקלדת כדי לחייג"
- "החזק שיחה"
- "המשך בשיחה"
- "סיים שיחה"
- "הצגת לוח החיוג"
- "הסתרת לוח החיוג"
- "השתקה"
- "ביטול ההשתקה"
- "הוסף שיחה"
- "מזג שיחות"
- "החלף"
- "נהל שיחות"
- "נהל שיחת ועידה"
- "שיחת ועידה"
- "ניהול"
- "אודיו"
- "שיחת וידאו"
- "שנה לשיחה קולית"
- "החלף מצלמה"
- "הפעל את המצלמה"
- "כבה את המצלמה"
- "אפשרויות נוספות"
- "הנגן הופעל"
- "הנגן הפסיק"
- "המצלמה לא מוכנה"
- "המצלמה מוכנה"
- "אירוע הפעלת שיחה לא ידוע"
- "שירות"
- "הגדרות"
- "<לא הוגדר>"
- "הגדרות אחרות של שיחה"
- "שיחה באמצעות %s"
- "שיחה נכנסת באמצעות %s"
- "תמונה של איש קשר"
- "עבור לשיחה פרטית"
- "בחר איש קשר"
- "כתוב תגובה משלך..."
- "בטל"
- "שלח"
- "ענה"
- "שלח SMS"
- "דחה"
- "ענה כשיחת וידאו"
- "ענה כשיחת אודיו"
- "קבל בקשת וידאו"
- "דחה בקשת וידאו"
- "אשר את הבקשה לשידור וידאו"
- "דחה את הבקשה לשידור וידאו"
- "אשר את הבקשה לקבלת וידאו"
- "דחה את הבקשה לקבלת וידאו"
- "הסט למעלה כדי %s."
- "הסט שמאלה כדי %s."
- "הסט ימינה כדי %s."
- "הסט למטה כדי %s."
- "רטט"
- "רטט"
- "צליל"
- "צליל ברירת מחדל (%1$s)"
- "רינגטון של טלפון"
- "רטט בעת צלצול"
- "רינגטון ורטט"
- "נהל שיחת ועידה"
- "מספר חירום"
- "תמונת פרופיל"
- "המצלמה כבויה"
- "באמצעות %s"
- "ההערה נשלחה"
- "הודעות אחרונות"
- "פרטי עסק"
- "במרחק %.1f מייל"
- "במרחק %.1f ק\"מ"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "ייפתח מחר ב-%s"
- "נפתח היום ב-%s"
- "נסגר ב-%s"
- "נסגר היום ב-%s"
- "פתוח עכשיו"
- "סגור עכשיו"
- "חשד לשיחת ספאם"
- "השיחה הסתיימה %1$s"
- "זוהי הפעם הראשונה שמתקשרים אליך מהמספר הזה."
- "אנו חושדים שהמספר הזה הוא של שולח ספאם."
- "חסימה/דיווח על ספאם"
- "הוספת איש קשר"
- "לא ספאם"
-
diff --git a/InCallUI/res/values-ja/strings.xml b/InCallUI/res/values-ja/strings.xml
deleted file mode 100644
index 551d896b55f36149b71e29c9501f5df7e877bf74..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ja/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "電話"
- "保留中"
- "不明"
- "非通知"
- "公衆電話"
- "グループ通話"
- "通話が遮断されました"
- "スピーカー"
- "モバイル端末のイヤホン"
- "有線ヘッドセット"
- "Bluetooth"
- "次の番号を送信しますか?\n"
- "番号を送信中\n"
- "送信"
- "はい"
- "いいえ"
- "ワイルド文字を置換:"
- "グループ通話 %s"
- "ボイスメールの番号"
- "発信中"
- "リダイヤル中"
- "グループ通話"
- "着信中"
- "仕事の通話が着信中"
- "通話終了"
- "保留中"
- "通話終了"
- "通話中"
- "この電話の番号: %s"
- "ビデオハングアウトに接続中"
- "ビデオハングアウト"
- "ビデオハングアウトをリクエスト中"
- "ビデオハングアウトの接続エラー"
- "ビデオハングアウトのリクエスト不承認"
- "コールバック先\n %1$s"
- "緊急通報コールバック先\n %1$s"
- "発信中"
- "不在着信"
- "不在着信"
- "不在着信 %s 件"
- "%s さんからの不在着信"
- "通話中"
- "仕事の通話中"
- "Wi-Fi 通話中"
- "仕事の Wi-Fi 通話中"
- "保留中"
- "着信中"
- "仕事の通話が着信中"
- "Wi-Fi 通話が着信中"
- "仕事の Wi-Fi 通話が着信中"
- "ビデオハングアウトが着信中"
- "迷惑電話の疑いがある通話を着信しています"
- "ビデオハングアウト リクエストが着信中"
- "新着のボイスメール"
- "新着のボイスメール(%d 件)"
- "%s に発信"
- "ボイスメールの番号が不明です"
- "通信サービスはありません"
- "選択したネットワーク(%s)が利用できません"
- "電話に出る"
- "通話終了"
- "ビデオ"
- "音声"
- "受ける"
- "拒否する"
- "コールバック"
- "メッセージ"
- "別の端末で通話中"
- "通話を転送"
- "機内モードを OFF にしてから発信してください。"
- "ご加入の通信サービスがありません。"
- "モバイル ネットワークが利用できません。"
- "発信するには、有効な番号を入力してください。"
- "発信できません。"
- "MMI シーケンスを開始しています..."
- "サービスはサポートされていません。"
- "通話を切り替えられません。"
- "通話を分割できません。"
- "転送できません。"
- "グループ通話できません。"
- "着信を拒否できません。"
- "通話を解放できません。"
- "SIP 通話"
- "緊急通報"
- "無線通信を ON にしています..."
- "通信サービスはありません。もう一度お試しください…"
- "発信できません。%s は緊急通報番号ではありません。"
- "発信できません。緊急通報番号におかけください。"
- "キーボードで番号を入力してください"
- "通話を保留"
- "通話を再開"
- "通話を終了"
- "ダイヤルパッドを表示"
- "ダイヤルパッドを非表示"
- "ミュート"
- "ミュートを解除"
- "通話を追加"
- "グループ通話"
- "切り替え"
- "通話を管理"
- "グループ通話オプション"
- "グループ通話"
- "管理"
- "音声"
- "ビデオ"
- "音声通話に変更"
- "カメラを切り替え"
- "カメラを ON にする"
- "カメラを OFF にする"
- "その他のオプション"
- "プレーヤーを開始しました"
- "プレーヤーを停止しました"
- "カメラが準備できていません"
- "カメラが準備できました"
- "不明な通話セッション イベントです"
- "サービス"
- "セットアップ"
- "<未設定>"
- "その他の通話設定"
- "%s で発信中"
- "%s で着信中"
- "連絡先の写真"
- "個別通話に切り替え"
- "連絡先を選択"
- "カスタム返信を作成..."
- "キャンセル"
- "送信"
- "電話に出る"
- "SMS を送信する"
- "拒否"
- "ビデオハングアウトで電話に出る"
- "音声通話で電話に出る"
- "ビデオハングアウト リクエストを承認する"
- "ビデオハングアウト リクエストを拒否する"
- "ビデオハングアウト送信リクエストを承認する"
- "ビデオハングアウト送信リクエストを拒否する"
- "ビデオハングアウト受信リクエストを承認する"
- "ビデオハングアウト受信リクエストを拒否する"
- "上にスライドして%sを行います。"
- "左にスライドして%sを行います。"
- "右にスライドして%sを行います。"
- "下にスライドして%sを行います。"
- "バイブレーション"
- "バイブレーション"
- "着信音"
- "デフォルトの通知音(%1$s)"
- "着信音"
- "着信時のバイブレーション"
- "着信音とバイブレーション"
- "グループ通話オプション"
- "緊急通報番号"
- "プロフィール写真"
- "カメラ OFF"
- "%s に着信"
- "メモを送信しました"
- "最近のメッセージ"
- "ビジネス情報"
- "%.1f マイル内"
- "%.1f km 内"
- "%1$s、%2$s"
- "%1$s~%2$s"
- "%1$s、%2$s"
- "明日 %sに営業開始"
- "本日 %sに営業開始"
- "%sに営業終了"
- "本日 %sに営業終了"
- "現在営業中"
- "営業終了"
- "迷惑電話の疑いあり"
- "通話が終了しました %1$s"
- "この番号からの通話を受信したのはこれが初めてです。"
- "この通話は迷惑電話の可能性があります。"
- "ブロック / 報告"
- "連絡先に追加"
- "迷惑電話ではない"
-
diff --git a/InCallUI/res/values-ka/strings.xml b/InCallUI/res/values-ka/strings.xml
deleted file mode 100644
index b0100656166524109bea61bd33be1031eb10cc89..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ka/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ტელეფონი"
- "მოცდის რეჟიმში"
- "უცნობი"
- "დაფარული ნომერი"
- "ტელეფონ-ავტომატი"
- "საკონფერენციო ზარი"
- "ზარი შეწყდა"
- "დინამიკი"
- "ყურსაცვამის საყურისი"
- "სადენიანი ყურსაცვამი"
- "Bluetooth"
- "გსურთ შემდეგი ტონების გაგზავნა?\n"
- "ტონების გაგზავნა\n"
- "გაგზავნა"
- "დიახ"
- "არა"
- "ჩანაცვლების სიმბოლო ჩანაცვლდეს შემდეგით:"
- "საკონფერენციო ზარი: %s"
- "ხმოვანი ფოსტის ნომერი"
- "მიმდინარეობს აკრეფა"
- "იკრიფება ხელახლა"
- "საკონფერენციო ზარი"
- "შემომავალი ზარი"
- "შემომავალი ზარი (სამსახური)"
- "ზარი დასრულდა"
- "მოცდის რეჟიმში"
- "მიმდინარეობს გათიშვა"
- "საუბრის რეჟიმში"
- "ჩემი ნომერია %s"
- "მიმდინარეობს ვიდეოს დაკავშირება"
- "ვიდეო ზარი"
- "მიმდინარეობს ვიდეოს მოთხოვნა"
- "ვიდეო ზარის დაკავშირება ვერ მოხერხდა"
- "ვიდეოს მოთხოვნა უარყოფილია"
- "თქვენი ნომერი გადმორეკვისთვის\n %1$s"
- "თქვენი ნომერი გადაუდებელი გადმორეკვისთვის\n %1$s"
- "მიმდინარეობს აკრეფა"
- "გამოტოვებული ზარი"
- "გამოტოვებული ზარები"
- "%s გამოტოვებული ზარი"
- "გამოტოვებული ზარი %s-ისგან"
- "მიმდინარე ზარი"
- "მიმდინარე ზარი (სამსახური)"
- "მიმდინარე Wi-Fi ზარი"
- "მიმდინარე Wi-Fi ზარი (სამსახური)"
- "მოცდის რეჟიმში"
- "შემომავალი ზარი"
- "შემომავალი ზარი (სამსახური)"
- "შემომავალი Wi-Fi ზარი"
- "შემომავალი Wi-Fi ზარი (სამსახური)"
- "შემომავალი ვიდეო ზარი"
- "შემომავალი ზარი - სავარაუდოდ სპამი"
- "შემომავალი ვიდეოს მოთხოვნა"
- "ახალი ხმოვანი შეტყობინება"
- "ახალი ხმოვანი შეტყობინება (%d)"
- "%s-ზე დარეკვა"
- "ხმოვანი ფოსტის ნომერი უცნობია"
- "სერვისი არ არის"
- "არჩეული ქსელი (%s) მიუწვდომელია"
- "პასუხი"
- "გათიშვა"
- "ვიდეო"
- "ხმოვანი"
- "მიღება"
- "დახურვა"
- "გადარეკვა"
- "შეტყობინება"
- "სხვა მოწყობილობაზე მიმდინარე ზარი"
- "ზარის ტრანსფერი"
- "ზარის განსახორციელებლად, ჯერ გამორთეთ თვითმფრინავის რეჟიმი."
- "არ არის რეგისტრირებული ქსელში."
- "ფიჭური ქსელი მიუწვდომელია."
- "ზარის განსახორციელებლად, შეიყვანეთ სწორი ნომერი."
- "დარეკვა ვერ ხერხდება."
- "MMI თანმიმდევრობის დაწყება…"
- "სერვისი არ არის მხარდაჭერილი."
- "ზარების გადართვა ვერ ხერხდება."
- "ზარის განცალკევება ვერ ხერხდება."
- "გადამისამართება ვერ ხერხდება."
- "საკონფერენციო ზარის განხორციელება ვერ ხერხდება."
- "ზარის უარყოფა ვერ ხერხდება."
- "ზარ(ებ)ის გათიშვა ვერ ხერხდება."
- "SIP ზარი"
- "გადაუდებელი ზარი"
- "მიმდინარეობს რადიოს ჩართვა…"
- "სერვისი არ არის. მიმდინარეობს ხელახლა ცდა…"
- "დარეკვა ვერ ხერხდება. %s არ არის გადაუდებელი დახმარების ნომერი."
- "დარეკვა ვერ ხერხდება. აკრიფეთ გადაუდებელი დახმარების ნომერი."
- "ნომრის ასაკრეფად გამოიყენეთ კლავიატურა"
- "მოცდის რეჟიმზე გადაყვანა"
- "ზარის განახლება"
- "ზარის დასრულება"
- "ციფერბლატის ჩვენება"
- "ციფერბლატის დამალვა"
- "დადუმება"
- "დადუმების გაუქმება"
- "ზარის დამატება"
- "ზარების გაერთიანება"
- "ჩანაცვლება"
- "ზარების მართვა"
- "საკონფერენციო ზარის მართვა"
- "საკონფერენციო ზარი"
- "მართვა"
- "აუდიო"
- "ვიდეო ზარი"
- "ხმოვან ზარზე გადართვა"
- "კამერის გადართვა"
- "კამერის ჩართვა"
- "კამერის გამორთვა"
- "სხვა ვარიანტები"
- "დამკვრელი ჩაირთო"
- "დამკვრელი გამოირთო"
- "კამერა არ არის მზად"
- "კამერა მზადაა"
- "ზარის სესიის უცნობი მოვლენა"
- "სერვისი"
- "დაყენება"
- "<არ არის დაყენებული>"
- "ზარის სხვა პარამეტრები"
- "მიმდინარეობს დარეკვა %s-ის მეშვეობით"
- "შემომავალი ზარი %s-დან"
- "კონტაქტის ფოტო"
- "პირადი რეჟიმი"
- "კონტაქტის არჩევა"
- "საკუთარის შექმნა..."
- "გაუქმება"
- "გაგზავნა"
- "პასუხი"
- "SMS-ის გაგზავნა"
- "უარყოფა"
- "პასუხი ვიდეო ზარის სახით"
- "პასუხი ხმოვანი ზარის სახით"
- "ვიდეოს მოთხოვნის მიღება"
- "ვიდეოს მოთხოვნის უარყოფა"
- "ვიდეოს გადაცემის მოთხოვნის მიღება"
- "ვიდეოს გადაცემის მოთხოვნის უარყოფა"
- "ვიდეოს მიღების მოთხოვნაზე დათანხმება"
- "ვიდეოს მიღების მოთხოვნის უარყოფა"
- "გაასრიალეთ ზემოთ, რათა შესრულდეს %s."
- "გაასრიალეთ მარცხნივ, რათა შესრულდეს %s."
- "გაასრიალეთ მარჯვნივ, რათა შესრულდეს %s."
- "გაასრიალეთ ქვემოთ, რათა შესრულდეს %s."
- "ვიბრაცია"
- "ვიბრაცია"
- "ხმა"
- "ნაგულისხმები ხმა (%1$s)"
- "ტელეფონის ზარი"
- "ვიბრაცია დარეკვისას"
- "ზარის მელოდია და ვიბრაცია"
- "საკონფერენციო ზარის მართვა"
- "გადაუდებელი დახმარების ნომერი"
- "პროფილის ფოტო"
- "კამერა გამორთულია"
- "%s-დან"
- "შენიშვნა გაიგზავნა"
- "ბოლო შეტყობინებები"
- "ბიზნეს-ინფორმაცია"
- "%.1f მილში"
- "%.1f კმ-ში"
- "%1$s, %2$s"
- "%1$s — %2$s"
- "%1$s, %2$s"
- "იხსნება ხვალ %s-ზე"
- "იხსნება დღეს %s-ზე"
- "იკეტება %s-ზე"
- "დაიკეტა დღეს %s-ზე"
- "ახლა ღიაა"
- "ახლა დაკეტილია"
- "სავარაუდ.სპამ.აბონ."
- "ზარი დასრულდა %1$s"
- "ამ ნომრიდან პირველად დაგირეკეს."
- "ეჭვი გვაქვს, რომ ეს ზარი სპამია."
- "დაბლოკ./სპამ.შეტყობ."
- "კონტაქტის დამატება"
- "არ არის სპამი"
-
diff --git a/InCallUI/res/values-kk/strings.xml b/InCallUI/res/values-kk/strings.xml
deleted file mode 100644
index 07ea6fb7824f11f1675a76c08f4b7e2af4d7d12e..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-kk/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Телефон"
- "Күтуде"
- "Белгісіз"
- "Жеке нөмір"
- "Автомат-телефон"
- "Конференциялық қоңырау"
- "Қоңырау үзілді"
- "Динамик"
- "Телефон құлаққабы"
- "Сымды құлақаспап жинағы"
- "Bluetooth"
- "Келесі әуендер жіберілсін бе?\n"
- "Жіберу әуендері\n"
- "Жіберу"
- "Иә"
- "Жоқ"
- "Қойылмалы таңбаны келесі таңбамен алмастыру"
- "%s конференциялық қоңырауы"
- "Дауыстық пошта нөмірі"
- "Терілуде"
- "Қайта терілуде"
- "Конференциялық қоңырау"
- "Кіріс қоңырау"
- "Кіріс жұмыс қоңырауы"
- "Қоңырау аяқталды"
- "Күтуде"
- "Қоңырау аяқталуда"
- "Қоңырауда"
- "Mенің нөмірім — %s"
- "Бейне қосылуда"
- "Бейне қоңырау"
- "Бейне сұралуда"
- "Бейне қоңырауға қосылу мүмкін емес"
- "Бейне сұрауы қабылданбады"
- "Кері қоңырау шалу нөміріңіз\n %1$s"
- "Төтенше кері қоңырау шалу нөміріңіз\n %1$s"
- "Терілуде"
- "Өткізіп алған қоңырау"
- "Өткізіп алған қоңыраулар"
- "%s өткізіп алған қоңырау"
- "%s қоңырауы өткізіп алынған"
- "Ағымдағы қоңырау"
- "Ағымдағы жұмыс қоңырауы"
- "Ағымдағы Wi-Fi қоңырауы"
- "Ағымдағы Wi-Fi жұмыс қоңырауы"
- "Күтуде"
- "Кіріс қоңырау"
- "Кіріс жұмыс қоңырауы"
- "Кіріс Wi-Fi қоңырауы"
- "Кіріс Wi-Fi жұмыс қоңырауы"
- "Кіріс бейне қоңырау"
- "Кіріс қоңырауы спам болуы мүмкін"
- "Кіріс бейне сұрау"
- "Жаңа дауыстық хабар"
- "Жаңа дауыстық хабар (%d)"
- "%s нөмірін теру"
- "Дауыстық пошта нөмірі белгісіз"
- "Қызмет жоқ"
- "Таңдалған (%s) желісі қол жетімді емес"
- "Жауап"
- "Қоңырауды аяқтау"
- "Бейне"
- "Дауыс"
- "Қабылдау"
- "Қабылдамау"
- "Кері қоңырау шалу"
- "Хабар"
- "Қоңырау басқа құрылғыдан шалынуда"
- "Қоңырауды басқа құрылғыға бағыттау"
- "Қоңырау шалу үшін алдымен ұшақ режимін өшіріңіз."
- "Желіде тіркелмеген."
- "Ұялы желі қол жетімді емес."
- "Қоңырау шалу үшін жарамды нөмірді енгізіңіз."
- "Қоңырау шалу мүмкін емес."
- "MMI қатарын бастау…"
- "Қызметке қолдау көрсетілмейді."
- "Қоңырауларды ауыстыру мүмкін емес."
- "Қоңырауды бөлу мүмкін емес."
- "Тасымалдау мүмкін емес."
- "Конференция мүмкін емес."
- "Қоңырауды қабылдамау мүмкін емес."
- "Қоңырау(лар)ды босату мүмкін емес."
- "SIP қоңырауы"
- "Төтенше қоңырау"
- "Радио қосылуда…"
- "Қызмет жоқ. Әрекет қайталануда…"
- "Қоңырау шалу мүмкін емес. %s төтенше нөмір емес."
- "Қоңырау шалу мүмкін емес. Төтенше нөмірді теріңіз."
- "Теру үшін пернетақтаны пайдалану"
- "Қоңырауды ұстап тұру"
- "Қоңырауды жалғастыру"
- "Қоңырауды аяқтау"
- "Теру тақтасын көрсету"
- "Теру тақтасын жасыру"
- "Дыбысты өшіру"
- "Дыбысын қосу"
- "Қоңырау қосу"
- "Қоңырауларды біріктіру"
- "Алмастыру"
- "Қоңырауларды басқару"
- "Конференциялық қоңырауды басқару"
- "Конференциялық қоңырау"
- "Басқару"
- "Aудио"
- "Бейне қоңырау"
- "Дауыстық қоңырауға өзгерту"
- "Камераны ауыстыру"
- "Камераны қосу"
- "Камераны өшіру"
- "Қосымша опциялар"
- "Ойнатқыш іске қосылды"
- "Ойнатқыш тоқтатылды"
- "Камера дайын емес"
- "Камера дайын"
- "Белгісіз қоңырау сеансы оқиғасы"
- "Қызмет"
- "Реттеу"
- "<Орнатылмаған>"
- "Басқа қоңырау параметрлері"
- "%s арқылы қоңырау шалу"
- "%s арқылы кіріс"
- "контакт фотосуреті"
- "жеке қоңырауға ауысу"
- "контакт таңдау"
- "Өзіңіздікін жазыңыз..."
- "Бас тарту"
- "Жіберу"
- "Жауап"
- "SMS жіберу"
- "Қабылдамау"
- "Бейне қоңырауға жауап беру"
- "Аудио қоңырауға жауап беру"
- "Бейне сұрауды қабылдау"
- "Бейне сұрауды қабылдамау"
- "Бейне тасымалдау сұрауын қабылдау"
- "Бейне тасымалдау сұрауын қабылдамау"
- "Бейне алу сұрауын қабылдау"
- "Бейне алу сұрауын қабылдамау"
- "%s үшін жоғары сырғытыңыз."
- "%s үшін сол жаққа сырғытыңыз."
- "%s үшін оң жаққа сырғытыңыз."
- "%s үшін төмен сырғытыңыз."
- "Діріл"
- "Діріл"
- "Дыбыс"
- "Әдепкі дыбыс (%1$s)"
- "Телефонның қоңырау әуені"
- "Шылдырлағанда дірілдеу"
- "Қоңырау әуені және діріл"
- "Конференциялық қоңырауды басқару"
- "Төтенше нөмір"
- "Профиль фотосуреті"
- "Камераны өшіру"
- "%s арқылы"
- "Ескертпе жіберілді"
- "Жақындағы хабарлар"
- "Іскери ақпарат"
- "%.1f миля қашықтықта"
- "%.1f км қашықтықта"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Ертең %s уақытында ашылады"
- "Бүгін %s уақытында ашылады"
- "%s уақытында жабылады"
- "Бүгін %s уақытында жабық"
- "Қазір ашық"
- "Қазір жабық"
- "Спам қоңырау шалушы болуы мүмкін"
- "Қоңырау аяқталды (%1$s)"
- "Бұл нөмірдің сізге алғашқы қоңырау шалуы."
- "Бұл қоңырау спамер деп күдіктенеміз."
- "Бөгеу/спамға жіберу"
- "Контакт қосу"
- "Спам емес"
-
diff --git a/InCallUI/res/values-km/strings.xml b/InCallUI/res/values-km/strings.xml
deleted file mode 100644
index 7a31d8933967b4ef4811ce21f2f2098172e7cb4f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-km/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ទូរស័ព្ទ"
- "រង់ចាំ"
- "មិនស្គាល់"
- "លេខឯកជន"
- "ទូរស័ព្ទសាធារណៈ"
- "ការហៅជាក្រុម"
- "ការហៅទូរស័ព្ទបានដាក់ចុះ"
- "ឧបករណ៍បំពងសម្លេង"
- "អូប៉ាល័រសំឡេងទូរស័ព្ទ"
- "កាសមានខ្សែ"
- "ប៊្លូធូស"
- "ផ្ញើសំឡេងដូចខាងក្រោមឬ?\n"
- "ផ្ញើសំឡេង \n"
- "ផ្ញើ"
- "បាទ/ចាស"
- "ទេ"
- "ជំនួសតួអក្សរជំនួសដោយ"
- "ការហៅជាក្រុម %s"
- "លេខសារជាសំឡេង"
- "កំពុងហៅ"
- "ការចុចហៅឡើងវិញ"
- "ការហៅជាក្រុម"
- "ការហៅចូល"
- "កំពុងហៅចូលពីកន្លែងការងារ"
- "បានបញ្ចប់ការហៅ"
- "រង់ចាំ"
- "បញ្ចប់ការសន្ទនា"
- "កំពុងហៅ"
- "លេខរបស់ខ្ញុំគឺ %s"
- "ភ្ជាប់វីដេអូ"
- "ហៅជាវីដេអូ"
- "ស្នើវីដេអូ"
- "មិនអាចភ្ជាប់ការហៅជាវីដេអូបានទេ"
- "បានបដិសេធសំណើហៅជាវីដេអូ"
- "លេខហៅទៅវិញរបស់អ្នក\n%1$s"
- "លេខហៅទៅវិញពេលអាសន្នរបស់អ្នក\n %1$s"
- "កំពុងហៅ"
- "ខកខានទទួល"
- "ខកខានទទួល"
- "ខកខានទទួល %s ដង"
- "ខកខានទទួលពី %s"
- "កំពុងបន្តការហៅ"
- "ការហៅពីកន្លែងការងារកំពុងដំណើរការ"
- "ការហៅតាម Wi-Fi កំពុងបន្ត"
- "ការហៅតាម Wi-Fi ពីកន្លែងការងារកំពុងដំណើរការ"
- "រង់ចាំ"
- "ការហៅចូល"
- "កំពុងហៅចូលពីកន្លែងការងារ"
- "មានការហៅចូលតាម Wi-Fi"
- "កំពុងហៅចូលពីកន្លែងការងារតាម Wi-Fi"
- "ការហៅចូលជាវីដេអូ"
- "ការហៅបន្លំចូលដែលសង្ស័យ"
- "សំណើការហៅជាវីដេអូចូល"
- "សារជាសំឡេងថ្មី"
- "សារជាសំឡេងថ្មី (%d)"
- "ហៅ %s"
- "លេខសារជាសំឡេងមិនស្គាល់"
- "គ្មានសេវាទេ"
- "បណ្ដាញដែលបានជ្រើស ( %s ) មិនអាចប្រើបានទេ"
- "ឆ្លើយតប"
- "បញ្ចប់ការសន្ទនា"
- "វីដេអូ"
- "សំឡេង"
- "ព្រមទទួល"
- "បដិសេធ"
- "ហៅទៅវិញ"
- "សារ"
- "ការហៅកំពុងដំណើរការលើឧបករណ៍ផ្សេង"
- "ផ្ទេរការហៅ"
- "ដើម្បីកំណត់ការហៅ សូមបិទរបៀបពេលជិះយន្តហោះជាមុនសិន"
- "មិនបានចុះឈ្មោះនៅលើបណ្ដាញទេ"
- "បណ្ដាញចល័តមិនអាចប្រើបានទេ"
- "ដើម្បីធ្វើការហៅ សូមបញ្ចូលលេខដែលត្រឹមត្រូវ"
- "មិនអាចហៅបានទេ"
- "កំពុងចាប់ផ្តើមលំដាប់ MMI…"
- "សេវាកម្មមិនត្រូវបានគាំទ្រទេ"
- "មិនអាចប្តូរការហៅបានទេ"
- "មិនអាចបំបែកការហៅបានទេ"
- "មិនអាចផ្ទេរបានទេ"
- "មិនអាចធ្វើការហៅជាក្រុមបានទេ"
- "មិនអាចបដិសេធការហៅបានទេ"
- "មិនអាចធ្វើការហៅបានទេ"
- "ការហៅ SIP"
- "ការហៅពេលអាសន្ន"
- "កំពុងបើកវិទ្យុ…"
- "គ្មានសេវាទេ សូមព្យាយាមម្តង…"
- "មិនអាចហៅបានទេ។ %s មិនមែនជាលេខអាសន្នទេ"
- "មិនអាចហៅបានទេ សូមចុចហៅលេខអាសន្ន"
- "ប្រើក្ដារចុច ដើម្បីចុចលេខ"
- "រង់ចាំការហៅ"
- "បន្តការហៅ"
- "បញ្ចប់ការហៅ"
- "បង្ហាញបន្ទះលេខ"
- "លាក់បន្ទះលេខ"
- "បិទ"
- "បើកសំឡេង"
- "បន្ថែមការហៅ"
- "បញ្ចូលការហៅចូលគ្នា"
- "ប្ដូរ"
- "គ្រប់គ្រងការហៅ"
- "គ្រប់គ្រងការហៅជាក្រុម"
- "ការហៅជាសន្និសិទ"
- "គ្រប់គ្រង"
- "សំឡេង"
- "ហៅជាវីដេអូ"
- "ប្ដូរទៅការហៅជាសំឡេង"
- "ប្ដូរកាមេរ៉ា"
- "បើកកាមេរ៉ា"
- "បិទកាមេរ៉ា"
- "ជម្រើសច្រើនទៀត"
- "អ្នកលេងបានចាប់ផ្តើម"
- "អ្នកលេងបានឈប់"
- "កាមេរ៉ាមិនទាន់ត្រៀមរួចរាល់ទេ"
- "កាមេរ៉ាត្រៀមរួចរាល់ហើយ"
- "ព្រឹត្តិការណ៍វេននៃការហៅមិនស្គាល់"
- "សេវាកម្ម"
- "ដំឡើង"
- "<មិនបានកំណត់>"
- "កំណត់ការហៅផ្សេងទៀត"
- "ហៅតាមរយៈ %s"
- "ចូលតាមរយៈ %s"
- "រូបថតទំនាក់ទំនង"
- "ចូលជាលក្ខណៈឯកជន"
- "ជ្រើសទំនាក់ទំនង"
- "សរសេរដោយខ្លួនអ្នកផ្ទាល់..."
- "បោះបង់"
- "ផ្ញើ"
- "ឆ្លើយតប"
- "ផ្ញើសារ SMS"
- "បដិសេធ"
- "ឆ្លើយតបជាការហៅជាវីដេអូ"
- "ឆ្លើយតបជាការហៅជាសំឡេង"
- "ទទួលយកសំណើវីដេអូ"
- "ទទួលយកសំណើវីដេអូ"
- "ទទួលយកសំណើបញ្ជូនជាវីដេអូ"
- "បដិសេធសំណើបញ្ជូនជាវីដេអូ"
- "ទទួលយកសំណើទទួលជាវីដេអូ"
- "បដិសេធសំណើទទួលជាវីដេអូ"
- "រុញឡើងលើដើម្បី %s"
- "រុញទៅឆ្វេងដើម្បី %s"
- "រុញទៅស្ដាំដើម្បី %s"
- "រុញចុះក្រោមដើម្បី %s"
- "ញ័រ"
- "ញ័រ"
- "សំឡេង"
- "សំឡេងលំនាំដើម (%1$s)"
- "សំឡេងរោទ៍ទូរស័ព្ទ"
- "ញ័រពេលរោទ៍"
- "សំឡេងរោទ៍ និងញ័រ"
- "គ្រប់គ្រងការហៅជាក្រុម"
- "លេខអាសន្ន"
- "រូបថតប្រវត្តិរូប"
- "បិទកាមេរ៉ា"
- "តាមរយៈ %s"
- "បានផ្ញើចំណាំ"
- "សារថ្មីៗ"
- "ព័ត៌មានធុរកិច្ច"
- "ចម្ងាយ %.1f ម៉ាយល៍"
- "ចម្ងាយ %.1f គម"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "បើកថ្ងៃស្អែកនៅម៉ោង %s"
- "បើកថ្ងៃនេះនៅម៉ោង %s"
- "បិទនៅម៉ោង %s"
- "បានបិទថ្ងៃនេះនៅម៉ោង %s"
- "បើកឥឡូវនេះ"
- "បិទឥឡូវនេះ"
- "អ្នកហៅបន្លំដែលសង្ស័យ"
- "ការហៅបានបញ្ចប់ %1$s"
- "នេះគឺជាលើកដំបូងដែលលេខនេះបានហៅមកអ្នក។"
- "យើងបានសង្ស័យថាការហៅនេះជាសារឥតបានការ។"
- "រារាំង/រាយការណ៍សារឥតបានការ"
- "បញ្ចូលទំនាក់ទំនង"
- "មិនមែនសារឥតបានការ"
-
diff --git a/InCallUI/res/values-kn/strings.xml b/InCallUI/res/values-kn/strings.xml
deleted file mode 100644
index 441f6e189274eac322a3c59ea100c1c5c667d64d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-kn/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ಫೋನ್"
- "ತಡೆಹಿಡಿಯಲಾಗಿದೆ"
- "ಅಪರಿಚಿತ"
- "ಖಾಸಗಿ ಸಂಖ್ಯೆ"
- "ಪೇಫೋನ್"
- "ಕಾನ್ಫರೆನ್ಸ್ ಕರೆ"
- "ಕರೆಯನ್ನು ಬಿಡಲಾಗಿದೆ"
- "ಸ್ಪೀಕರ್"
- "ಹ್ಯಾಂಡ್ಸೆಟ್ ಇಯರ್ಪೀಸ್"
- "ವೈರ್ಡ್ ಹೆಡ್ಸೆಟ್"
- "ಬ್ಲೂಟೂತ್"
- "ಕೆಳಗಿನ ಟೋನ್ಗಳನ್ನು ಕಳುಹಿಸುವುದೇ?\n"
- "ಟೋನ್ಗಳನ್ನು ಕಳುಹಿಸಲಾಗುತ್ತಿದೆ\n"
- "ಕಳುಹಿಸು"
- "ಹೌದು"
- "ಇಲ್ಲ"
- "ಇದರೊಂದಿಗೆ ವಿಶೇಷ ಅಕ್ಷರಗಳನ್ನು ಸ್ಥಳಾಂತರಿಸು"
- "ಕಾನ್ಫರೆನ್ಸ್ ಕರೆ %s"
- "ಧ್ವನಿಮೇಲ್ ಸಂಖ್ಯೆ"
- "ಡಯಲ್ ಮಾಡಲಾಗುತ್ತಿದೆ"
- "ಮರು ಡಯಲ್ ಮಾಡಲಾಗುತ್ತಿದೆ"
- "ಕಾನ್ಫರೆನ್ಸ್ ಕರೆ"
- "ಒಳಬರುವ ಕರೆ"
- "ಒಳಬರುವ ಕೆಲಸದ ಕರೆ"
- "ಕರೆ ಅಂತ್ಯಗೊಂಡಿದೆ"
- "ತಡೆಹಿಡಿಯಲಾಗಿದೆ"
- "ಹ್ಯಾಂಗ್ ಮಾಡಲಾಗುತ್ತಿದೆ"
- "ಕರೆಯಲ್ಲಿ"
- "ನನ್ನ ಸಂಖ್ಯೆ %s"
- "ವೀಡಿಯೊ ಸಂಪರ್ಕಪಡಿಸಲಾಗುತ್ತಿದೆ"
- "ವೀಡಿಯೊ ಕರೆ"
- "ವೀಡಿಯೊ ವಿನಂತಿಸಲಾಗುತ್ತಿದೆ"
- "ವೀಡಿಯೊ ಕರೆಯನ್ನು ಸಂಪರ್ಕಪಡಿಸಲಾಗುವುದಿಲ್ಲ"
- "ವೀಡಿಯೊ ವಿನಂತಿಯನ್ನು ತಿರಸ್ಕರಿಸಲಾಗಿದೆ"
- "ನಿಮ್ಮ ಮರಳಿಕರೆ ಮಾಡುವ ಸಂಖ್ಯೆ\n %1$s"
- "ನಿಮ್ಮ ತುರ್ತು ಮರಳಿಕರೆ ಮಾಡುವ ಸಂಖ್ಯೆ\n %1$s"
- "ಡಯಲ್ ಮಾಡಲಾಗುತ್ತಿದೆ"
- "ಮಿಸ್ಡ್ ಕಾಲ್"
- "ಮಿಸ್ಡ್ ಕಾಲ್ಗಳು"
- "%s ಮಿಸ್ಡ್ ಕಾಲ್ಗಳು"
- "%s ಅವರಿಂದ ಮಿಸ್ಡ್ ಕಾಲ್"
- "ಚಾಲ್ತಿಯಲ್ಲಿರುವ ಕರೆ"
- "ಚಾಲ್ತಿಯಲ್ಲಿರುವ ಕೆಲಸದ ಕರೆ"
- "ಚಾಲ್ತಿಯಲ್ಲಿರುವ ವೈ-ಫೈ ಕರೆ"
- "ಚಾಲ್ತಿಯಲ್ಲಿರುವ ವೈ-ಫೈ ಕೆಲಸದ ಕರೆ"
- "ತಡೆಹಿಡಿಯಲಾಗಿದೆ"
- "ಒಳಬರುವ ಕರೆ"
- "ಒಳಬರುವ ಕೆಲಸದ ಕರೆ"
- "ಒಳಬರುವ ವೈ-ಫೈ ಕರೆ"
- "ಒಳಬರುವ ವೈ-ಫೈ ಕೆಲಸದ ಕರೆ"
- "ಒಳಬರುವ ವೀಡಿಯೊ ಕರೆ"
- "ಒಳಬರುವ ಶಂಕಿತ ಸ್ಪ್ಯಾಮ್ ಕರೆ"
- "ಒಳಬರುವ ವೀಡಿಯೊ ವಿನಂತಿ"
- "ಹೊಸ ಧ್ವನಿಮೇಲ್"
- "ಹೊಸ ಧ್ವನಿಮೇಲ್ (%d)"
- "%s ಗೆ ಡಯಲ್ ಮಾಡು"
- "ಅಪರಿಚಿತ ಧ್ವನಿಮೇಲ್ ಸಂಖ್ಯೆ"
- "ಸೇವೆ ಇಲ್ಲ"
- "ಆಯ್ಕೆಮಾಡಿದ (%s) ನೆಟ್ವರ್ಕ್ ಲಭ್ಯವಿಲ್ಲ"
- "ಉತ್ತರ"
- "ಹ್ಯಾಂಗ್ ಅಪ್"
- "ವೀಡಿಯೊ"
- "ಧ್ವನಿ"
- "ಸಮ್ಮತಿಸು"
- "ವಜಾಗೊಳಿಸಿ"
- "ಮರಳಿ ಕರೆ"
- "ಸಂದೇಶ"
- "ಮತ್ತೊಂದು ಸಾಧನದಲ್ಲಿ ಚಾಲ್ತಿಯಲ್ಲಿರುವ ಕರೆ"
- "ಕರೆ ವರ್ಗಾಯಿಸಿ"
- "ಕರೆ ಮಾಡಲು, ಮೊದಲು ಏರ್ಪ್ಲೇನ್ ಮೋಡ್ ಆಫ್ ಮಾಡಿ."
- "ನೆಟ್ವರ್ಕ್ನಲ್ಲಿ ಇನ್ನೂ ನೋಂದಣಿಯಾಗಿಲ್ಲ."
- "ಸೆಲ್ಯುಲಾರ್ ನೆಟ್ವರ್ಕ್ ಲಭ್ಯವಿಲ್ಲ."
- "ಕರೆಯನ್ನು ಮಾಡಲು, ಮಾನ್ಯವಾದ ಸಂಖ್ಯೆಯನ್ನು ನಮೂದಿಸಿ."
- "ಕರೆ ಮಾಡಲು ಸಾಧ್ಯವಿಲ್ಲ."
- "MMI ಅನುಕ್ರಮ ಪ್ರಾರಂಭವಾಗುತ್ತಿದೆ…"
- "ಸೇವೆ ಬೆಂಬಲಿತವಾಗಿಲ್ಲ."
- "ಕರೆಗಳನ್ನು ಬದಲಾಯಿಸಲು ಸಾಧ್ಯವಿಲ್ಲ."
- "ಕರೆಯನ್ನು ಪ್ರತ್ಯೇಕಿಸಲು ಸಾಧ್ಯವಿಲ್ಲ."
- "ವರ್ಗಾಯಿಸಲು ಸಾಧ್ಯವಿಲ್ಲ."
- "ಕಾನ್ಫರೆನ್ಸ್ ಮಾಡಲು ಸಾಧ್ಯವಿಲ್ಲ."
- "ಕರೆ ತಿರಸ್ಕರಿಸಲಾಗುವುದಿಲ್ಲ."
- "ಕರೆ(ಗಳು) ಬಿಡುಗಡೆ ಮಾಡಲು ಸಾಧ್ಯವಿಲ್ಲ."
- "SIP ಕರೆ"
- "ತುರ್ತು ಕರೆ"
- "ರೇಡಿಯೋ ಆನ್ ಮಾಡಲಾಗುತ್ತಿದೆ…"
- "ಯಾವುದೇ ಸೇವೆ ಇಲ್ಲ. ಮತ್ತೆ ಪ್ರಯತ್ನಿಸಲಾಗುತ್ತಿದೆ..."
- "ಕರೆ ಮಾಡಲು ಸಾಧ್ಯವಿಲ್ಲ. %s ತುರ್ತು ಸಂಖ್ಯೆಯಲ್ಲ."
- "ಕರೆ ಮಾಡಲು ಸಾಧ್ಯವಿಲ್ಲ. ತುರ್ತು ಸಂಖ್ಯೆಯನ್ನು ಡಯಲ್ ಮಾಡಿ."
- "ಡಯಲ್ ಮಾಡಲು ಕೀಬೋರ್ಡ್ ಬಳಸಿ"
- "ಕರೆಯನ್ನು ಹೋಲ್ಡ್ ಮಾಡು"
- "ಕರೆಯನ್ನು ಮುಂದುವರಿಸಿ"
- "ಕರೆ ಅಂತ್ಯಗೊಳಿಸಿ"
- "ಡಯಲ್ಪ್ಯಾಡ್ ತೋರಿಸು"
- "ಡಯಲ್ಪ್ಯಾಡ್ ಮರೆಮಾಡು"
- "ಮ್ಯೂಟ್"
- "ಅನ್ಮ್ಯೂಟ್"
- "ಕರೆಯನ್ನು ಸೇರಿಸು"
- "ಕರೆಗಳನ್ನು ವಿಲೀನಗೊಳಿಸು"
- "ಸ್ವ್ಯಾಪ್ ಮಾಡು"
- "ಕರೆಗಳನ್ನು ನಿರ್ವಹಿಸಿ"
- "ಕಾನ್ಫರೆನ್ಸ್ ಕರೆಯನ್ನು ನಿರ್ವಹಿಸಿ"
- "ಕಾನ್ಫರೆನ್ಸ್ ಕರೆ"
- "ನಿರ್ವಹಿಸು"
- "ಆಡಿಯೊ"
- "ವೀಡಿಯೊ ಕರೆ"
- "ಧ್ವನಿ ಕರೆಗೆ ಬದಲಾಯಿಸಿ"
- "ಕ್ಯಾಮರಾ ಬದಲಿಸಿ"
- "ಕ್ಯಾಮರಾ ಆನ್ ಮಾಡಿ"
- "ಕ್ಯಾಮರಾ ಆಫ್ ಮಾಡಿ"
- "ಇನ್ನಷ್ಟು ಆಯ್ಕೆಗಳು"
- "ಪ್ಲೇಯರ್ ಪ್ರಾರಂಭವಾಗಿದೆ"
- "ಪ್ಲೇಯರ್ ನಿಲ್ಲಿಸಲಾಗಿದೆ"
- "ಕ್ಯಾಮರಾ ಸಿದ್ಧವಾಗಿಲ್ಲ"
- "ಕ್ಯಾಮರಾ ಸಿದ್ಧವಾಗಿದೆ"
- "ಅಪರಿಚಿತ ಕರೆಯ ಸೆಶನ್ ಈವೆಂಟ್"
- "ಸೇವೆ"
- "ಸೆಟಪ್"
- "<ಹೊಂದಿಸಿಲ್ಲ>"
- "ಇತರ ಕರೆ ಸೆಟ್ಟಿಂಗ್ಗಳು"
- "%s ಮೂಲಕ ಕರೆ ಮಾಡಲಾಗುತ್ತಿದೆ"
- "%s ಮೂಲಕ ಒಳಬರುತ್ತಿರುವ ಕರೆ"
- "ಸಂಪರ್ಕ ಫೋಟೋ"
- "ಖಾಸಗಿಯಾಗಿ ಹೋಗಿ"
- "ಸಂಪರ್ಕವನ್ನು ಆಯ್ಕೆಮಾಡಿ"
- "ನಿಮ್ಮ ಸ್ವಂತದ್ದನ್ನು ಬರೆಯಿರಿ..."
- "ರದ್ದುಮಾಡಿ"
- "ಕಳುಹಿಸು"
- "ಉತ್ತರ"
- "SMS ಕಳುಹಿಸಿ"
- "ನಿರಾಕರಿಸು"
- "ವೀಡಿಯೊ ಕರೆ ರೂಪದಲ್ಲಿ ಉತ್ತರಿಸಿ"
- "ಆಡಿಯೊ ಕರೆಯಂತೆ ಉತ್ತರಿಸಿ"
- "ವೀಡಿಯೊ ವಿನಂತಿ ಒಪ್ಪಿಕೊಳ್ಳು"
- "ವೀಡಿಯೊ ವಿನಂತಿ ತಿರಸ್ಕರಿಸು"
- "ವೀಡಿಯೊ ಪ್ರಸಾರ ವಿನಂತಿ ಸಮ್ಮತಿಸಿ"
- "ವೀಡಿಯೊ ಪ್ರಸಾರ ವಿನಂತಿ ತಿರಸ್ಕರಿಸಿ"
- "ವೀಡಿಯೊ ಸ್ವೀಕರಿಸುವಿಕೆ ವಿನಂತಿ ಸಮ್ಮತಿಸಿ"
- "ವೀಡಿಯೊ ಸ್ವೀಕರಿಸುವಿಕೆ ವಿನಂತಿ ತಿರಸ್ಕರಿಸಿ"
- "%s ಗೆ ಮೇಲಕ್ಕೆ ಸ್ಲೈಡ್ ಮಾಡಿ."
- "%s ಗೆ ಎಡಕ್ಕೆ ಸ್ಲೈಡ್ ಮಾಡಿ."
- "%s ಗೆ ಬಲಕ್ಕೆ ಸ್ಲೈಡ್ ಮಾಡಿ."
- "%s ಗೆ ಕೆಳಕ್ಕೆ ಸ್ಲೈಡ್ ಮಾಡಿ."
- "ವೈಬ್ರೇಟ್"
- "ವೈಬ್ರೇಟ್"
- "ಶಬ್ದ"
- "ಡಿಫಾಲ್ಟ್ ಧ್ವನಿ (%1$s)"
- "ಫೋನ್ ರಿಂಗ್ಟೋನ್"
- "ರಿಂಗ್ ಆಗುವಾಗ ವೈಬ್ರೇಟ್ ಆಗು"
- "ರಿಂಗ್ಟೋನ್ ಮತ್ತು ವೈಬ್ರೇಟ್"
- "ಕಾನ್ಫರೆನ್ಸ್ ಕರೆಯನ್ನು ನಿರ್ವಹಿಸಿ"
- "ತುರ್ತು ಸಂಖ್ಯೆ"
- "ಪ್ರೊಫೈಲ್ ಫೋಟೋ"
- "ಕ್ಯಾಮರಾ ಆಫ್"
- "%s ಮೂಲಕ"
- "ಟಿಪ್ಪಣಿ ಕಳುಹಿಸಲಾಗಿದೆ"
- "ಇತ್ತೀಚಿನ ಸಂದೇಶಗಳು"
- "ವ್ಯಾಪಾರ ಮಾಹಿತಿ"
- "%.1f ಮೈಲು ದೂರ"
- "%.1f ಕಿಮೀ ದೂರ"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "ನಾಳೆ %s ಗಂಟೆಗೆ ತೆರೆಯುತ್ತದೆ"
- "ಇಂದು %s ಗಂಟೆಗೆ ತೆರೆಯುತ್ತದೆ"
- "%s ಗಂಟೆಗೆ ಮುಚ್ಚಲಾಗಿದೆ"
- "ಇಂದು %s ಗಂಟೆಗೆ ಮುಚ್ಚಲಾಗಿದೆ"
- "ಇದೀಗ ತೆರೆಯಲಾಗಿದೆ"
- "ಇದೀಗ ಮುಚ್ಚಲಾಗಿದೆ"
- "ಶಂಕಿತ ಸ್ಪ್ಯಾಮ್ ಕರೆದಾರರು"
- "ಕರೆ ಮುಕ್ತಾಯಗೊಂಡಿದೆ %1$s"
- "ಇದೇ ಮೊದಲ ಬಾರಿಗೆ ಈ ಸಂಖ್ಯೆಯಿಂದ ನಿಮಗೆ ಕರೆ ಮಾಡಲಾಗಿದೆ."
- "ನಾವು ಈ ಕರೆಯನ್ನು ಸ್ಪ್ಯಾಮರ್ ಎಂದು ಶಂಕಿಸಿದ್ದೇವೆ."
- "ಸ್ಪ್ಯಾಮ್ ನಿರ್ಬಂಧಿಸು/ವರದಿ ಮಾಡು"
- "ಸಂಪರ್ಕ ಸೇರಿಸಿ"
- "ಸ್ಪ್ಯಾಮ್ ಅಲ್ಲ"
-
diff --git a/InCallUI/res/values-ko/strings.xml b/InCallUI/res/values-ko/strings.xml
deleted file mode 100644
index 973dc46370fdbd4e7555164293f3efc633897ac6..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ko/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "전화"
- "대기 중"
- "알 수 없음"
- "비공개 번호"
- "공중전화"
- "다자간 통화"
- "연락되지 않음"
- "스피커"
- "핸드셋 수화부"
- "유선 헤드셋"
- "블루투스"
- "다음 톤을 보내시겠습니까?\n"
- "신호음 보내기\n"
- "전송"
- "예"
- "아니요"
- "와일드 문자를 다음으로 바꿈:"
- "다자간 통화 %s"
- "음성사서함 번호"
- "전화 거는 중"
- "재다이얼 중"
- "다자간 통화"
- "수신 전화"
- "수신 업무 전화"
- "통화 종료됨"
- "대기 중"
- "전화 끊는 중"
- "통화 중"
- "내 전화번호는 %s입니다."
- "화상 통화 연결 중"
- "화상 통화"
- "화상 통화 요청 중"
- "화상 통화를 연결할 수 없습니다."
- "화상 통화 요청이 거부되었습니다."
- "콜백 번호\n %1$s"
- "긴급 콜백 번호\n%1$s"
- "전화 거는 중"
- "부재중 전화"
- "부재중 전화"
- "부재중 전화 %s통"
- "%s의 부재중 전화"
- "발신 전화"
- "발신 업무 전화"
- "발신 Wi-Fi 전화"
- "발신 Wi-Fi 업무 전화"
- "대기 중"
- "수신 전화"
- "수신 업무 전화"
- "Wi-Fi 수신 전화"
- "수신 Wi-Fi 업무 전화"
- "수신 화상 통화"
- "의심스러운 스팸 발신자로부터 온 전화"
- "수신 화상 통화 요청"
- "새로운 음성사서함"
- "새 음성사서함(%d개)"
- "%s(으)로 전화 걸기"
- "알 수 없는 음성사서함 번호"
- "서비스 불가"
- "선택한 네트워크(%s)를 사용할 수 없음"
- "전화 받기"
- "전화 끊기"
- "화상"
- "음성"
- "수락"
- "해제"
- "전화 걸기"
- "메시지"
- "다른 기기에서 진행 중인 통화"
- "통화 전환"
- "전화를 걸려면 먼저 비행기 모드를 해제하세요."
- "네트워크에서 등록되지 않았습니다."
- "사용 가능한 이동통신망이 없습니다."
- "전화를 걸려면 올바른 번호를 입력하세요."
- "전화를 걸 수 없습니다."
- "MMI 시퀀스 시작 중..."
- "서비스가 지원되지 않습니다."
- "통화를 전환할 수 없습니다."
- "통화를 분리할 수 없습니다."
- "통화를 전환할 수 없습니다."
- "다자간 통화를 이용할 수 없습니다."
- "통화를 거부할 수 없습니다."
- "통화를 끊을 수 없습니다."
- "SIP 통화"
- "긴급 전화"
- "무선을 켜는 중..."
- "서비스를 사용할 수 없습니다. 다시 시도 중..."
- "전화를 걸 수 없습니다. %s은(는) 긴급 번호가 아닙니다."
- "전화를 걸 수 없습니다. 긴급 번호를 사용하세요."
- "키보드를 사용하여 전화 걸기"
- "통화 대기"
- "통화 재개"
- "통화 종료"
- "다이얼패드 표시"
- "다이얼패드 숨기기"
- "음소거"
- "음소거 해제"
- "통화 추가"
- "통화 병합"
- "전환"
- "통화 관리"
- "다자간 통화 관리"
- "다자간 통화"
- "관리"
- "오디오"
- "화상 통화"
- "음성 통화로 변경"
- "카메라 전환"
- "카메라 켜기"
- "카메라 끄기"
- "옵션 더보기"
- "플레이어가 시작되었습니다."
- "플레이어가 중지되었습니다."
- "카메라가 준비되지 않았습니다."
- "카메라가 준비되었습니다."
- "알 수 없는 통화 세션 이벤트"
- "서비스"
- "설정"
- "<설정 안됨>"
- "기타 통화 설정"
- "%s을(를) 통해 걸려온 전화"
- "%s을(를) 통해 걸려온 전화"
- "연락처 사진"
- "비공개로 실행"
- "연락처 선택"
- "나만의 응답 작성…"
- "취소"
- "전송"
- "전화 받기"
- "SMS 보내기"
- "거부"
- "화상 통화로 받기"
- "음성 통화로 받기"
- "화상 통화 요청 수락"
- "화상 통화 요청 거부"
- "화상 통화 전송 요청 허용"
- "화상 통화 전송 요청 거부"
- "화상 통화 수신 요청 허용"
- "화상 통화 수신 요청 거부"
- "%s하려면 위로 슬라이드합니다."
- "%s하려면 왼쪽으로 슬라이드합니다."
- "%s하려면 오른쪽으로 슬라이드합니다."
- "%s하려면 아래로 슬라이드합니다."
- "진동"
- "진동"
- "소리"
- "기본 알림음(%1$s)"
- "전화 벨소리"
- "전화 수신 시 진동"
- "벨소리 및 진동"
- "다자간 통화 관리"
- "비상 전화번호"
- "프로필 사진"
- "카메라 꺼짐"
- "수신 번호: %s"
- "메모가 전송되었습니다."
- "최근 메시지"
- "비즈니스 정보"
- "%.1fmi 거리"
- "%.1fkm 거리"
- "%1$s, %2$s"
- "%1$s~%2$s"
- "%1$s, %2$s"
- "내일 %s에 영업 시작"
- "오늘 %s에 영업 시작"
- "%s에 영업 종료"
- "오늘 %s에 영업 종료됨"
- "영업 중"
- "영업 종료"
- "의심스러운 스팸 발신자"
- "%1$s번으로 끝나는 번호에서 걸려온 전화"
- "이 번호에서 처음으로 걸려온 전화입니다."
- "스팸 전화로 의심됩니다."
- "스팸 차단/신고"
- "연락처 추가"
- "스팸 해제"
-
diff --git a/InCallUI/res/values-ky/strings.xml b/InCallUI/res/values-ky/strings.xml
deleted file mode 100644
index bebdcfde88763ef69d78051697c0dce35ef5e95f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ky/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Телефон"
- "Күтүлүүдө"
- "Белгисиз"
- "Купуя номер"
- "Таксофон"
- "Конференц-чалуу"
- "Чалуу үзүлдү"
- "Катуу сүйлөткүч"
- "Гарнитура"
- "Зымдуу гарнитура"
- "Bluetooth"
- "Төмөнкү номер жөнөтүлсүнбү?\n"
- "Обондор жөнөтүлүүдө\n"
- "Жөнөтүү"
- "Ооба"
- "Жок"
- "Атайын белгини төмөнкүгө алмаштыруу"
- "Конференц-чалуу %s"
- "Үн почтасынын номери"
- "Терилүүдө"
- "Кайра терилүүдө"
- "Конференц-чалуу"
- "Кирүүчү чалуу"
- "Жумуш боюнча чалуу"
- "Чалуу аяктады"
- "Күтүлүүдө"
- "Чалуу аяктоодо"
- "Чалууда"
- "Менин номерим %s"
- "Видео туташтырылууда"
- "Видео чалуу"
- "Видео суралууда"
- "Видео чалууга туташуу мүмкүн болбой жатат"
- "Видео сурам четке кагылды"
- "Кайра чалына турган номер\n %1$s"
- "Өзгөчө кырдаалда кайра чалына турган номер\n %1$s"
- "Терилүүдө"
- "Кабыл алынбаган чалуу"
- "Кабыл алынбаган чалуулар"
- "%s кабыл алынбаган чалуу"
- "%s дегенден кабыл алынбаган чалуу"
- "Учурдагы чалуу"
- "Учурдагы чалуу (жумуш боюнча)"
- "Учурдагы Wi-Fi чалуу"
- "Учурдагы Wi-Fi чалуу (жумуш боюнча)"
- "Күтүлүүдө"
- "Кирүүчү чалуу"
- "Жумуш боюнча чалуу"
- "Кирүүчү Wi-Fi чалуу"
- "Жумуш боюнча келип жаткан Wi-Fi чалуу"
- "Кирүүчү видео чалуу"
- "Келип жаткан чалуу спам окшойт"
- "Кирүүчү видео сурамы"
- "Жаңы үн почтасы"
- "Жаңы үн почтасы (%d)"
- "%s номерин терүү"
- "Үн почтасынын номери белгисиз"
- "Байланыш жок"
- "Тандалган тармак (%s) жеткиликсиз"
- "Жооп берүү"
- "Чалууну бүтүрүү"
- "Видео"
- "Үн"
- "Кабыл алуу"
- "Этибарга албоо"
- "Кайра чалуу"
- "Билдирүү"
- "Башка түзмөктө сүйлөшүп жатасыз"
- "Чалууну бул түзмөккө өткөрүү"
- "Учак режимин өчүрүп туруп чалыңыз."
- "Тармакта катталган эмес."
- "Мобилдик тармак жеткиликтүү эмес."
- "Чалуу үчүн, жарактуу номер киргизиңиз."
- "Чалынбай жатат."
- "MMI кезеги башталууда…"
- "Кызмат колдоого алынбайт."
- "Чалуулар которуштурулбай жатат."
- "Чалуу бөлүнбөй жатат."
- "Өткөрүлбөй жатат."
- "Конференц-чалуу түзүлбөй жатат."
- "Чалуу четке кагылбай жатат."
- "Чалуу (-лар) ажыратылбай жатат."
- "SIP чалуу"
- "Өзгөчө кырдаалда чалуу"
- "Радио күйгүзүлүүдө…"
- "Кызмат жок. Кайра аракет кылууда…"
- "Чалынбай жатат. %s өзгөчө кырдаал номери эмес."
- "Чалынбай жатат. Өзгөчө кырдаал номерин териңиз."
- "Баскычтоп менен териңиз"
- "Чалууну кармап туруу"
- "Чалууну улантуу"
- "Чалууну бүтүрүү"
- "Номер тергичти көрсөтүү"
- "Номер тергичти жашыруу"
- "Үнсүз"
- "Үндү чыгаруу"
- "Чалуу кошуу"
- "Чалууларды бириктирүү"
- "Алмаштыруу"
- "Чалууларды башкаруу"
- "Конференц-чалууну башкаруу"
- "Конференц чалуу"
- "Башкаруу"
- "Аудио"
- "Видео чалуу"
- "Үн чалууга өзгөртүү"
- "Камераны которуштуруу"
- "Камераны күйгүзүү"
- "Камераны өчүрүү"
- "Дагы параметрлер"
- "Ойноткуч башталды"
- "Ойноткуч токтотулду"
- "Камера даяр эмес"
- "Камера даяр"
- "Чалуу сеансынын окуясы белгисиз"
- "Кызмат"
- "Орнотуу"
- "<Коюлган эмес>"
- "Башка чалуу жөндөөлөрү"
- "%s аркылуу чалуу"
- "%s аркылуу келүүдө"
- "байланыштын сүрөтү"
- "купуя режимине өтүү"
- "байланыш тандоо"
- "Сиздин жообуңуз…"
- "Жокко чыгаруу"
- "Жөнөтүү"
- "Жооп берүү"
- "SMS жөнөтүү"
- "Четке кагуу"
- "Видео чалуу түрүндө жооп берүү"
- "Аудио чалуу түрүндө жооп берүү"
- "Видео сурамын кабыл алуу"
- "Видео сурамын четке кагуу"
- "Видео өткөрүү сурамын кабыл алуу"
- "Видео өткөрүү сурамын четке кагуу"
- "Видео алуу сурамын кабыл алуу"
- "Видео алуу сурамын четке кагуу"
- "%s үчүн жогору жылмыштырыңыз."
- "%s үчүн солго жылмыштырыңыз."
- "%s үчүн оңго жылмыштырыңыз."
- "%s үчүн төмөн жылмыштырыңыз."
- "Дирилдөө"
- "Дирилдөө"
- "Үн"
- "Демейки үнү (%1$s)"
- "Телефондун рингтону"
- "Дирилдеп шыңгырасын"
- "Шыңгыр жана дирилдөө"
- "Конференц-чалууну башкаруу"
- "Өзгөчө кырдаал номери"
- "Профилдин сүрөтү"
- "Камера өчүк"
- "%s аркылуу"
- "Билдирүү жөнөтүлдү"
- "Акыркы билдирүүлөр"
- "Компания тууралуу маалымат"
- "%.1f миля алыста"
- "%.1f км алыста"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Эртең саат %s ачылат"
- "Бүгүн саат %s ачылат"
- "Саат %s жабылат"
- "Бүгүн саат %s жабылды"
- "Азыр ачык"
- "Эми жабылды"
- "Спам окшойт"
- "Чалуу %1$s бүттү"
- "Бул номер сизге биринчи жолу чалып жатат."
- "Бул чалуу спам окшойт."
- "Бөгөттөө/спам катары кабарлоо"
- "Байланыш кошуу"
- "Спам эмес"
-
diff --git a/InCallUI/res/values-lo/strings.xml b/InCallUI/res/values-lo/strings.xml
deleted file mode 100644
index 3e7e815209382246de89c825694b464a2b61b234..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-lo/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ໂທລະສັບ"
- "ຖືສາຍລໍຖ້າ"
- "ບໍ່ຮູ້ຈັກ"
- "ເບີສ່ວນຕົວ"
- "ຕູ້ໂທລະສັບສາທາລະນະ"
- "ການປະຊຸມທາງໂທລະສັບ"
- "ສາຍຫຼຸດແລ້ວ"
- "ລຳໂພງ"
- "ຊຸດຫູຟັງ"
- "ຊຸດຫູຟັງແບບມີສາຍ"
- "Bluetooth"
- "ສົ່ງໂທນສຽງຕໍ່ໄປນີ້ບໍ?\n"
- "ກຳລັງສົ່ງໂທນສຽງ\n"
- "ສົ່ງ"
- "ແມ່ນ"
- "ບໍ່"
- "ປ່ຽນແທນ \"ອັກຂະລະຕົວແທນ\" ດ້ວຍ"
- "ການປະຊຸມທາງໂທລະສັບ %s"
- "ເບີຂໍ້ຄວາມສຽງ"
- "ກຳລັງໂທ"
- "ກຳລັງໂທຄືນ"
- "ການປະຊຸມທາງໂທລະສັບ"
- "ສາຍໂທເຂົ້າ"
- "ສາຍໂທເຂົ້າຈາກບ່ອນເຮັດວຽກ"
- "ວາງສາຍແລ້ວ"
- "ຖືສາຍລໍຖ້າ"
- "ກຳລັງວາງສາຍ"
- "ຢູ່ໃນສາຍ"
- "ເບີໂທຂອງຂ້ອຍແມ່ນ %s"
- "ກຳລັງເຊື່ອມຕໍ່ວິດີໂອ"
- "ການໂທວິດີໂອ"
- "ກຳລັງຮ້ອງຂໍການໂທວິດີໂອ"
- "ບໍ່ສາມາດເຊື່ອມຕໍ່ການໂທວິດີໂອໄດ້"
- "ປະຕິເສດການຮ້ອງຂໍການໂທວິດີໂອແລ້ວ"
- "ເບີໂທກັບຂອງທ່ານ\n %1$s"
- "ເບີໂທກັບສຸກເສີນຂອງທ່ານ\n %1$s"
- "ກຳລັງໂທ"
- "ສາຍບໍ່ໄດ້ຮັບ"
- "ສາຍບໍ່ໄດ້ຮັບ"
- "%s ສາຍບໍ່ໄດ້ຮັບ"
- "ສາຍບໍ່ໄດ້ຮັບຈາກ %s"
- "ສາຍກຳລັງໂທ"
- "ສາຍກຳລັງໂທຈາກບ່ອນເຮັດວຽກ"
- "ສາຍກຳລັງໂທຜ່ານ Wi-Fi"
- "ສາຍກຳລັງໂທຜ່ານ Wi-Fi ຈາກບ່ອນເຮັດວຽກ"
- "ຖືສາຍລໍຖ້າ"
- "ສາຍໂທເຂົ້າ"
- "ສາຍໂທເຂົ້າຈາກບ່ອນເຮັດວຽກ"
- "ສາຍໂທເຂົ້າຜ່ານ Wi-Fi"
- "ສາຍໂທເຂົ້າຜ່ານ Wi-Fi ຈາກບ່ອນເຮັດວຽກ"
- "ສາຍໂທວິດີໂອເຂົ້າ"
- "ມີການໂທທີ່ຄາດວ່າເປັນສະແປມໂທເຂົ້າມາ"
- "ຄຳຮ້ອງຂໍວິດີໂອທີ່ເຂົ້າມາ"
- "ຂໍ້ຄວາມສຽງໃໝ່"
- "ຂໍ້ຄວາມສຽງໃໝ່ (%d)"
- "ໂທຫາ %s"
- "ເບີຂໍ້ຄວາມສຽງບໍ່ຮູ້ຈັກ"
- "ບໍ່ມີການບໍລິການ"
- "ເຄືອຂ່າຍທີ່ເລືອກ (%s) ບໍ່ສາມາດໃຊ້ໄດ້"
- "ຮັບສາຍ"
- "ວາງສາຍ"
- "ວິດີໂອ"
- "ສຽງ"
- "ຍອມຮັບ"
- "ປິດໄວ້"
- "ໂທກັບ"
- "ຂໍ້ຄວາມ"
- "ສາຍທີ່ກຳລັງໂທອອກໃນອຸປະກອນອື່ນ"
- "ໂອນສາຍ"
- "ເພື່ອເຮັດການໂທ, ໃຫ້ປິດໂໝດເຮືອບິນກ່ອນ"
- "ບໍ່ໄດ້ລົງທະບຽນໃນເຄືອຂ່າຍ."
- "ບໍ່ມີເຄືອຂ່າຍມືຖືທີ່ໃຊ້ໄດ້."
- "ເພື່ອເຮັດການໂທ, ປ້ອນເບີໂທທີ່ໃຊ້ໄດ້."
- "ບໍ່ສາມາດໂທໄດ້."
- "ກຳລັງເລີ່ມຕົ້ນລຳດັບ MMI..."
- "ບໍ່ຮອງຮັບການບໍລິການ."
- "ບໍ່ສາມາດສະຫຼັບສາຍໂທໄດ້."
- "ບໍ່ສາມາດແຍກສາຍໂທໄດ້."
- "ບໍ່ສາມາດໂອນສາຍໄດ້."
- "ບໍ່ສາມາດປະຊຸມໄດ້."
- "ບໍ່ສາມາດປະຕິເສດສາຍໂທໄດ້."
- "ບໍ່ສາມາດປ່ອຍສາຍໂທໄດ້."
- "ການໂທ SIP"
- "ການໂທສຸກເສີນ"
- "ກຳລັງເປີດວິທະຍຸ"
- "ບໍ່ມີການບໍລິການ. ກຳລັງລອງໃໝ່ອີກ…"
- "ບໍ່ສາມາດໂທໄດ້. %s ບໍ່ແມ່ນເບີໂທສຸກເສີນ."
- "ບໍ່ສາມາດໂທໄດ້. ກົດເບີໂທສຸກເສີນ."
- "ໃຊ້ແປ້ນພິມເພື່ອກົດໂທ"
- "ຖືສາຍ"
- "ສືບຕໍ່ສາຍ"
- "ວາງສາຍ"
- "ສະແດງປຸ່ມກົດ"
- "ເຊື່ອງປຸ່ມກົດ"
- "ປິດສຽງ"
- "ເຊົາປິດສຽງ"
- "ເພີ່ມການໂທ"
- "ລວມສາຍ"
- "ສະຫຼັບ"
- "ຈັດການການໂທ"
- "ຈັດການການປະຊຸມທາງໂທລະສັບ"
- "ການປະຊຸມທາງໂທລະສັບ"
- "ຈັດການ"
- "ສຽງ"
- "ການໂທວິດີໂອ"
- "ປ່ຽນເປັນການໂທດ້ວຍສຽງ"
- "ສັບປ່ຽນກ້ອງ"
- "ເປີດກ້ອງ"
- "ປິດກ້ອງ"
- "ຕົວເລືອກເພີ່ມເຕີມ"
- "ເຄື່ອງຫຼິ້ນເລີ່ມຕົ້ນແລ້ວ"
- "ເຄື່ອງຫຼິ້ນຢຸດແລ້ວ"
- "ກ້ອງຖ່າຍຮູບບໍ່ພ້ອມ"
- "ກ້ອງຖ່າຍຮູບພ້ອມແລ້ວ"
- "ເຫດການເຊສຊັນການໂທບໍ່ຮູ້ຈັກ"
- "ການບໍລິການ"
- "ຕັ້ງຄ່າ"
- "<ບໍ່ໄດ້ຕັ້ງ>"
- "ການຕັ້ງຄ່າການໂທອື່ນ"
- "ກຳລັງໂທຜ່ານ %s"
- "ສາຍໂທເຂົ້າຈາກ %s"
- "ຮູບລາຍຊື່ຜູ້ຕິດຕໍ່"
- "ໃຊ້ແບບສ່ວນຕົວ"
- "ເລືອກລາຍຊື່ຜູ້ຕິດຕໍ່"
- "ຂຽນ...ຂອງທ່ານເອງ"
- "ຍົກເລີກ"
- "ສົ່ງ"
- "ຮັບສາຍ"
- "ສົ່ງ SMS"
- "ປະຕິເສດ"
- "ຮັບສາຍໂທວິດີໂອ"
- "ຮັບສາຍໂທແບບສຽງ"
- "ຍອມຮັບການຂໍວິດີໂອ"
- "ປະຕິເສດການຂໍວິດີໂອ"
- "ຍອມຮັບການຂໍສົ່ງວິດີໂອ"
- "ປະຕິເສດການຂໍສົ່ງວິດີໂອ"
- "ຍອມຮັບການຂໍຮັບວິດີໂອ"
- "ປະຕິເສດການຂໍຮັບວິດີໂອ"
- "ເລື່ອນຂຶ້ນເພື່ອ %s."
- "ເລື່ອນໄປຊ້າຍເພື່ອ %s."
- "ເລື່ອນໄປຂວາເພື່ອ %s."
- "ເລື່ອນລົງເພື່ອ %s."
- "ສັ່ນເຕືອນ"
- "ສັ່ນເຕືອນ"
- "ສຽງ"
- "ສຽງເລີ່ມຕົ້ນ (%1$s)"
- "ຣິງໂທນໂທລະສັບ"
- "ສັ່ນເຕືອນເມື່ອດັງ"
- "ຣິງໂທນ ແລະ ການສັ່ນເຕືອນ"
- "ຈັດການການປະຊຸມທາງໂທລະສັບ"
- "ເບີໂທສຸກເສີນ"
- "ຮູບໂປຣໄຟລ໌"
- "ກ້ອງຖ່າຍຮູບປິດຢູ່"
- "ຜ່ານ %s"
- "ສົ່ງບັນທຶກແລ້ວ"
- "ຂໍ້ຄວາມບໍ່ດົນມານີ້"
- "ຂໍ້ມູນທຸລະກິດ"
- "ຫ່າງອອກໄປ %.1f ໄມລ໌"
- "ຫ່າງອອກໄປ %.1f ກມ"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "ເປີດມື້ອື່ນເວລາ %s"
- "ເປີດມື້ນີ້ເວລາ %s"
- "ປິດເວລາ %s"
- "ປິດແລ້ວມື້ນີ້ເວລາ %s"
- "ດຽວນີ້ເປີດ"
- "ປິດແລ້ວດຽວນີ້"
- "ຄາດວ່າເປັນການໂທສະແປມ"
- "ການໂທສິ້ນສຸດແລ້ວ %1$s"
- "ນີ້ເປັນເທື່ອທຳອິດທີ່ເບີນີ້ໂທຫາທ່ານ."
- "ພວກເຮົາສົງໄສວ່າເບີໂທນີ້ເປັນສະແປມ."
- "ບລັອກ/ລາຍງານສະແປມ"
- "ເພີ່ມລາຍຊື່ຜູ້ຕິດຕໍ່"
- "ບໍ່ແມ່ນສະແປມ"
-
diff --git a/InCallUI/res/values-lt/strings.xml b/InCallUI/res/values-lt/strings.xml
deleted file mode 100644
index 2d2a701469b71a441385d61c73f383e224246488..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-lt/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefonas"
- "Sulaikyta"
- "Nežinoma"
- "Privatus numeris"
- "Taksofonas"
- "Konferencinis skambutis"
- "Skambutis atmestas"
- "Garsiakalbis"
- "Tel. su gars. prie ausies"
- "Laidinės ausinės"
- "Bluetooth"
- "Siųsti šiuo tonus?\n"
- "Siunčiami tonai\n"
- "Siųsti"
- "Taip"
- "Ne"
- "Pakaitos simbolį pakeisti"
- "Konferencinis skambutis %s"
- "Balso pašto numeris"
- "Renkamas numeris"
- "Numeris renkamas pakartotinai"
- "Konferencinis skambutis"
- "Gaunamasis skambutis"
- "Gaunamasis darbo skambutis"
- "Skambutis baigtas"
- "Sulaikyta"
- "Baigiamas pokalbis"
- "Dalyvauju skambutyje"
- "Mano numeris: %s"
- "Prisijungiama prie vaizdo skambučio"
- "Vaizdo skambutis"
- "Pateikiama vaizdo skambučio užklausa"
- "Nepavyko prijungti vaizdo įrašo skambučio"
- "Vaizdo įrašo užklausa atmesta"
- "Atskambinimo numeris\n%1$s"
- "Atskambinimo numeris, kuriuos skambina pagalbos tarnyba\n%1$s"
- "Renkamas numeris"
- "Praleistas skambutis"
- "Praleisti skambučiai"
- "Praleistų skambučių: %s"
- "Praleistas skambutis nuo %s"
- "Vykstantis pokalbis"
- "Vykstantis darbo skambutis"
- "Vykstantis „Wi-Fi“ skambutis"
- "Vykstantis „Wi-Fi“ darbo skambutis"
- "Sulaikyta"
- "Gaunamasis skambutis"
- "Gaunamasis darbo skambutis"
- "Gaunamasis „Wi-Fi“ skambutis"
- "Gaunamasis „Wi-Fi“ darbo skambutis"
- "Gaunamas vaizdo skambutis"
- "Gaunamasis įtartinas šlamšto skambutis"
- "Gaunama vaizdo skambučio užklausa"
- "Naujas balso pašto pranešimas"
- "Naujas balso pašto pranešimas (%d)"
- "Rinkti %s"
- "Nežinomas balso pašto numeris"
- "Nėra paslaugos"
- "Pasirinktas tinklas (%s) negalimas"
- "Atsiliepti"
- "Padėti ragelį"
- "Vaizdo įrašas"
- "Balsas"
- "Priimti"
- "Atsisakyti"
- "Perskambinti"
- "Siųsti pranešimą"
- "Kitame įrenginyje vykstantis skambutis"
- "Perkelti skambutį"
- "Jei norite skambinti, išjunkite lėktuvo režimą."
- "Neregistruota tinkle."
- "Korinis tinklas nepasiekiamas"
- "Kad galėtumėte paskambinti, įveskite tinkamą numerį."
- "Nepavyko paskambinti."
- "Paleidžiama MMI seka..."
- "Paslauga nepalaikoma."
- "Nepavyko perjungti skambučių."
- "Nepavyko atskirti skambučio."
- "Nepavyko peradresuoti."
- "Nepavyko sukurti konferencijos."
- "Nepavyko atmesti skambučio."
- "Nepavyko atjungti skamb."
- "SIP skambutis"
- "Skambutis pagalbos numeriu"
- "Įjungiamas radijas…"
- "Nėra ryšio. Bandoma dar kartą…"
- "Nepavyko paskambinti. %s nėra pagalbos numeris."
- "Nepavyko paskambinti. Surinkite pagalbos tarnybos numerį."
- "Naudokite klaviatūrą ir rinkite numerius"
- "Sulaikyti skambutį"
- "Tęsti skambutį"
- "Baigti skambutį"
- "Rodyti skambinimo skydelį"
- "Slėpti skambinimo skydelį"
- "Nutildyti"
- "Įjungti garsą"
- "Pridėti skambutį"
- "Sujungti skambučius"
- "Apkeisti"
- "Valdyti skambučius"
- "Tvarkyti konferencinį skambutį"
- "Konferencinis skambutis"
- "Tvarkyti"
- "Garsas"
- "Vaizdo skambutis"
- "Pakeisti į balso skambutį"
- "Perjungti fotoaparatą"
- "Įjungti fotoaparatą"
- "Išjungti fotoaparatą"
- "Daugiau parinkčių"
- "Leistuvė paleista"
- "Leistuvė sustabdyta"
- "Fotoaparatas neparuoštas"
- "Fotoaparatas paruoštas"
- "Nežinomas skambučio sesijos įvykis"
- "Paslaugos teikėjas"
- "Sąranka"
- "<Nenustatyta>"
- "Kiti skambučio nustatymai"
- "Skambinama naudojantis „%s“ paslaugomis"
- "Gaunama per „%s“"
- "kontakto nuotrauka"
- "naudoti privatų režimą"
- "pasirinkti kontaktą"
- "Sukurkite patys..."
- "Atšaukti"
- "Siųsti"
- "Atsiliepti"
- "Siųsti SMS"
- "Atmesti"
- "Atsiliepti kaip į vaizdo skambutį"
- "Atsiliepti kaip į garso skambutį"
- "Priimti vaizdo įrašo užkl"
- "Atmesti vaizdo įrašo užklausą"
- "Priimti vaizdo įrašo perdavimo užklausą"
- "Atmesti vaizdo įrašo perdavimo užklausą"
- "Priimti vaizdo įrašo gavimo užklausą"
- "Atmesti vaizdo įrašo gavimo užklausą"
- "Slyskite aukštyn link parinkties „%s“."
- "Slyskite į kairę link parinkties „%s“."
- "Slyskite į dešinę link parinkties „%s“."
- "Slyskite žemyn link %s."
- "Vibruoti"
- "Vibruoti"
- "Garsas"
- "Numatytasis garsas (%1$s)"
- "Telefono skambėjimo tonas"
- "Vibruoti, kai skambina"
- "Skambėjimo tonas ir vibracija"
- "Tvarkyti konferencinį skambutį"
- "Pagalbos numeris"
- "Profilio nuotrauka"
- "Fotoaparatas išjungtas"
- "naudojant %s"
- "Užrašas išsiųstas"
- "Naujausi pranešimai"
- "Įmonės informacija"
- "Už %.1f myl."
- "Už %.1f km"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Rytoj atidaroma %s"
- "Šiandien atidaroma %s"
- "Uždaroma %s"
- "Šiandien uždaryta %s"
- "Dabar atidaryta"
- "Dabar uždaryta"
- "Įt. skamb. dėl šl."
- "Skambutis baigtas (%1$s)"
- "Tai pirmas kartas, kai jums buvo skambinama iš šio numerio."
- "Įtarėme, kad šis skambutis yra šlamštas."
- "Bl. / pran. apie šl."
- "Pridėti kontaktą"
- "Ne šlamštas"
-
diff --git a/InCallUI/res/values-lv/strings.xml b/InCallUI/res/values-lv/strings.xml
deleted file mode 100644
index 685ba8b0cfdacdfe1f4103e630183cda78091582..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-lv/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Tālrunis"
- "Aizturēts"
- "Nezināms"
- "Privāts numurs"
- "Maksas tālrunis"
- "Konferences zvans"
- "Zvans tika pārtraukts."
- "Skaļrunis"
- "Auss skaļrunis"
- "Austiņas ar vadu"
- "Bluetooth"
- "Vai sūtīt tālāk norādītos signālus?\n"
- "Sūtīšanas signāli\n"
- "Sūtīt"
- "Jā"
- "Nē"
- "Aizstāt aizstājējzīmi ar:"
- "Konferences zvans: %s"
- "Balss pasta numurs"
- "Notiek numura sastādīšana"
- "Notiek atkārtota zvanīšana"
- "Konferences zvans"
- "Ienākošs zvans"
- "Ienākošs darba zvans"
- "Zvans ir pabeigts"
- "Aizturēts"
- "Notiek klausules nolikšana"
- "Notiek zvans"
- "Mans tālruņa numurs: %s"
- "Notiek video savienojuma izveide"
- "Videozvans"
- "Notiek video pieprasīšana"
- "Nevar veikt videozvanu"
- "Video pieprasījums noraidīts"
- "Jūsu atzvana numurs\n %1$s"
- "Jūsu ārkārtas atzvana numurs\n %1$s"
- "Notiek numura sastādīšana"
- "Neatbildēts zvans"
- "Neatbildēti zvani"
- "%s neatbildēti zvani"
- "Neatbildēts zvans no: %s"
- "Notiekošs zvans"
- "Notiekošs darba zvans"
- "Notiekošs Wi-Fi zvans"
- "Notiekošs darba Wi-Fi zvans"
- "Aizturēts"
- "Ienākošs zvans"
- "Ienākošs darba zvans"
- "Ienākošs Wi-Fi zvans"
- "Ienākošs darba Wi-Fi zvans"
- "Ienākošs videozvans"
- "Ienākošs, iespējams, nevēlams zvans"
- "Ienākošs video pieprasījums"
- "Jauns balss pasta ziņojums"
- "Jauns balss pasts (%d)"
- "Sastādiet šādu numuru: %s"
- "Balss pasta numurs nav zināms."
- "Nav pakalpojuma"
- "Atlasītais tīkls (%s) nav pieejams."
- "Atbildēt"
- "Beigt zvanu"
- "Video"
- "Balss"
- "Pieņemt"
- "Noraidīt"
- "Atzvanīt"
- "Sūtīt īsziņu"
- "Notiekošs zvans citā ierīcē"
- "Pāradresēt zvanu"
- "Lai veiktu zvanu, vispirms izslēdziet lidojuma režīmu."
- "Nav reģistrēts tīklā."
- "Mobilais tīkls nav pieejams."
- "Lai veiktu zvanu, ievadiet derīgu numuru."
- "Nevar veikt zvanu."
- "Notiek MMI secības startēšana…"
- "Pakalpojums netiek atbalstīts."
- "Nevar pārslēgt zvanus."
- "Nevar nošķirt zvanu."
- "Nevar pārsūtīt."
- "Nevar veikt konferences zvanu."
- "Nevar noraidīt zvanu."
- "Nevar pārtraukt zvanu(-us)."
- "SIP zvans"
- "Ārkārtas izsaukums"
- "Notiek radio ieslēgšana…"
- "Nav pakalpojuma. Notiek atkārtots mēģinājums…"
- "Nevar veikt zvanu. %s nav ārkārtas numurs."
- "Nevar veikt zvanu. Zvaniet ārkārtas numuram."
- "Izmantojiet tastatūru, lai sastādītu numuru"
- "Aizturēt zvanu"
- "Atsākt zvanu"
- "Beigt zvanu"
- "Rādīt numura sastādīšanas tastatūru"
- "Slēpt numura sastādīšanas tastatūru"
- "Izslēgt skaņu"
- "Ieslēgt skaņu"
- "Pievienot zvanu"
- "Apvienot zvanus"
- "Mainīt"
- "Pārvaldīt zvanus"
- "Pārvaldīt konferences zvanu"
- "Konferences zvans"
- "Pārvaldīt"
- "Audio"
- "Videozvans"
- "Mainīt uz balss zvanu"
- "Pārslēgt kameru"
- "Ieslēgt kameru"
- "Izslēgt kameru"
- "Citas iespējas"
- "Atskaņošana sākta"
- "Atskaņošana apturēta"
- "Kamera nav gatava"
- "Kamera ir gatava"
- "Nezināms zvana sesijas notikums"
- "Pakalpojums"
- "Iestatīšana"
- "<Nav iestatīts>"
- "Citi zvanu iestatījumi"
- "Zvans, ko nodrošina %s"
- "Ienākošie zvani, ko nodrošina %s"
- "kontaktpersonas fotoattēls"
- "pārslēgt uz privāto režīmu"
- "atlasīt kontaktpersonu"
- "Rakstīt savu…"
- "Atcelt"
- "Sūtīt"
- "Atbildēt"
- "Sūtīt īsziņu"
- "Noraidīt"
- "Atbildēt videozvanā"
- "Atbildēt audiozvanā"
- "Apstiprināt video pieprasījumu"
- "Noraidīt video pieprasījumu"
- "Apstiprināt video pārsūtīšanas pieprasījumu"
- "Noraidīt video pārsūtīšanas pieprasījumu"
- "Apstiprināt video saņemšanas pieprasījumu"
- "Noraidīt video saņemšanas pieprasījumu"
- "Velciet uz augšu, lai veiktu šādu darbību: %s."
- "Velciet pa kreisi, lai veiktu šādu darbību: %s."
- "Velciet pa labi, lai veiktu šādu darbību: %s."
- "Velciet uz leju, lai veiktu šādu darbību: %s."
- "Vibrācija"
- "Vibrācija"
- "Signāls"
- "Noklusējuma signāls (%1$s)"
- "Tālruņa zvana signāls"
- "Vibrācija zvana laikā"
- "Zvana signāls un vibrācija"
- "Konferences zvana pārvaldība"
- "Ārkārtas numurs"
- "Profila fotoattēls"
- "Kamera ir izslēgta"
- "no numura %s"
- "Piezīme nosūtīta"
- "Pēdējie ziņojumi"
- "Informācija par uzņēmumu"
- "%.1f jūdzes(-džu) attālumā"
- "%.1f km attālumā"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Tiks atvērts rīt plkst. %s"
- "Tiks atvērts šodien plkst. %s"
- "Tiks slēgts plkst. %s"
- "Tika slēgts šodien plkst. %s"
- "Atvērts"
- "Slēgts"
- "Nevēlams zvanītājs"
- "Zvans beidzās: %1$s"
- "Šis jums ir pirmais zvans no šī numura."
- "Iespējams, šis zvans bija no nevēlama zvanītāja."
- "Bloķēt numuru/ziņot"
- "Pievienot personu"
- "Nav nevēlams numurs"
-
diff --git a/InCallUI/res/values-mk/strings.xml b/InCallUI/res/values-mk/strings.xml
deleted file mode 100644
index 3161c5475bcfcea92cebf60f5977ddbc9c07de56..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-mk/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Телефон"
- "На чекање"
- "Непознат"
- "Приватен број"
- "Говорница"
- "Конференциски повик"
- "Повикот е прекинат"
- "Звучник"
- "Слушалка"
- "Жичени слушалки"
- "Bluetooth"
- "Испратете ги следниве тонови?\n"
- "Се испраќаат тонови\n"
- "Испрати"
- "Да"
- "Не"
- "Заменете го резервниот знак со"
- "Конференциски повик %s"
- "Број на говорна пошта"
- "Бирање"
- "Повторно бирање"
- "Конференциски повик"
- "Дојдовен повик"
- "Дојдовен работен повик"
- "Повикот заврши"
- "На чекање"
- "Повикот се прекинува"
- "Повик во тек"
- "Мојот број е %s"
- "Се поврзува видео"
- "Видеоповик"
- "Се бара видео"
- "Не може да се поврзе видеоповик"
- "Барањето за видео е одбиено"
- "Вашиот број за повратен повик\n %1$s"
- "Вашиот број за итен повик\n %1$s"
- "Бирање"
- "Пропуштен повик"
- "Пропуштени повици"
- "%s пропуштени повици"
- "Пропуштен повик од %s"
- "Тековен повик"
- "Тековен работен повик"
- "Појдовен повик преку Wi-Fi"
- "Тековен работен повик преку Wi-Fi"
- "На чекање"
- "Дојдовен повик"
- "Дојдовен работен повик"
- "Дојдовен повик преку Wi-Fi"
- "Дојдовен работен повик преку Wi-Fi"
- "Дојдовен видеоповик"
- "Дојдовниот повик може да е спам"
- "Дојдовно барање за видео"
- "Нова говорна пошта"
- "Нова говорна пошта (%d)"
- "Бирај %s"
- "Непознат број на говорна пошта"
- "Нема услуга"
- "Избраната мрежа (%s) е недостапна"
- "Одговори"
- "Спушти"
- "Видео"
- "Гласовен"
- "Прифати"
- "Отфрли"
- "Врати повик"
- "Порака"
- "Повик во тек на друг уред"
- "Префрлање повик"
- "За да остварите повик, прво исклучете го авионскиот режим."
- "Не е регистриран на мрежа."
- "Не е достапна мобилна мрежа."
- "За да остварите повик, внесете важечки број."
- "Не може да се повика."
- "Започнува ММИ низа..."
- "Услугата не е поддржана."
- "Не може да се префрлат повици."
- "Не може да се оддели повик."
- "Не може да се пренесе."
- "Не може да се оствари конференциски повик."
- "Не може да се отфрли повик."
- "Не може да се оствари повик."
- "Повик преку SIP"
- "Повик за итни случаи"
- "Се вклучува радиото..."
- "Нема услуга. Се обидува повторно…"
- "Не може да се повика. %s не е број за итни повици."
- "Не може да се повика. Бирајте го бројот за итни повици."
- "Користете ја тастатурата за бирање"
- "Стави на чекање"
- "Продолжи го повикот"
- "Заврши го повикот"
- "Прикажи копчиња за бирање"
- "Сокриј копчиња за бирање"
- "Исклучи звук"
- "Вклучи звук"
- "Додај повик"
- "Спои повици"
- "Замени"
- "Управувај со повици"
- "Управувај со конференциски повик"
- "Конференциски повик"
- "Управувај"
- "Аудио"
- "Видеоповик"
- "Промени во гласовен повик"
- "Промени ја камерата"
- "Вклучете ја камерата"
- "Исклучете ја камерата"
- "Повеќе опции"
- "Плеерот се вклучи"
- "Плеерот запре"
- "Камерата не е подготвена"
- "Камерата е подготвена"
- "Непознат настан при сесија повици"
- "Услуга"
- "Поставување"
- "<Нема поставка>"
- "Други поставки за повик"
- "Повикување преку %s"
- "Дојдовни повици преку %s"
- "фотографија на контакт"
- "префли на приватно"
- "избери контакт"
- "Напиши сопствена..."
- "Откажи"
- "Испрати"
- "Одговори"
- "Испрати SMS"
- "Одбиј"
- "Одговори со видеоповик"
- "Одговори со аудиоповик"
- "Прифати барање за видео"
- "Одбиј барање за видео"
- "Прифати барање за пренос на видео"
- "Одбиј барање за пренос на видео"
- "Прифати барање за прием на видео"
- "Одбиј барање за прием на видео"
- "Лизгај нагоре за %s."
- "Лизгај налево за %s."
- "Лизгај надесно за %s."
- "Лизгај надолу за %s."
- "Вибрации"
- "Вибрации"
- "Звук"
- "Стандарден звук (%1$s)"
- "Мелодија на телефонот"
- "Вибрации при ѕвонење"
- "Мелодија и вибрации"
- "Управувај со конференциски повик"
- "Број за итни случаи"
- "Фотографија на профилот"
- "Камерата е исклучена"
- "преку %s"
- "Испратена е белешка"
- "Неодамнешни пораки"
- "Деловни информации"
- "Оддалечено %.1f милји"
- "Оддалечено %.1f км"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Отвора утре во %s"
- "Отвора денес во %s"
- "Затвора во %s"
- "Денес затвори во %s"
- "Сега е отворено"
- "Сега е затворено"
- "Повикот е можен спам"
- "Повикот заврши %1$s"
- "За првпат добивте повик од бројов."
- "Постоеше сомнеж дека повиков е спам."
- "Блок./пријави спам"
- "Додајте го контактот"
- "Не е спам"
-
diff --git a/InCallUI/res/values-ml/strings.xml b/InCallUI/res/values-ml/strings.xml
deleted file mode 100644
index 5c313ad31b1f16f2875a4b22b0a78fb0bddbc3f3..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ml/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ഫോൺ"
- "ഹോൾഡിലാണ്"
- "അജ്ഞാതം"
- "സ്വകാര്യ നമ്പർ"
- "പണം നൽകി ഉപയോഗിക്കുന്ന ഫോൺ"
- "കോൺഫറൻസ് കോൾ"
- "കോൾ വിട്ടു"
- "സ്പീക്കർ"
- "ഹാൻഡ്സെറ്റ് ഇയർപീസ്"
- "വയേർഡ് ഹെഡ്സെറ്റ്"
- "Bluetooth"
- "ഇനിപ്പറയുന്ന ടോണുകൾ അയയ്ക്കണോ?\n"
- "ടോണുകൾ അയയ്ക്കുന്നു\n"
- "അയയ്ക്കുക"
- "ഉവ്വ്"
- "ഇല്ല"
- "വൈൽഡ് പ്രതീകം ഇതുപയോഗിച്ച് മാറ്റിസ്ഥാപിക്കുക"
- "കോൺഫറൻസ് കോൾ %s"
- "വോയ്സ്മെയിൽ നമ്പർ"
- "ഡയൽ ചെയ്യുന്നു"
- "വീണ്ടും ഡയൽചെയ്യുന്നു"
- "കോൺഫറൻസ് കോൾ"
- "ഇൻകമിംഗ് കോൾ"
- "ഇൻകമിംഗ് ഔദ്യോഗിക കോൾ"
- "കോൾ അവസാനിച്ചു"
- "ഹോൾഡിലാണ്"
- "ഹാംഗ് അപ്പ് ചെയ്യുന്നു"
- "കോളിലാണ്"
- "എന്റെ നമ്പർ %s ആണ്"
- "വീഡിയോ കണക്റ്റുചെയ്യുന്നു"
- "വീഡിയോ കോൾ"
- "വീഡിയോ അഭ്യർത്ഥിക്കുന്നു"
- "വീഡിയോ കോളുമായി കണക്റ്റുചെയ്യാനാവില്ല"
- "വീഡിയോ അഭ്യർത്ഥന നിരസിച്ചു"
- "നിങ്ങൾ തിരിച്ചുവിളിക്കേണ്ട നമ്പർ\n %1$s"
- "അടിയന്തിരമായി നിങ്ങൾ തിരിച്ചുവിളിക്കേണ്ട നമ്പർ\n %1$s"
- "ഡയൽ ചെയ്യുന്നു"
- "മിസ്ഡ് കോൾ"
- "മിസ്ഡ് കോളുകൾ"
- "%s മിസ്ഡ് കോളുകൾ"
- "%s എന്നതിൽ നിന്നുള്ള മിസ്ഡ് കോൾ"
- "കോൾ സജീവമാണ്"
- "ഓൺഗോയിംഗ് ഔദ്യോഗിക കോൾ"
- "ഓൺഗോയിംഗ് വൈഫൈ കോൾ"
- "ഓൺഗോയിംഗ് വൈഫൈ ഔദ്യോഗിക കോൾ"
- "ഹോൾഡിലാണ്"
- "ഇൻകമിംഗ് കോൾ"
- "ഇൻകമിംഗ് ഔദ്യോഗിക കോൾ"
- "ഇൻകമിംഗ് വൈഫൈ കോൾ"
- "ഇൻകമിംഗ് വൈഫൈ ഔദ്യോഗിക കോൾ"
- "ഇൻകമിംഗ് വീഡിയോ കോൾ"
- "സംശയാസ്പദമായ ഇൻകമിംഗ് സ്പാം കോൾ"
- "ഇൻകമിംഗ് വീഡിയോ അഭ്യർത്ഥന"
- "പുതിയ വോയ്സ്മെയിൽ"
- "പുതിയ വോയ്സ്മെയിൽ (%d)"
- "%s ഡയൽ ചെയ്യുക"
- "വോയ്സ്മെയിൽ നമ്പർ അജ്ഞാതമാണ്"
- "സേവനമില്ല"
- "തിരഞ്ഞെടുത്ത നെറ്റ്വർക്ക് (%s) ലഭ്യമല്ല"
- "മറുപടി"
- "ഹാംഗ് അപ്പുചെയ്യുക"
- "വീഡിയോ"
- "വോയ്സ്"
- "അംഗീകരിക്കുക"
- "ഡിസ്മിസ്"
- "തിരിച്ചുവിളിക്കുക"
- "സന്ദേശം"
- "മറ്റൊരു ഉപകരണത്തിൽ നടന്നുകൊണ്ടിരിക്കുന്ന കോൾ"
- "കോൾ കൈമാറുക"
- "ഒരു കോൾ ചെയ്യാൻ, ആദ്യം ഫ്ലൈറ്റ് മോഡ് ഓഫുചെയ്യുക."
- "നെറ്റ്വർക്കിൽ രജിസ്റ്റർ ചെയ്തിട്ടില്ല."
- "സെല്ലുലാർ നെറ്റ്വർക്ക് ലഭ്യമല്ല."
- "ഒരു കോൾ ചെയ്യുന്നതിന്, സാധുതയുള്ള നമ്പർ നൽകുക."
- "കോൾ ചെയ്യാനായില്ല."
- "MMI സീക്വൻസ് ആരംഭിക്കുന്നു…"
- "സേവനം പിന്തുണയ്ക്കുന്നില്ല."
- "കോളുകൾ മാറാനാവില്ല."
- "കോൾ വേർതിരിക്കാനാവില്ല."
- "കൈമാറ്റം ചെയ്യാനാവില്ല."
- "കോൺഫറൻസ് കോൾ ചെയ്യാനാവില്ല."
- "കോൾ നിരസിക്കാനാവില്ല."
- "കോൾ (കോളുകൾ) വിളിക്കാനാവില്ല."
- "SIP കോൾ"
- "എമർജൻസി കോൾ"
- "റേഡിയോ ഓൺ ചെയ്യുന്നു…"
- "സേവനമൊന്നുമില്ല. വീണ്ടും ശ്രമിക്കുന്നു…"
- "കോൾ ചെയ്യാനാവില്ല. %s എന്നത് ഒരു അടിയന്തിര നമ്പറല്ല."
- "കോൾ ചെയ്യാനാവില്ല. ഒരു അടിയന്തിര കോൾ നമ്പർ ഡയൽചെയ്യുക."
- "ഡയൽ ചെയ്യാൻ കീബോർഡ് ഉപയോഗിക്കുക"
- "കോൾ ഹോൾഡുചെയ്യുക"
- "കോൾ പുനരാരംഭിക്കുക"
- "കോൾ അവസാനിപ്പിക്കുക"
- "ഡയൽപാഡ് കാണിക്കുക"
- "ഡയൽപാഡ് മറയ്ക്കുക"
- "മ്യൂട്ടുചെയ്യുക"
- "അൺമ്യൂട്ടുചെയ്യുക"
- "കോൾ ചേർക്കുക"
- "കോളുകൾ ലയിപ്പിക്കുക"
- "സ്വാപ്പുചെയ്യുക"
- "കോളുകൾ നിയന്ത്രിക്കുക"
- "കോൺഫറൻസ് കോൾ നിയന്ത്രിക്കുക"
- "കോൺഫറൻസ് കോൾ"
- "മാനേജുചെയ്യുക"
- "ഓഡിയോ"
- "വീഡിയോ കോൾ"
- "വോയ്സ് കോളിലേക്ക് മാറ്റുക"
- "ക്യാമറ സ്വിച്ചുചെയ്യുക"
- "ക്യാമറ ഓണാക്കുക"
- "ക്യാമറ ഓഫാക്കുക"
- "കൂടുതൽ ഓപ്ഷനുകൾ"
- "പ്ലെയർ ആരംഭിച്ചു"
- "പ്ലേയർ നിർത്തി"
- "ക്യാമറ തയ്യാറായില്ല"
- "ക്യാമറ തയ്യാറായി"
- "അജ്ഞാത കോൾ സെഷൻ ഇവന്റ്"
- "സേവനം"
- "സജ്ജമാക്കുക"
- "<ക്രമീകരിച്ചിട്ടില്ല>"
- "മറ്റ് കോൾ ക്രമീകരണം"
- "%s മുഖേന വിളിക്കുന്നു"
- "%s മുഖേനയുള്ള ഇൻകമിംഗ്"
- "കോൺടാക്റ്റ് ഫോട്ടോ"
- "സ്വകാര്യം എന്നതിലേക്ക് പോകുക"
- "കോൺടാക്റ്റ് തിരഞ്ഞെടുക്കുക"
- "നിങ്ങളുടെ സ്വന്തം സന്ദേശമെഴുതുക..."
- "റദ്ദാക്കുക"
- "അയയ്ക്കുക"
- "മറുപടി"
- "SMS അയയ്ക്കുക"
- "നിരസിക്കുക"
- "വീഡിയോ കോളായി മറുപടി നൽകുക"
- "ഓഡിയോ കോളായി മറുപടി നൽകുക"
- "വീഡിയോ കോളിനുള്ള അഭ്യർത്ഥന അംഗീകരിക്കുക"
- "വീഡിയോ കോൾ അഭ്യർത്ഥന നിരസിക്കുക"
- "വീഡിയോ പ്രക്ഷേപണ അഭ്യർത്ഥന അംഗീകരിക്കുക"
- "വീഡിയോ പ്രക്ഷേപണ അഭ്യർത്ഥന നിരസിക്കുക"
- "വീഡിയോ കോൾ സ്വീകരിക്കാനുള്ള അഭ്യർത്ഥന അംഗീകരിക്കുക"
- "വീഡിയോ കോൾ സ്വീകരിക്കാനുള്ള അഭ്യർത്ഥന നിരസിക്കുക"
- "%s എന്നതിനായി മുകളിലേയ്ക്ക് സ്ലൈഡുചെയ്യുക."
- "%s എന്നതിനായി ഇടത്തേയ്ക്ക് സ്ലൈഡുചെയ്യുക."
- "%s എന്നതിനായി വലത്തേയ്ക്ക് സ്ലൈഡുചെയ്യുക."
- "%s എന്നതിനായി താഴേക്ക് സ്ലൈഡുചെയ്യുക."
- "വൈബ്രേറ്റുചെയ്യുക"
- "വൈബ്രേറ്റുചെയ്യുക"
- "ശബ്ദം"
- "സ്ഥിര ശബ്ദം (%1$s)"
- "ഫോൺ റിംഗ്ടോൺ"
- "റിംഗുചെയ്യുമ്പോൾ വൈബ്രേറ്റുചെയ്യുക"
- "റിംഗ്ടോണും വൈബ്രേറ്റുചെയ്യലും"
- "കോൺഫറൻസ് കോൾ നിയന്ത്രിക്കുക"
- "അടിയന്തര നമ്പർ"
- "പ്രൊഫൈൽ ഫോട്ടോ"
- "ക്യാമറ ഓഫാക്കുക"
- "%s വഴി"
- "കുറിപ്പ് അയച്ചു"
- "ഏറ്റവും പുതിയ സന്ദേശങ്ങൾ"
- "ബിസിനസ്സ് വിവരം"
- "%.1f മൈൽ അകലെ"
- "%.1f കിലോമീറ്റർ അകലെ"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "നാളെ %s-ന് തുറക്കുന്നു"
- "ഇന്ന് %s-ന് തുറക്കുന്നു"
- "%s-ന് അടയ്ക്കുന്നു"
- "ഇന്ന് %s-ന് അടച്ചു"
- "ഇപ്പോൾ തുറന്നിരിക്കുന്നു"
- "ഇപ്പോൾ അടച്ചിരിക്കുന്നു"
- "സംശയാസ്പദമായ സ്പാം കോളർ"
- "കോൾ അവസാനിച്ചു, %1$s"
- "ഈ നമ്പറിൽ നിന്ന് ആദ്യമായാണ് നിങ്ങൾക്ക് കോൾ വരുന്നത്."
- "ഈ കോൾ ഒരു സ്പാമർ ആണെന്ന് ഞങ്ങൾക്ക് സംശയമുണ്ടായിരുന്നു."
- "ബ്ലോക്കുചെയ്യുക/സ്പാമാണെന്ന് റിപ്പോർട്ടുചെയ്യുക"
- "കോൺടാക്റ്റ് ചേർക്കുക"
- "സ്പാം അല്ല"
-
diff --git a/InCallUI/res/values-mn/strings.xml b/InCallUI/res/values-mn/strings.xml
deleted file mode 100644
index 972f914a44ae78019c70f183be72e98dbe05a2ce..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-mn/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Утас"
- "Хүлээлгэнд байгаа"
- "Тодорхойгүй"
- "Нууцалсан дугаар"
- "Төлбөртэй утас"
- "Хурлын дуудлага"
- "Дуудлага таслагдсан"
- "Чанга яригч"
- "Утасны чихэвч"
- "Утастай чихэвч"
- "Bluetooth"
- "Дараах аяыг илгээх үү?\n"
- "Ая илгээж байна\n"
- "Илгээх"
- "Тийм"
- "Үгүй"
- "Тэмдэгтийг дараахаар солих"
- "Хурлын дуудлага %s"
- "Дуут шуудангийн дугаар"
- "Залгаж байна"
- "Дахин залгаж байна"
- "Хурлын дуудлага"
- "Орох дуудлага"
- "Орох ажлын дуудлага"
- "Дуудлага дууссан"
- "Хүлээлгэнд"
- "Тасалж байна"
- "Дуудлагатай"
- "Миний дугаар %s"
- "Видеог холбож байна"
- "Видео дуудлага"
- "Видео хүлээж байна"
- "Видео дуудлагад холбогдож чадсангүй"
- "Бичлэг хийх хүсэлтийг зөвшөөрсөнгүй"
- "Таны буцаан залгах дугаар\n %1$s"
- "Таны яаралтай хулээн авах дугаар\n %1$s"
- "Залгаж байна"
- "Аваагүй дуудлага"
- "Аваагүй дуудлага"
- "%s аваагүй дуудлага"
- "%s-н аваагүй дуудлага"
- "Залгаж буй дуудлага"
- "Холбогдсон албаны дуудлага"
- "Холбогдсон Wi-Fi дуудлага"
- "Залгаж буй Wi-Fi албаны дуудлага"
- "Хүлээгдэж байна"
- "Орох дуудлага"
- "Орох ажлын дуудлага"
- "Орох Wi-Fi дуудлага"
- "Орох Wi-Fi албаны дуудлага"
- "Орох видео дуудлага"
- "Орж ирсэн сэжигтэй спам дуудлага"
- "Орох видео хүсэлт"
- "Шинэ дуут шуудан"
- "Шинэ дуут шуудан (%d)"
- "%s руу залгах"
- "Дуут шуудангийн дугаар тодорхойгүй"
- "Үйлчилгээ байхгүй"
- "Сонгосон сүлжээг (%s) ашиглах боломжгүй"
- "Хариулт"
- "Таслах"
- "Видео"
- "Дуу хоолой"
- "Зөвшөөрөх"
- "Алгасах"
- "Буцааж залгах"
- "Зурвас"
- "Өөр төхөөрөмж дээр хийгдэж буй дуудлага"
- "Дуудлага шилжүүлэх"
- "Залгахын тулд эхлээд Нислэгийн горимоос гарна уу."
- "Сүлжээнд бүртгэгдээгүй байна."
- "Үүрэн сүлжээ байхгүй."
- "Залгахын тулд хүчин төгөлдөр дугаар оруулна уу."
- "Залгах боломжгүй байна."
- "MMI дарааллыг эхлүүлж байна…"
- "Дэмжигдээгүй үйлчилгээ байна."
- "Дуудлагыг солих боломжгүй байна."
- "Дуудлагыг салгаж чадахгүй байна."
- "Шилжүүлэх боломжгүй байна."
- "Хурлын дуудлага хийх боломжгүй байна."
- "Дуудлагыг цуцлах боломжгүй байна."
- "Дуудлага чөлөөлөх боломжгүй байна."
- "SIP дуудлага"
- "яаралтай"
- "Радиог асааж байна..."
- "Ажиллагаагүй байна. Дахин оролдоно уу..."
- "Залгах боломжгүй. %s нь яаралтай дугаар биш байна."
- "Залгах боломжгүй. Яаралтай дугаар луу залгана уу."
- "Залгахдаа гар ашиглана уу"
- "Дуудлага хүлээлгэх"
- "Дуудлагыг үргэлжлүүлэх"
- "Дуудлагыг дуусгах"
- "Залгах товчлуурыг харуулах"
- "Залгах товчлуурыг нуух"
- "Дуу хаах"
- "Дууг нээх"
- "Дуудлага нэмэх"
- "Дуудлага нэгтгэх"
- "Солих"
- "Дуудлага удирдах"
- "Хурлын дуудлага удирдах"
- "Хурлын дуудлага"
- "Удирдах"
- "Аудио"
- "Видео дуудлага"
- "Дуут дуудлага руу өөрчлөх"
- "Камер солих"
- "Камераа асаана уу"
- "Камер унтраах"
- "Нэмэлт сонголт"
- "Тоглуулагчийг эхлүүлсэн"
- "Тоглуулагчийг зогсоосон"
- "Камер бэлэн бус байна"
- "Камер бэлэн байна"
- "Үл мэдэгдэх дуудлагын үе"
- "Үйлчилгээ"
- "Тохируулга"
- "Тохируулаагүй"
- "Бусад дуудлагын тохиргоо"
- "%s-р залгаж байна"
- "%s-р ирж байна"
- "харилцагчийн зураг"
- "хувийн яриа"
- "харилцагч сонгох"
- "Өөрийн ...-г бичээрэй"
- "Цуцлах"
- "Илгээх"
- "Хариулт"
- "SMS илгээх"
- "Татгалзах"
- "Видео дуудлагаар хариулах"
- "Аудио дуудлагаар хариулах"
- "Видео хүсэлтийг хүлээн зөвшөөрөх"
- "Видео хүсэлтээс татгалзах"
- "Видео дамжуулах хүсэлтийг хүлээн зөвшөөрөх"
- "Видео дамжуулах хүсэлтээс татгалзах"
- "Видео хүлээж авах хүсэлтийг зөвшөөрөх"
- "Видео хүлээн авах хүсэлтээс татгалзах"
- "%s хийх бол дээш гулсуулна уу."
- "%s-г харахын тулд зүүн тийш гулсуулна уу."
- "%s харахын тулд баруун тийш гулсуулна уу."
- "%s-г харахын тулд доош гулсуулна уу."
- "Чичиргээ"
- "Чичиргээ"
- "Дуу"
- "Үндсэн дуу (%1$s)"
- "Утасны хонхны ая"
- "Хонх дуугарах үед чичрэх"
- "Хонхны ая, Чичиргээ"
- "Хурлын дуудлагыг удирдах"
- "Яаралтай дугаар"
- "Профайл зураг"
- "Камер унтраалттай байна"
- "%s-р"
- "Тэмдэглэлийг илгээсэн"
- "Саяхны зурвас"
- "Бизнес мэдээлэл"
- "%.1f милийн зайтай"
- "%.1f км-н зайтай"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Маргааш %s-с нээгдэнэ"
- "Өнөөдөр %s-с нээгдэнэ"
- "%s-с хаадаг"
- "Өнөөдөр %s-с хаасан"
- "Одоо нээлттэй"
- "Одоо хаалттай"
- "Сэжигтэй спам дуудлага хийгч"
- "Дуудлага дууссан %1$s"
- "Энэ дугаараас танд анх удаа дуудлага ирсэн."
- "Бид үүнийг спам дуудлага гэж үзсэн."
- "Спам гэж мэдээлэх/хориглох"
- "Харилцагч нэмэх"
- "Спам биш"
-
diff --git a/InCallUI/res/values-mr/strings.xml b/InCallUI/res/values-mr/strings.xml
deleted file mode 100644
index 15b3dfc32bf52e86694f6906cdcfc8c6b9201fb0..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-mr/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "फोन"
- "होल्ड वर"
- "अज्ञात"
- "खाजगी नंबर"
- "सार्वजनिक फोन"
- "परिषद कॉल"
- "कॉल सोडला"
- "स्पीकर"
- "हँडसेट इअरपीस"
- "वायर्ड हेडसेट"
- "ब्लूटुथ"
- "खालील टोन पाठवायचे?\n"
- "टोन पाठवित आहे\n"
- "पाठवा"
- "होय"
- "नाही"
- "खराब वर्णास यासह पुनर्स्थित करा"
- "परिषद कॉल %s"
- "व्हॉइसमेल नंबर"
- "डायल करीत आहे"
- "रीडायल करत आहे"
- "परिषद कॉल"
- "येणारा कॉल"
- "येणारा कार्य कॉल"
- "कॉल संपला"
- "होल्ड वर"
- "हँग अप करणेे"
- "कॉल मधील"
- "माझा नंबर %s आहे"
- "व्हिडिओ कनेक्ट करत आहे"
- "व्हिडिओ कॉल"
- "व्हिडिओ विनंती करत आहे"
- "व्हिडिओ कॉल कनेक्ट करू शकत नाही"
- "व्हिडिओ विनंती नाकारली"
- "आपला कॉलबॅक नंबर\n %1$s"
- "आपला आणीबाणी कॉलबॅक नंबर\n %1$s"
- "डायल करीत आहे"
- "सुटलेला कॉल"
- "सुटलेले कॉल"
- "%s सुटलेले कॉल"
- "%s कडील सुटलेला कॉल"
- "सुरू असलेला कॉल"
- "सुरु असलेला कार्य कॉल"
- "सुरु असलेला वाय-फाय कॉल"
- "सुरु असलेला वाय-फाय कार्य कॉल"
- "होल्ड वर"
- "येणारा कॉल"
- "येणारा कार्य कॉल"
- "येणारा वाय-फाय कॉल"
- "येणारा वाय-फाय कार्य कॉल"
- "येणारा व्हिडिओ कॉल"
- "येणारा संशयित स्पॅम कॉल"
- "येणारी व्हिडिओ विनंती"
- "नवीन व्हॉइसमेल"
- "नवीन व्हॉइसमेल (%d)"
- "%s डायल करा"
- "व्हॉइसमेल नंबर अज्ञात"
- "सेवा नाही"
- "निवडलेले नेटवर्क (%s) अनुपलब्ध"
- "उत्तर"
- "हँग अप"
- "व्हिडिओ"
- "व्हॉइस"
- "स्वीकार करा"
- "डिसमिस करा"
- "पुन्हा कॉल करा"
- "संदेश"
- "दुसऱ्या डिव्हाइसवर सुरु असलेला कॉल"
- "कॉल स्थानांतरित करा"
- "कॉल करण्यासाठी, प्रथम विमान मोड बंद करा."
- "नेटवर्कवर नोंदणीकृत नाही."
- "मोबाईल नेटवर्क उपलब्ध नाही."
- "कॉल करण्यासाठी, एक वैध नंबर प्रविष्ट करा."
- "कॉल करू शकत नाही."
- "MMI क्रम प्रारंभ करीत आहे..."
- "सेवा समर्थित नाही."
- "कॉल स्विच करू शकत नाही."
- "कॉल विभक्त करू शकत नाही."
- "हस्तांतर करू शकत नाही."
- "परिषद घेऊ शकत नाही."
- "कॉल नाकारू शकत नाही."
- "कॉल रिलीज करू शकत नाही."
- "SIP कॉल"
- "आणीबाणी कॉल"
- "रेडिओ चालू करीत आहे..."
- "सेवा नाही. पुन्हा प्रयत्न करत आहे…"
- "कॉल करू शकत नाही. %s हा आणीबाणी नंबर नाही."
- "कॉल करू शकत नाही. आणीबाणी नंबर डायल करा."
- "डायल करण्यासाठी कीबोर्डचा वापर करा"
- "कॉल होल्ड करा"
- "कॉल पुनः सुरु करा"
- "कॉल समाप्त करा"
- "डायलपॅड दर्शवा"
- "डायलपॅड लपवा"
- "नि:शब्द करा"
- "सशब्द करा"
- "कॉल जोडा"
- "कॉल विलीन करा"
- "अदलाबदल करा"
- "कॉल व्यवस्थापित करा"
- "परिषद कॉल व्यवस्थापित करा"
- "परिषद कॉल"
- "व्यवस्थापित करा"
- "ऑडिओ"
- "व्हिडिओ कॉल"
- "व्हॉइस कॉल वर बदला"
- "कॅमेरा स्विच करा"
- "कॅमेरा चालू करा"
- "कॅमेरा बंद करा"
- "अधिक पर्याय"
- "प्लेअर सुरु झाले"
- "प्लेअर थांबले"
- "कॅमेरा तयार नाही"
- "कॅमेरा तयार"
- "अज्ञात कॉल सत्र इव्हेंट"
- "सेवा"
- "सेटअप"
- "<सेट नाही>"
- "इतर कॉल सेटिंग्ज"
- "%s द्वारे कॉल करीत आहे"
- "%s द्वारे येणारे"
- "संपर्क फोटो"
- "खाजगी व्हा"
- "संपर्क निवडा"
- "आपण स्वतः लिहा…"
- "रद्द करा"
- "पाठवा"
- "उत्तर"
- "SMS पाठवा"
- "नकार द्या"
- "व्हिडिओ कॉल म्हणून उत्तर द्या"
- "ऑडिओ कॉल म्हणून उत्तर द्या"
- "व्हिडिओ विनंती स्वीकारा"
- "व्हिडिओ विनंतीस नकार द्या"
- "व्हिडिओ प्रसारण विनंती स्वीकार करा"
- "व्हिडिओ प्रसारण विनंतीस नकार द्या"
- "व्हिडिओ प्राप्त करा विनंती स्वीकार करा"
- "व्हिडिओ प्राप्त करा विनंतीस नकार द्या"
- "%s साठी वर स्लाइड करा."
- "%s साठी डावीकडे स्लाइड करा."
- "%s साठी उजवीकडे स्लाइड करा."
- "%s साठी खाली स्लाइड करा."
- "कंपन करा"
- "कंपन करा"
- "ध्वनी"
- "डीफॉल्ट आवाज (%1$s)"
- "फोन रिंगटोन"
- "रिंग करताना कंपन करा"
- "रिंगटोन आणि कंपन"
- "परिषद कॉल व्यवस्थापित करा"
- "आणीबाणी नंबर"
- "प्रोफाइल फोटो"
- "कॅमेरा बंद"
- "%s द्वारा"
- "टीप पाठविली"
- "अलीकडील संदेश"
- "व्यवसाय माहिती"
- "%.1f मैल दूर"
- "%.1f किमी दूर"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "उद्या %s वाजता उघडेल"
- "आज %s उघडेल"
- "आज %s वाजता बंद होईल"
- "आज %s वाजता बंद केले"
- "आता उघडा"
- "आता बंद केले आहे"
- "संशयित स्पॅम कॉलर"
- "कॉल समाप्त झाला %1$s"
- "या नंबरने अापल्याला कॉल केल्याची ही पहिलीच वेळ आहे."
- "अाम्हाला संशय अाहे की हा कॉल एक स्पॅमर असू शकतो."
- "अवरोधित करा/स्पॅमचा अहवाल द्या"
- "संपर्क जोडा"
- "स्पॅम नाही"
-
diff --git a/InCallUI/res/values-ms/strings.xml b/InCallUI/res/values-ms/strings.xml
deleted file mode 100644
index 4c7be38054e84a489d1cdf50b5e5ee3e88778678..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ms/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Ditunda"
- "Tidak diketahui"
- "Nombor peribadi"
- "Telefon Awam"
- "Panggilan sidang"
- "Panggilan diputuskan"
- "Pembesar suara"
- "Alat dengar tel bimbit"
- "Set kepala berwayar"
- "Bluetooth"
- "Hantar nada berikut?\n"
- "Menghantar nada\n"
- "Hantar"
- "Ya"
- "Tidak"
- "Gantikan aksara bebas dengan"
- "Panggilan sidang %s"
- "Nombor mel suara"
- "Mendail"
- "Mendail semula"
- "Panggilan sidang"
- "Panggilan masuk"
- "Pgln masuk tempat kerja"
- "Panggilan tamat"
- "Ditunda"
- "Menamatkan panggilan"
- "Dalam panggilan"
- "Nombor saya ialah %s"
- "Menyambungkan video"
- "Panggilan video"
- "Meminta video"
- "Tidak dapat menyambungkan panggilan video"
- "Permintaan video ditolak"
- "Nombor panggilan balik anda%1$s\n"
- "Nombor panggilan balik kecemasan anda\n%1$s"
- "Mendail"
- "Panggilan terlepas"
- "Panggilan terlepas"
- "%s panggilan terlepas"
- "Panggilan tidak dijawab daripada %s"
- "Panggilan sedang berlangsung"
- "Panggilan sedang berlangsung daripada tempat kerja"
- "Panggilan Wi-Fi sedang berlangsung"
- "Panggian Wi-Fi sedang berlangsung daripada tempat kerja"
- "Ditunda"
- "Panggilan masuk"
- "Panggilan masuk daripada tempat kerja"
- "Panggilan masuk melalui Wi-Fi"
- "Panggilan masuk melalui Wi-Fi daripada tempat kerja"
- "Panggilan video masuk"
- "Disyaki panggilan spam masuk"
- "Permintaan video masuk"
- "Mel suara baharu"
- "Mel suara baharu (%d)"
- "Dail %s"
- "Nombor mel suara tidak dikenali"
- "Tiada perkhidmatan"
- "Rangkaian pilihan (%s) tidak tersedia"
- "Jawab"
- "Letakkan gagang"
- "Video"
- "Suara"
- "Terima"
- "Ketepikan"
- "Panggil balik"
- "Mesej"
- "Panggilan sedang berlangsung pada peranti lain"
- "Pindahkan Panggilan"
- "Untuk membuat panggilan, matikan mod Pesawat terlebih dahulu."
- "Tidak didaftarkan pada rangkaian."
- "Rangkaian selular tidak tersedia."
- "Untuk membuat panggilan, masukkan nombor yang sah."
- "Tidak dapat memanggil."
- "Memulakan jujukan MMI..."
- "Perkhidmatan tidak disokong."
- "Tidak dapat menukar panggilan."
- "Tidak dapat mengasingkan panggilan."
- "Tidak dapat memindahkan."
- "Tidak dapat membuat panggilan persidangan."
- "Tidak dapat menolak panggilan."
- "Tidak dapat melepaskan panggilan."
- "Panggilan SIP"
- "Panggilan kecemasan"
- "Menghidupkan radio..."
- "Tiada perkhidmatan. Mencuba lagi..."
- "Tidak dapat memanggil. %s bukan nombor kecemasan."
- "Tidak dapat memanggil. Dail nombor kecemasan."
- "Gunakan papan kekunci untuk mendail"
- "Tahan Panggilan"
- "Sambung Semula Panggilan"
- "Tamatkan Panggilan"
- "Tunjukkan Pad Pendail"
- "Sembunyikan Pad Pendail"
- "Redam"
- "Nyahredam"
- "Tambah panggilan"
- "Gabung panggilan"
- "Silih"
- "Urus panggilan"
- "Urus panggilan sidang"
- "Panggilan sidang"
- "Urus"
- "Audio"
- "Panggilan video"
- "Tukar ke panggilan suara"
- "Tukar kamera"
- "Hidupkan kamera"
- "Matikan kamera"
- "Lagi pilihan"
- "Pemain Dimulakan"
- "Pemain Dihentikan"
- "Kamera tidak bersedia"
- "Kamera bersedia"
- "Acara sesi panggilan tidak diketahui"
- "Perkhidmatan"
- "Persediaan"
- "<Tidak ditetapkan>"
- "Tetapan panggilan lain"
- "Memanggil melalui %s"
- "Panggilan masuk melalui %s"
- "foto kenalan"
- "jadi peribadi"
- "pilih kenalan"
- "Tulis sendiri…"
- "Batal"
- "Hantar"
- "Jawab"
- "Hantar SMS"
- "Tolak"
- "Jawab sebagai panggilan video"
- "Jawab sebagai panggilan audio"
- "Terima permintaan video"
- "Tolak permintaan video"
- "Terima permintaan hantar video"
- "Tolak permintaan hantar video"
- "Terima permintaan terima video"
- "Tolak permintaan terima video"
- "Luncurkan ke atas untuk %s."
- "Luncurkan ke kiri untuk %s."
- "Luncurkan ke kanan untuk %s."
- "Luncurkan ke bawah untuk %s."
- "Bergetar"
- "Bergetar"
- "Bunyi"
- "Bunyi lalai (%1$s)"
- "Nada dering telefon"
- "Bergetar apabila berdering"
- "Nada dering & Bergetar"
- "Urus panggilan sidang"
- "Nombor kecemasan"
- "Foto profil"
- "Kamera dimatikan"
- "melalui %s"
- "Nota dihantar"
- "Mesej terbaharu"
- "Maklumat perniagaan"
- "%.1f batu dari sini"
- "%.1f km dari sini"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Dibuka esok pada pukul %s"
- "Dibuka hari ini pada pukul %s"
- "Tutup pada pukul %s"
- "Ditutup hari ini pada pukul %s"
- "Dibuka sekarang"
- "Ditutup sekarang"
- "Disyaki pmggil spam"
- "Panggilan tamat %1$s"
- "Ini kali pertama nombor ini memanggil anda."
- "Kami mengesyaki panggilan ini adalah spam."
- "Sekat/laporkan spam"
- "Tambahkan kenalan"
- "Bukan spam"
-
diff --git a/InCallUI/res/values-my/strings.xml b/InCallUI/res/values-my/strings.xml
deleted file mode 100644
index efe91436f57bfbe43c7066c48af0f3e960ca5fe9..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-my/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ဖုန်း"
- "ခဏ ကိုင်ထားစဉ်"
- "အမျိုးအမည်မသိ"
- "ကိုယ်ပိုင်ဖုန်းနံပါတ်"
- "အများသုံးဖုန်း"
- "အစည်းအဝေးခေါ်ဆိုမှု"
- "ဖုန်းလိုင်းကျသွားခဲ့သည်"
- "စပီကာ"
- "လက်ကိုင်တယ်လီဖုန်းနားခွက်"
- "ကြိုးတပ် မိုက်ခွက်ပါနားကြပ်"
- "ဘလူးတုသ်"
- "အောက်ပါ တီးလုံးများကို ပို့မလား။\n"
- "အသံများ ပို့နေသည်\n"
- "ပို့ပါ"
- "Yes"
- "No"
- "အစားထိုး အထူးအက္ခရာတွင် အစားထိုးရန်"
- "အစည်းအဝေးခေါ်ဆိုမှု %s"
- "အသံစာနံပါတ်"
- "ခေါ်ဆိုနေသည်"
- "ပြန်ခေါ်နေသည်"
- "အစည်းအဝေးခေါ်ဆိုမှု"
- "အဝင် ခေါ်ဆိုမှု"
- "အလုပ်ဆိုင်ရာ အဝင် ခေါ်ဆိုမှု"
- "ဖုန်းခေါ်ဆိုမှု ပြီးဆုံးပါပြီ"
- "ခဏ ကိုင်ထားစဉ်"
- "ဖုန်းချနေပါသည်"
- "ဖုန်းခေါ်ဆိုနေဆဲ"
- "ကျွန်ုပ်၏ နံပါတ်မှာ %s ဖြစ်ပါသည်"
- "ဗီဒီယို ချိတ်ဆက်နေသည်"
- "ဗီဒီယို ခေါ်ဆိုမှု"
- "ဗီဒီယိုခေါ်ဆိုနေသည်"
- "ဗွီဒီယို ခေါ်ဆိုမှု ချိတ်ဆက်၍မရပါ။"
- "ဗီဒီယို ခေါ်ဆိုမှုကို ပယ်ချလိုက်ပါပြီ"
- "သင့်ကိုပြန်လည်ခေါ်ဆိုရန် နံပါတ်\n %1$s"
- "သင့်ကိုအရေးပေါ် ပြန်လည်ခေါ်ဆိုရန် နံပါတ်\n %1$s"
- "ဖုန်းခေါ်နေသည်"
- "လွတ်သွားသော ခေါ်ဆိုမှု"
- "လွတ်သွားသော ခေါ်ဆိုမှုများ"
- "လွတ်သွားသော ခေါ်ဆိုမှု %s"
- "%s မှလွတ်သွားသော ခေါ်ဆိုမှု"
- "လက်ရှိခေါ်ဆိုမှု"
- "လက်ရှိအလုပ်ခေါ်ဆိုမှု"
- "လက်ရှိ Wi-Fi ခေါ်ဆိုမှု"
- "လက်ရှိအလုပ် Wi-Fi ခေါ်ဆိုမှု"
- "ခဏ ကိုင်ထားစဉ်"
- "အဝင် ခေါ်ဆိုမှု"
- "အလုပ်ဆိုင်ရာ အဝင်ခေါ်ဆိုမှု"
- "အဝင် Wi-Fi ခေါ်ဆိုမှု"
- "အလုပ်ဆိုင်ရာ အဝင် Wi-Fi ခေါ်ဆိုမှု"
- "အဝင်ဗီဒီယိုခေါ်ဆိုမှု"
- "ခေါ်နေသော မသင်္ကာဖွယ်ရာ စပမ်းခေါ်ဆိုမှု"
- "ဗီဒီယိုအဝင် ခေါ်ဆိုမှု"
- "အသံစာအသစ်"
- "အသံစာ အသစ် (%d) ခု"
- "%s ကိုခေါ်ပါ"
- "အသံစာ၏နံပါတ်ကို မသိပါ"
- "ဆက်သွယ်မှု ဧရိယာပြင်ပသို့ ရောက်ရှိနေသည်"
- "ရွေးချယ်ထားသော ကွန်ရက် (%s) မရရှိနိုင်ပါ"
- "ဖြေကြားပါ"
- "ဖုန်းချပါ"
- "ဗီဒီယို"
- "အသံ"
- "လက်ခံပါ"
- "ပယ်ပါ"
- "ပြန်ခေါ်ပါ"
- "မက်ဆေ့ဂျ်"
- "အခြားကိရိယာတွင် လက်ရှိခေါ်ဆိုနေမှု"
- "ခေါ်ဆိုမှုကို လွှဲပြောင်းပါ"
- "ခေါ်ဆိုမှု ပြုလုပ်ရန်အတွက် လေယာဉ်ပျံမုဒ်ကို ဦးစွာပိတ်ပါ။"
- "ကွန်ယက်ပေါ်တွင် မှတ်ပုံတင်ထားခြင်း မရှိပါ။"
- "ဆဲလ်လူလာ ကွန်ရက် မရှိပါ။"
- "ခေါ်ဆိုမှု ပြုလုပ်ရန်အတွက် မှန်ကန်သည့်နံပါတ်တစ်ခုကို ထည့်ပါ။"
- "ခေါ်ဆို၍မရပါ။"
- "MMI အစီအစဉ် စတင်နေသည်..."
- "ဝန်ဆောင်မှုအား ပံ့ပိုးမထားပါ။"
- "ခေါ်ဆိုမှုများကို လှည့်ပြောင်း၍မရပါ။"
- "ခေါ်ဆိုမှုကို ခွဲခြား၍မရပါ။"
- "မလွှဲပြောင်းနိုင်ပါ။"
- "အစည်းအဝေးခေါ်ဆိုမှု ပြုလုပ်၍မရပါ။"
- "ခေါ်ဆိုမှုကို ငြင်းဆို၍မရပါ။"
- "ခေါ်ဆိုမှု(များ) ကို လွှတ်၍မရပါ။"
- "SIP ခေါ်ဆိုမှု"
- "အရေးပေါ် ခေါ်ဆိုမှု"
- "ရေဒီယို ဖွင့်နေသည်…"
- "ချိတ်ဆက်မှု ဧရိယာပြင်ပရောက်နေပါသည်။ ထပ်စမ်းကြည့်ပါ..."
- "ခေါ်ဆို၍မရနိုင်ပါ။ %s သည်အရေးပေါ်နံပါတ်တစ်ခု မဟုတ်ပါ။"
- "ခေါ်ဆို၍မရနိုင်ပါ။ အရေးပေါ်နံပါတ်တစ်ခုကို ခေါ်ဆိုပါ။"
- "ခေါ်ဆိုရန် ကီးဘုတ်ကိုအသုံးပြုပါ"
- "ခေါ်ဆိုမှု ခေတ္တရပ်ထားပါ"
- "ခေါ်ဆိုမှုကို ဆက်လုပ်ပါ"
- "ခေါ်ဆိုမှု အပြီးသတ်ပါ"
- "နံပါတ်အကွက် ပြပါ"
- "နံပါတ်အကွက် ဝှက်ထားပါ"
- "အသံပိတ်ပါ"
- "အသံပြန်ဖွင့်ပါ"
- "ခေါ်ဆိုမှုထည့်ပါ"
- "ခေါ်ဆိုမှုများကို ပေါင်းစည်းပါ"
- "ဖလှယ်ပါ"
- "ခေါ်ဆိုမှုများကို စီမံခန့်ခွဲပါ"
- "အစည်းအဝေးခေါ်ဆိုမှုကို စီမံခန့်ခွဲပါ"
- "မျက်နှာစုံညီစည်းဝေး ဖုန်းခေါ်ဆိုမှု"
- "စီမံခန့်ခွဲပါ"
- "အသံ"
- "ဗီဒီယို ခေါ်ဆိုမှု"
- "အသံခေါ်ဆိုမှုသို့ ပြောင်းပါ"
- "ကင်မရာပြောင်းပါ"
- "ကင်မရာဖွင့်ပါ"
- "ကင်မရာပိတ်ပါ"
- "နောက်ထပ် ရွေးစရာများ"
- "ပလေယာ စပါပြီ"
- "ပလေယာ ရပ်တန့်သွားပါပြီ"
- "ကင်မရာအဆင်သင့် မဖြစ်သေးပါ"
- "ကင်မရာအဆင်သင့်ဖြစ်ပါပြီ"
- "အမျိုးအမည်မသိ ခေါ်ဆိုမှုအချိန်ကာလ"
- "ဝန်ဆောင်မှု"
- "စနစ်ထည့်သွင်းမှုပြုလုပ်ပါ"
- "<မသတ်မှတ်ထားပါ>"
- "အခြားခေါ်ဆိုမှုဆက်တင်များ"
- "%s မှတစ်ဆင့် ခေါ်ဆိုခြင်း"
- "%s မှတစ်ဆင့်အဝင်ခေါ်ဆိုမှု"
- "အဆက်အသွယ်ဓာတ်ပုံ"
- "တသီးတသန့်ချိတ်ဆက်ရန်"
- "လိပ်စာရွေးပါ"
- "သင့်ကိုယ်ပိုင် စာသား ရေးပါ..."
- "မလုပ်တော့"
- "ပို့ပါ"
- "ဖြေကြားပါ"
- "SMS ပို့ပါ"
- "ငြင်းပယ်ပါ"
- "ဗီဒီယိုခေါ်ဆိုမှုအဖြစ် ဖြေကြားပါ"
- "အသံခေါ်ဆိုမှုအဖြစ် ဖြေကြားပါ"
- "ဗီဒီယိုခေါ်ဆိုမှုကို လက်ခံပါ"
- "ဗီဒီယိုခေါ်ဆိုမှုကို ငြင်းပယ်ပါ"
- "ဗီဒီယိုထုတ်လွှင့်ခြင်းတောင်းဆိုမှုကို လက်ခံပါ"
- "ဗီဒီယိုထုတ်လွှင့်ခြင်းတောင်းဆိုမှုကို ငြင်းပယ်ပါ"
- "ဗီဒီယိုလက်ခံရရှိမှုတောင်းဆိုချက်ကို လက်ခံပါ"
- "ဗီဒီယိုလက်ခံရရှိကြောင်းတောင်းဆိုမှုကို ငြင်းပယ်ပါ"
- "%s အတွက် အပေါ်ကို ပွတ်ဆွဲပါ"
- "%s အတွက် ဘယ်ဖက်ကို ပွတ်ဆွဲပါ"
- "%s အတွက် ညာဖက်ကို ပွတ်ဆွဲပါ"
- "%s အတွက် အောက်ကို ပွတ်ဆွဲပါ"
- "တုန်ခါပါ"
- "တုန်ခါပါ"
- "အသံ"
- "မူရင်း အသံ (%1$s)"
- "ဖုန်းမြည်သံ"
- "ဖုန်းမြည်စဉ် တုန်ခါပါ"
- "ဖုန်းမြည်သံ & တုန်ခါသံ"
- "အစည်းအဝေးခေါ်ဆိုမှုကို စီမံခန့်ခွဲပါ"
- "အရေးပေါ်နံပါတ်"
- "ပရိုဖိုင် ဓာတ်ပုံ"
- "ကင်မရာ ပိတ်ပါ"
- "%s မှတစ်ဆင့်"
- "မှတ်ချက်ကို ပို့လိုက်ပါပြီ"
- "မကြာသေးမီက မက်ဆေ့ဂျ်များ"
- "စီးပွားရေး အချက်အလက်"
- "%.1f မိုင်အကွာ"
- "%.1f ကီလိုမီတာအကွာ"
- "%1$s၊ %2$s"
- "%1$s - %2$s"
- "%1$s၊ %2$s"
- "မနက်ဖြန် %s ၌ဖွင့်မည်"
- "ယနေ့ %s ၌ဖွင့်မည်"
- "%s ၌ပိတ်ပါမည်"
- "ယနေ့ %s ၌ပိတ်ခဲ့သည်"
- "ယခုဖွင့်ပါ"
- "ယခုပိတ်ပါ"
- "မသင်္ကာဖွယ်ရာ စပမ်းခေါ်ဆိုသူ"
- "ဖုန်းခေါ်ဆိုမှု ပြီးဆုံးပါပြီ %1$s"
- "ဤနံပါတ်သည် သင့်ထံ ပထမဆုံးခေါ်ဆိုသော နံပါတ်ဖြစ်သည်။"
- "ယခုဖုန်းခေါ်ဆိုမှုသည် စပမ်းပို့သူဆီမှ ဖြစ်နိုင်သည်ဟု ထင်ပါသည်။"
- "စပမ်းကို ပိတ်ဆို့ပါ/သတင်းပေးပို့ပါ"
- "အဆက်အသွယ် ထည့်ပါ"
- "စပမ်း မဟုတ်ပါ"
-
diff --git a/InCallUI/res/values-nb/strings.xml b/InCallUI/res/values-nb/strings.xml
deleted file mode 100644
index d39e4d4416736ae85eb35f6f3d290b70a99a5d7d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-nb/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "På vent"
- "Ukjent"
- "Skjult nummer"
- "Telefonkiosk"
- "Konferansesamtale"
- "Anropet ble avbrutt"
- "Høyttaler"
- "Telefonhøyttaler"
- "Hodetelefoner med kabel"
- "Bluetooth"
- "Vil du sende disse lydene?\n"
- "Sender lydene\n"
- "Send"
- "Ja"
- "Nei"
- "Erstatt jokertegn med"
- "Konferansesamtale %s"
- "Nummeret til talepostkassen"
- "Ringer"
- "Ringer på nytt"
- "Konferansesamtale"
- "Innkommende anrop"
- "Innkommende jobbanrop"
- "Anropet er avsluttet"
- "På vent"
- "Legger på"
- "Anrop pågår"
- "Nummeret mitt er %s"
- "Kobler til video"
- "Videoanrop"
- "Ber om video"
- "Kan ikke koble til videoanropet"
- "Videoforespørselen er avvist"
- "Tilbakeringingsnummeret ditt\n %1$s"
- "Tilbakeringingsnummeret ditt for nødstilfeller\n %1$s"
- "Ringer"
- "Tapt anrop"
- "Tapte anrop"
- "%s tapte anrop"
- "Tapt anrop fra %s"
- "Pågående anrop"
- "Pågående jobbanrop"
- "Pågående Wi-Fi-anrop"
- "Pågående jobbanrop via Wi-Fi"
- "På vent"
- "Innkommende anrop"
- "Innkommende jobbanrop"
- "Innkommende Wi-Fi-anrop"
- "Innkommende jobbanrop via Wi-Fi"
- "Innkommende videoanrop"
- "Innkommende anrop fra en mulig useriøs oppringer"
- "Innkommende videoforespørsel"
- "Ny talepost"
- "Ny talepost (%d)"
- "Ring %s"
- "Nummeret til talepostkassen er ukjent"
- "Ingen tjeneste"
- "Det valgte nettverket (%s) er ikke tilgjengelig"
- "Svar"
- "Legg på"
- "Video"
- "Uten video"
- "Godta"
- "Avvis"
- "Ring tilbake"
- "Melding"
- "Samtale pågår på en annen enhet"
- "Overfør samtalen"
- "For å ringe, slå av flymodus først."
- "Ikke registrert på nettverket."
- "Mobilnettverket er ikke tilgjengelig."
- "For å ringe, skriv inn et gyldig nummer."
- "Kan ikke ringe."
- "Starter MMI-sekvens …"
- "Tjenesten støttes ikke."
- "Kan ikke bytte samtaler."
- "Kan ikke splitte opp anropet."
- "Kan ikke overføre."
- "Kan ikke opprette konferanse."
- "Kan ikke avvise anropet."
- "Kan ikke frigjøre samtale(r)."
- "SIP-anrop"
- "Nødanrop"
- "Slår på radioen …"
- "Ingen tjeneste. Prøver på nytt …"
- "Kan ikke ringe. %s er ikke et nødnummer."
- "Kan ikke ringe. Ring et nødnummer."
- "Bruk tastaturet for å ringe"
- "Sett anropet på vent"
- "Gjenoppta anropet"
- "Avslutt anropet"
- "Vis tastaturet"
- "Skjul tastaturet"
- "Slå av lyden"
- "Slå på lyden"
- "Legg til anrop"
- "Slå sammen anrop"
- "Bytt"
- "Administrer anrop"
- "Administrer konferansesamtale"
- "Konferansesamtale"
- "Administrer"
- "Lyd"
- "Videoanrop"
- "Bytt til taleanrop"
- "Bytt kamera"
- "Slå på kameraet"
- "Slå av kameraet"
- "Flere alternativer"
- "Avspilleren har startet"
- "Avspilleren har stoppet"
- "Kameraet er ikke klart"
- "Kameraet er klart"
- "Ukjent anrop"
- "Tjeneste"
- "Konfigurering"
- "<Ikke angitt>"
- "Andre anropsinnstillinger"
- "Ringer via %s"
- "Innkommende via %s"
- "kontaktbilde"
- "aktivér privat samtale"
- "velg kontakt"
- "Skriv ditt eget"
- "Avbryt"
- "Send"
- "Svar"
- "Send SMS"
- "Avslå"
- "Svar med video"
- "Svar uten video"
- "Godta videoforespørselen"
- "Avslå videoforespørselen"
- "Godta forespørselen om å sende video"
- "Avslå forespørselen om å sende video"
- "Godta forespørselen om å motta video"
- "Avslå forespørselen om å motta video"
- "Dra opp for %s."
- "Dra til venstre for å %s."
- "Dra til høyre for å %s."
- "Dra ned for å %s."
- "Vibrering"
- "Vibrering"
- "Lyd"
- "Standardlyd (%1$s)"
- "Telefonringelyd"
- "Vibrer når telefonen ringer"
- "Ringelyd og vibrering"
- "Administrer konferansesamtale"
- "Nødnummer"
- "Profilbilde"
- "Kameraet er slått av"
- "via %s"
- "Notatet er sendt"
- "Nylige meldinger"
- "Informasjon om bedriften"
- "%.1f mile unna"
- "%.1f km unna"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Åpner i morgen kl. %s"
- "Åpner i dag kl. %s"
- "Stenger kl. %s"
- "Stengte i dag kl. %s"
- "Åpen nå"
- "Stengt nå"
- "Mulig useriøst anrop"
- "Samtalen ble avsluttet %1$s"
- "Dette er første gang du blir oppringt fra dette nummeret."
- "Vi har mistanke om at dette anropet kommer fra en useriøs oppringer."
- "Blokkér/rapportér"
- "Legg til som kontakt"
- "Ikke useriøs"
-
diff --git a/InCallUI/res/values-ne/strings.xml b/InCallUI/res/values-ne/strings.xml
deleted file mode 100644
index 71c1ccae962cd2da0feb569c1b99787bab577abb..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ne/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "फोन"
- "होल्डमा"
- "अज्ञात"
- "निजी नम्बर"
- "पेफोन"
- "सम्मेलन कल"
- "कल ड्रप भयो"
- "स्पिकर"
- "हेन्डसेट इयरपिस"
- "तारसहितको हेडसेट"
- "ब्लुटुथ"
- "निम्न टोनहरू पठाउने हो?\n"
- "टोनहरू\n पठाउँदै"
- "पठाउनुहोस्"
- "हो"
- "होइन"
- "यसलाई वाइल्ड क्यारेक्टर राखेर बदल्नुहोस्"
- "सम्मेलन कल %s"
- "भ्वाइस मेल नम्बर"
- "डायल गर्दै"
- "पुन: डायल गर्दै"
- "सम्मेलन कल"
- "आगमन कल"
- "कार्यालयबाट आएको कल"
- "कल अन्त्य भयो"
- "होल्डमा छ"
- "फोन काट्दै"
- "कलमा"
- "मेरो नम्बर %s हो"
- "भिडियो जडान गरिँदै"
- "भिडियो कल"
- "भिडियोका लागि अनुरोध गर्दै"
- "भिडियो कलमा जडान गर्न सक्दैन"
- "भिडियो अनुरोध अस्वीकार गरियो"
- "तपाईंको कलब्याक नम्बर\n %1$s"
- "तपाईंको आपतकालीन कलब्याक नम्बर\n %1$s"
- "डायल गर्दै"
- "छुटेको कल"
- "छुटेका कलहरू"
- "%s छुटेका कलहरू"
- "%s बाट आएको छुटेको कल"
- "चलिरहेको कल"
- "चालु रहेको कार्यालयको कल"
- "चालु रहेको WI-Fi कल"
- "Wi-Fi मार्फत चालु रहेको कार्यालयको कल"
- "होल्डमा"
- "आगमन कल"
- "कार्यालयबाट आएको कल"
- "आगमन Wi-Fi कल"
- "Wi-Fi मार्फत कार्यालयबाट आएको कल"
- "आगमन भिडियो कल"
- "शंकास्पद आगमन स्प्याम कल"
- "आगमन भिडियो अनुरोध"
- "नयाँ भ्वाइस मेल"
- "नयाँ भ्वाइसमेल (%d)"
- "%s मा डायल गर्नुहोस्"
- "भ्वाइस मेल नम्बर अज्ञात छ"
- "कुनै सेवा छैन"
- "चयन गरिएको नेटवर्क (%s) अनुपलब्ध छ"
- "जवाफ दिनुहोस्"
- "राख्नुहोस्"
- "भिडियो"
- "आवाज"
- "स्वीकार गर्नुहोस्"
- "खारेज गर्नुहोस्"
- "कल फर्काउने"
- "सन्देश"
- "अर्को यन्त्रमा चलिरहेको कल"
- "कल स्थानान्तरण गर्नुहोस्"
- "कल गर्नका लागि, पहिले हवाइजहाज मोड बन्द गर्नुहोस्।"
- "नेटवर्कमा दर्ता भएको छैन।"
- "सेलुलर नेटवर्क उपलब्ध छैन।"
- "एक कल गर्नको लागि, मान्य नम्बर प्रविष्ट गर्नुहोस्।"
- "कल गर्न सकिंदैन।"
- "MMI अनुक्रम सुरु गर्दै..."
- "सेवा समर्थित छैन।"
- "कल स्विच गर्न सक्दैन।"
- "कल अलग गर्न सक्दैन।"
- "ट्रान्सफर गर्न सक्दैन।"
- "सम्मेलन गर्न सक्दैन।"
- "कल अस्वीकार गर्न सक्दैन।"
- "कल (हरू) जारी गर्न सकिंदैन।"
- "SIP कल"
- "आपतकालीन कल"
- "रेडियो खोल्दै..."
- "कुनै सेवा छैन। फेरि प्रयास गर्दै..."
- "कल गर्न सकिंदैन। %s आपतकालीन नम्बर होइन।"
- "कल गर्न सकिंदैन। आपतकालीन नम्बर डायल गर्नुहोस्।"
- "डायल गर्न किबोर्ड प्रयोग गर्नुहोस्"
- "कललाई होल्ड गर्नुहोस्"
- "कललाई पुन: निरन्तरता दिनुहोस्"
- "कल अन्त्य गर्नुहोस्"
- "डायलप्याड देखाउनुहोस्"
- "डायलप्याड लुकाउनुहोस्"
- "मौन"
- "अनम्यूट गर्नुहोस्"
- "कल थप्नुहोस्"
- "कलहरू मर्ज गर्नुहोस्"
- "स्वाप"
- "कलहरूको प्रबन्ध मिलाउनुहोस्"
- "सम्मेलन कलको प्रबन्ध मिलाउनहोस्"
- "सम्मेलन कल"
- "व्यवस्थापन गर्नुहोस्"
- "अडियो"
- "भिडियो कल"
- "आवाज कलमा परिवर्तन गर्नुहोस्"
- "क्यामेरा स्विच गर्नुहोस्"
- "क्यामेरालाई सक्रिय गर्नुहोस्"
- "क्यामेरालाई निष्क्रिय पार्नुहोस्"
- "थप विकल्पहरू"
- "प्लेयर सुरु भयो"
- "प्लेयर रोकियो"
- "क्यामेरा तयार छैन"
- "क्यामेरा तयार छ"
- "अज्ञात कल सत्र घटना"
- "सेवा"
- "सेटअप"
- "<सेट गरिएको छैन>"
- "अन्य कल सेटिङहरू"
- "%s मार्फत कल गर्दै"
- "%s मार्फत आगमन"
- "सम्पर्क तस्बिर"
- "निजी कलमा जानुहोस्"
- "सम्पर्क चयन गर्नुहोस्"
- "तपाईंको आफ्नै लेख्नुहोस्..."
- "रद्द गर्नुहोस्"
- "पठाउनुहोस्"
- "जवाफ दिनुहोस्"
- "SMS पठाउनुहोस्"
- "अस्वीकार गर्नुहोस्"
- "भिडियो कलको रूपमा जवाफ दिनुहोस्"
- "अडियो कलको रूपमा जवाफ दिनुहोस्"
- "भिडियो अनुरोध स्वीकार गर्नुहोस्"
- "भिडियो अनुरोध अस्वीकार गर्नुहोस्"
- "भिडियो प्रसारण गर्ने अनुरोध स्वीकार गर्नुहोस्"
- "भिडियो प्रसारण गर्ने अनुरोध अस्वीकार गर्नुहोस्"
- "भिडियो प्राप्त गर्ने अनुरोधलाई स्वीकार गर्नुहोस्"
- "भिडियो प्राप्त गर्ने अनुरोध अस्वीकार गर्नुहोस्"
- "%s को लागि माथि स्लाइड गर्नुहोस्।"
- "%s को लागि बायाँ स्लाइड गर्नुहोस्।"
- "%s को लागि दायाँ स्लाइड गर्नुहोस्।"
- "%s को लागि तल स्लाइड गर्नुहोस्।"
- "कम्पन हुने"
- "कम्पन हुने"
- "आवाज"
- "पूर्वनिर्धारित ध्वनि (%1$s)"
- "फोनको रिङटोन"
- "घन्टी बज्दा कम्पन गराउनुहोस्"
- "रिङटोन & कम्पन"
- "सम्मेलन कलको प्रबन्ध मिलाउनुहोस्"
- "आपतकालीन नम्बर"
- "प्रोफाइल तस्बिर"
- "क्यामेरा बन्द छ"
- "%s बाट"
- "नोट पठाइयो"
- "भर्खरैका सन्देशहरू"
- "व्यवसाय बारे जानकारी"
- "%.1f माइल टाढा"
- "%.1f किलोमिटर टाढा"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "भोलि %s मा खुल्छ"
- "आज %s मा खुल्छ"
- "%s मा बन्द हुन्छ"
- "आज %s मा बन्द भयो"
- "अहिले खुला छ"
- "अब बन्द भयो"
- "शंकास्पद स्प्याम कलर"
- "कल समाप्त भयो %1$s"
- "यो नम्बरबाट तपाईँलाई फोन आएको यो पहिलो पटक हो।"
- "हामीले यो कल स्प्यामर हुन सक्ने आशङ्का गर्यौँ।"
- "स्प्याम रोक्नु्/रिपोर्ट गर्ने"
- "सम्पर्क थप्नुहोस्"
- "स्प्याम होइन"
-
diff --git a/InCallUI/res/values-nl/strings.xml b/InCallUI/res/values-nl/strings.xml
deleted file mode 100644
index 9eaf556c0287c928f074a5f49408adf876a2edfe..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-nl/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefoon"
- "In de wacht"
- "Onbekend"
- "Privénummer"
- "Betaaltelefoon"
- "Telefonische vergadering"
- "Oproep beëindigd"
- "Luidspreker"
- "Oortelefoon van handset"
- "Bedrade headset"
- "Bluetooth"
- "De volgende tonen verzenden?\n"
- "Nummers verzenden\n"
- "Verzenden"
- "Ja"
- "Nee"
- "Jokerteken vervangen door"
- "Telefonische vergadering %s"
- "Voicemailnummer"
- "Kiezen"
- "Opnieuw bellen"
- "Telefonische vergadering"
- "Inkomende oproep"
- "Inkom. zakelijke oproep"
- "Oproep beëindigd"
- "In de wacht"
- "Ophangen"
- "In gesprek"
- "Mijn nummer is %s"
- "Verbinding maken met video"
- "Videogesprek"
- "Video aanvragen"
- "Kan geen videogesprek starten"
- "Videoverzoek geweigerd"
- "Je terugbelnummer\n %1$s"
- "Je terugbelnummer bij alarm\n %1$s"
- "Kiezen"
- "Gemiste oproep"
- "Gemiste oproepen"
- "%s gemiste oproepen"
- "Gemiste oproep van %s"
- "Actieve oproep"
- "Actieve zakelijke oproep"
- "Actieve wifi-oproep"
- "Actieve zakelijke oproep via wifi"
- "In de wacht"
- "Inkomende oproep"
- "Inkomende zakelijke oproep"
- "Inkomende wifi-oproep"
- "Inkomende zakelijke oproep via wifi"
- "Inkomend videogesprek"
- "Inkomende vermoedelijke spamoproep"
- "Inkomend videoverzoek"
- "Nieuwe voicemail"
- "Nieuwe voicemail (%d)"
- "%s bellen"
- "Voicemailnummer onbekend"
- "Geen service"
- "Geselecteerd netwerk (%s) niet beschikbaar"
- "Beantwoorden"
- "Ophangen"
- "Video"
- "Spraak"
- "Accepteren"
- "Sluiten"
- "Terugbellen"
- "Bericht"
- "Actief gesprek op een ander apparaat"
- "Gesprek doorschakelen"
- "Als je wilt bellen, moet je eerst de vliegtuigmodus uitschakelen."
- "Niet geregistreerd op netwerk."
- "Mobiel netwerk niet beschikbaar."
- "Als je wilt bellen, moet je een geldig nummer invoeren."
- "Kan niet bellen."
- "MMI-reeks starten..."
- "Service wordt niet ondersteund."
- "Kan niet schakelen tussen oproepen."
- "Kan oproep niet scheiden."
- "Kan niet doorschakelen."
- "Telefonische vergadering niet mogelijk."
- "Kan oproep niet weigeren."
- "Kan oproep(en) niet vrijgeven."
- "SIP-oproep"
- "Noodoproep"
- "Radio inschakelen…"
- "Geen bereik. Opnieuw proberen…"
- "Kan niet bellen. %s is geen alarmnummer."
- "Kan niet bellen. Bel een alarmnummer."
- "Toetsen gebruiken om te bellen"
- "Oproep in de wacht zetten"
- "Oproep hervatten"
- "Oproep beëindigen"
- "Toetsenblok weergeven"
- "Toetsenblok verbergen"
- "Dempen"
- "Dempen opheffen"
- "Oproep toevoegen"
- "Samenvoegen"
- "Wisselen"
- "Oproepen beheren"
- "Telef. vergadering beheren"
- "Telefonische vergadering"
- "Beheren"
- "Audio"
- "Vid.gespr."
- "Wijzigen in spraakoproep"
- "Van camera wisselen"
- "Camera inschakelen"
- "Camera uitschakelen"
- "Meer opties"
- "Speler gestart"
- "Speler gestopt"
- "Camera niet gereed"
- "Camera gereed"
- "Onbekende oproepsessiegebeurtenis"
- "Service"
- "Configuratie"
- "<Niet ingesteld>"
- "Andere instellingen voor bellen"
- "Bellen via %s"
- "Inkomend via %s"
- "contactfoto"
- "privé"
- "contact selecteren"
- "Eigen reactie opstellen..."
- "Annuleren"
- "Verzenden"
- "Beantwoorden"
- "Sms verzenden"
- "Weigeren"
- "Beantwoorden als videogesprek"
- "Beantwoorden als audiogesprek"
- "Videoverzoek accepteren"
- "Videoverzoek weigeren"
- "Verzoek voor video-overdracht accepteren"
- "Verzoek voor video-overdracht weigeren"
- "Verzoek voor video-ontvangst accepteren"
- "Verzoek voor video-ontvangst weigeren"
- "Veeg omhoog voor %s."
- "Veeg naar links voor %s."
- "Veeg naar rechts voor %s."
- "Veeg omlaag voor %s."
- "Trillen"
- "Trillen"
- "Geluid"
- "Standaardgeluid (%1$s)"
- "Beltoon telefoon"
- "Trillen bij bellen"
- "Beltoon en trillen"
- "Telefonische vergadering beheren"
- "Alarmnummer"
- "Profielfoto"
- "Camera uit"
- "via %s"
- "Notitie verzonden"
- "Recente berichten"
- "Bedrijfsinformatie"
- "%.1f mijl hiervandaan"
- "%.1f km hiervandaan"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Gaat morgen open om %s"
- "Gaat vandaag open om %s"
- "Sluit om %s"
- "Vandaag gesloten vanaf %s"
- "Nu geopend"
- "Nu gesloten"
- "Vermoedelijke spambeller"
- "Oproep beëindigd %1$s"
- "Dit is de eerste keer dat je bent gebeld door dit nummer."
- "We vermoedden dat deze oproep afkomstig was van een spammer."
- "Blokk./spam melden"
- "Contact toevoegen"
- "Geen spam"
-
diff --git a/InCallUI/res/values-pa/strings.xml b/InCallUI/res/values-pa/strings.xml
deleted file mode 100644
index 318fc4cdccd2328a3982ee5435a55ec287102f7d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-pa/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ਫੋਨ"
- "ਰੋਕੀ ਗਈ"
- "ਅਗਿਆਤ"
- "ਨਿੱਜੀ ਨੰਬਰ"
- "ਪੇ-ਫੋਨ"
- "ਕਾਨਫਰੰਸ ਕਾਲ"
- "ਕਾਲ ਡ੍ਰੌਪ ਹੋਈ"
- "ਸਪੀਕਰ"
- "ਹੈੱਡਸੈੱਟ ਈਯਰਪੀਸ"
- "ਵਾਇਰ ਵਾਲਾ ਹੈੱਡਸੈੱਟ"
- "ਬਲੂਟੁੱਥ"
- "ਕੀ ਅੱਗੇ ਦਿੱਤੀਆਂ ਗਈਆਂ ਧੁਨੀਆਂ ਭੇਜਣੀਆਂ ਹਨ?\n"
- "ਧੁਨੀਆਂ ਭੇਜੀਆਂ ਜਾ ਰਹੀਆਂ ਹਨ\n"
- "ਭੇਜੋ"
- "ਹਾਂ"
- "ਨਹੀਂ"
- "ਵਾਈਲਡ ਅੱਖਰ ਨੂੰ ਇਸ ਨਾਲ ਬਦਲੋ"
- "ਕਾਨਫਰੰਸ ਕਾਲ %s"
- "ਵੌਇਸਮੇਲ ਨੰਬਰ"
- "ਡਾਇਲ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"
- "ਦੁਬਾਰਾ ਡਾਇਲ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"
- "ਕਾਨਫਰੰਸ ਕਾਲ"
- "ਆ ਰਹੀ ਕਾਲ"
- "ਕੰਮ ਸੰਬੰਧਿਤ ਆ ਰਹੀ ਕਾਲ"
- "ਕਾਲ ਸਮਾਪਤ ਹੋਈ"
- "ਰੋਕੀ ਗਈ"
- "ਰੋਕੀ ਜਾ ਰਹੀ ਹੈ"
- "ਚਾਲੂ ਕਾਲ"
- "ਮੇਰਾ ਨੰਬਰ %s ਹੈ"
- "ਵੀਡੀਓ ਨੂੰ ਕਨੈਕਟ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"
- "ਵੀਡੀਓ ਕਾਲ"
- "ਵੀਡੀਓ ਲਈ ਬੇਨਤੀ ਕੀਤੀ ਜਾ ਰਹੀ ਹੈ"
- "ਵੀਡੀਓ ਕਾਲ ਕਨੈਕਟ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ"
- "ਵੀਡੀਓ ਬੇਨਤੀ ਅਸਵੀਕਾਰ ਕੀਤੀ ਗਈ"
- "ਤੁਹਾਡਾ ਕਾਲਬੈਕ ਨੰਬਰ \n %1$s"
- "ਤੁਹਾਡਾ ਐਮਰਜੈਂਸੀ ਕਾਲਬੈਕ ਨੰਬਰ\n %1$s"
- "ਡਾਇਲ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ"
- "ਖੁੰਝੀ ਹੋਈ ਕਾਲ"
- "ਖੁੰਝੀਆਂ ਹੋਈਆਂ ਕਾਲਾਂ"
- "%s ਖੁੰਝੀਆਂ ਹੋਈਆਂ ਕਾਲਾਂ"
- "%s ਤੋਂ ਖੁੰਝੀ ਹੋਈ ਕਾਲ"
- "ਜਾਰੀ ਕਾਲ"
- "ਕੰਮ ਸੰਬੰਧਿਤ ਜਾਰੀ ਕਾਲ"
- "ਜਾਰੀ Wi-Fi ਕਾਲ"
- "ਕੰਮ ਸੰਬੰਧਿਤ ਜਾਰੀ Wi-Fi ਕਾਲ"
- "ਰੋਕੀ ਗਈ"
- "ਆ ਰਹੀ ਕਾਲ"
- "ਕੰਮ ਸੰਬੰਧਿਤ ਆ ਰਹੀ ਕਾਲ"
- "ਆ ਰਹੀ Wi-Fi ਕਾਲ"
- "ਕੰਮ ਸੰਬੰਧਿਤ ਆ ਰਹੀ Wi-Fi ਕਾਲ"
- "ਆ ਰਹੀ ਵੀਡੀਓ ਕਾਲ"
- "ਸ਼ੱਕੀ ਸਪੈਮ ਕਾਲ ਆ ਰਹੀ ਹੈ"
- "ਆ ਰਹੀ ਵੀਡੀਓ ਬੇਨਤੀ"
- "ਨਵੀਂ ਵੌਇਸਮੇਲ"
- "ਨਵੀਂ ਵੌਇਸਮੇਲ (%d)"
- "%s ਡਾਇਲ ਕਰੋ"
- "ਵੌਇਸਮੇਲ ਨੰਬਰ ਅਗਿਆਤ"
- "ਕੋਈ ਸੇਵਾ ਨਹੀਂ"
- "ਚੁਣਿਆ ਗਿਆ ਨੈੱਟਵਰਕ (%s) ਉਪਲਬਧ ਨਹੀਂ ਹੈ"
- "ਜਵਾਬ ਦਿਓ"
- "ਰੋਕੋ"
- "ਵੀਡੀਓ"
- "ਵੌਇਸ"
- "ਸਵੀਕਾਰ ਕਰੋ"
- "ਰੱਦ ਕਰੋ"
- "ਵਾਪਸ ਕਾਲ ਕਰੋ"
- "ਸੁਨੇਹਾ"
- "ਕਿਸੇ ਹੋਰ ਡੀਵਾਈਸ \'ਤੇ ਜਾਰੀ ਕਾਲ"
- "ਕਾਲ ਟ੍ਰਾਂਸਫਰ ਕਰੋ"
- "ਇੱਕ ਕਾਲ ਕਰਨ ਲਈ, ਪਹਿਲਾਂ ਜਹਾਜ਼ ਮੋਡ ਬੰਦ ਕਰੋ।"
- "ਨੈੱਟਵਰਕ \'ਤੇ ਰਜਿਸਟਰ ਨਹੀਂ।"
- "ਸੈਲਿਊਲਰ ਨੈੱਟਵਰਕ ਉਪਲਬਧ ਨਹੀਂ ਹੈ।"
- "ਇੱਕ ਕਾਲ ਕਰਨ ਲਈ, ਇੱਕ ਵੈਧ ਨੰਬਰ ਦਾਖਲ ਕਰੋ।"
- "ਕਾਲ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ।"
- "MMI ਕੜੀ ਨੂੰ ਸ਼ੁਰੂ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ…"
- "ਸੇਵਾ ਸਮਰਥਿਤ ਨਹੀਂ ਹੈ।"
- "ਕਾਲਾਂ ਸਵਿੱਚ ਨਹੀਂ ਕੀਤੀਆਂ ਜਾ ਸਕਦੀਆਂ।"
- "ਵੱਖਰੇ ਤੌਰ \'ਤੇ ਕਾਲ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ।"
- "ਕਾਲ ਟ੍ਰਾਂਸਫਰ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ।"
- "ਕਾਨਫਰੰਸ ਕਾਲ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ।"
- "ਕਾਲ ਰੱਦ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ।"
- "ਕਾਲ(ਲਾਂ) ਰੀਲੀਜ਼ ਨਹੀਂ ਕੀਤੀਆਂ ਜਾ ਸਕਦੀਆਂ।"
- "SIP ਕਾਲ"
- "ਐਮਰਜੈਂਸੀ ਕਾਲ"
- "ਰੇਡੀਓ ਚਾਲੂ ਕੀਤਾ ਜਾ ਰਿਹਾ ਹੈ…"
- "ਕੋਈ ਸੇਵਾ ਨਹੀਂ। ਦੁਬਾਰਾ ਕੋਸ਼ਿਸ਼ ਕੀਤੀ ਜਾ ਰਹੀ ਹੈ…"
- "ਕਾਲ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ। %s ਇੱਕ ਐਮਰਜੈਂਸੀ ਨੰਬਰ ਨਹੀਂ ਹੈ।"
- "ਕਾਲ ਨਹੀਂ ਕੀਤੀ ਜਾ ਸਕਦੀ। ਇੱਕ ਐਮਰਜੈਂਸੀ ਨੰਬਰ ਡਾਇਲ ਕਰੋ।"
- "ਡਾਇਲ ਕਰਨ ਲਈ ਕੀ-ਬੋਰਡ ਵਰਤੋ"
- "ਕਾਲ ਰੋਕੋ"
- "ਕਾਲ ਮੁੜ-ਸ਼ੁਰੂ ਕਰੋ"
- "ਕਾਲ ਸਮਾਪਤ ਕਰੋ"
- "ਡਾਇਲਪੈਡ ਵਿਖਾਓ"
- "ਡਾਇਲਪੈਡ ਲੁਕਾਓ"
- "ਮਿਊਟ ਕਰੋ"
- "ਅਣਮਿਊਟ ਕਰੋ"
- "ਕਾਲ ਸ਼ਾਮਲ ਕਰੋ"
- "ਕਾਲਾਂ ਸ਼ਾਮਲ ਕਰੋ"
- "ਅਦਲਾ-ਬਦਲੀ ਕਰੋ"
- "ਕਾਲਾਂ ਦਾ ਪ੍ਰਬੰਧਨ ਕਰੋ"
- "ਕਾਨਫਰੰਸ ਕਾਲ ਦਾ ਪ੍ਰਬੰਧਨ ਕਰੋ"
- "ਕਾਨਫਰੰਸ ਕਾਲ"
- "ਪ੍ਰਬੰਧਨ ਕਰੋ"
- "ਔਡੀਓ"
- "ਵੀਡੀਓ ਕਾਲ"
- "ਵੌਇਸ ਕਾਲ ਵਿੱਚ ਬਦਲੋ"
- "ਕੈਮਰੇ \'ਤੇ ਬਦਲੋ"
- "ਕੈਮਰਾ ਚਾਲੂ ਕਰੋ"
- "ਕੈਮਰਾ ਬੰਦ ਕਰੋ"
- "ਹੋਰ ਚੋਣਾਂ"
- "ਪਲੇਅਰ ਸ਼ੁਰੂ ਹੋ ਗਿਆ"
- "ਪਲੇਅਰ ਰੁਕ ਗਿਆ"
- "ਕੈਮਰਾ ਤਿਆਰ ਨਹੀਂ ਹੈ"
- "ਕੈਮਰਾ ਤਿਆਰ ਹੈ"
- "ਅਗਿਆਤ ਕਾਲ ਸੈਸ਼ਨ ਵਰਤਾਰਾ"
- "ਸੇਵਾ"
- "ਸਥਾਪਨਾ"
- "<ਸੈੱਟ ਨਹੀਂ>"
- "ਹੋਰ ਕਾਲ ਸੈਟਿੰਗਾਂ"
- "%s ਰਾਹੀਂ ਕਾਲ ਕੀਤੀ ਜਾ ਰਹੀ ਹੈ"
- "%s ਰਾਹੀਂ ਆ ਰਹੀਆਂ ਕਾਲਾਂ"
- "ਸੰਪਰਕ ਫ਼ੋਟੋ"
- "ਨਿੱਜੀ ਵਿੱਚ ਬਦਲੋ"
- "ਸੰਪਰਕ ਚੁਣੋ"
- "ਆਪਣੇ ਆਪ ਲਿਖੋ..."
- "ਰੱਦ ਕਰੋ"
- "ਭੇਜੋ"
- "ਜਵਾਬ ਦਿਓ"
- "SMS ਭੇਜੋ"
- "ਅਸਵੀਕਾਰ ਕਰੋ"
- "ਵੀਡੀਓ ਕਾਲ ਵਜੋਂ ਜਵਾਬ ਦਿਓ"
- "ਔਡੀਓ ਕਾਲ ਵਜੋਂ ਜਵਾਬ ਦਿਓ"
- "ਵੀਡੀਓ ਬੇਨਤੀ ਸਵੀਕਾਰ ਕਰੋ"
- "ਵੀਡੀਓ ਬੇਨਤੀ ਨੂੰ ਅਸਵੀਕਾਰ ਕਰੋ"
- "ਵੀਡੀਓ ਟ੍ਰਾਂਸਮਿਟ ਬੇਨਤੀ ਨੂੰ ਸਵੀਕਾਰ ਕਰੋ"
- "ਵੀਡੀਓ ਟ੍ਰਾਂਸਮਿਟ ਬੇਨਤੀ ਨੂੰ ਅਸਵੀਕਾਰ ਕਰੋ"
- "ਵੀਡੀਓ ਪ੍ਰਾਪਤ ਕਰਨ ਦੀ ਬੇਨਤੀ ਨੂੰ ਸਵੀਕਾਰ ਕਰੋ"
- "ਵੀਡੀਓ ਪ੍ਰਾਪਤ ਕਰਨ ਦੀ ਬੇਨਤੀ ਨੂੰ ਅਸਵੀਕਾਰ ਕਰੋ"
- "%s ਲਈ ਉੱਤੇ ਸਲਾਈਡ ਕਰੋ।"
- "%s ਲਈ ਖੱਬੇ ਪਾਸੇ ਸਲਾਈਡ ਕਰੋ।"
- "%s ਲਈ ਸੱਜੇ ਪਾਸੇ ਸਲਾਈਡ ਕਰੋ।"
- "%s ਲਈ ਹੇਠਾਂ ਸਲਾਈਡ ਕਰੋ।"
- "ਥਰਥਰਾਹਟ ਕਰੋ"
- "ਥਰਥਰਾਹਟ ਕਰੋ"
- "ਧੁਨੀ"
- "ਪੂਰਵ-ਨਿਰਧਾਰਤ ਧੁਨੀ (%1$s)"
- "ਫੋਨ ਰਿੰਗਟੋਨ"
- "ਘੰਟੀ ਵੱਜਣ \'ਤੇ ਥਰਥਰਾਹਟ ਕਰੋ"
- "ਰਿੰਗਟੋਨ ਅਤੇ ਥਰਥਰਾਹਟ"
- "ਕਾਨਫਰੰਸ ਕਾਲ ਦਾ ਪ੍ਰਬੰਧਨ ਕਰੋ"
- "ਐਮਰਜੈਂਸੀ ਨੰਬਰ"
- "ਪ੍ਰੋਫਾਈਲ ਫ਼ੋਟੋ"
- "ਕੈਮਰਾ ਬੰਦ ਹੈ"
- "%s ਰਾਹੀਂ"
- "ਨੋਟ-ਕਥਨ ਭੇਜਿਆ ਗਿਆ"
- "ਹਾਲੀਆ ਸੁਨੇਹੇ"
- "ਵਪਾਰ ਜਾਣਕਾਰੀ"
- "%.1f ਮੀਲ ਦੂਰ"
- "%.1f ਕਿ.ਮੀ. ਦੂਰ"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "ਕੱਲ੍ਹ %s ਵਜੇ ਖੁੱਲ੍ਹੇਗਾ"
- "ਅੱਜ %s ਵਜੇ ਖੁੱਲ੍ਹੇਗਾ"
- "%s ਵਜੇ ਬੰਦ ਹੋਵੇਗਾ"
- "ਅੱਜ %s ਵਜੇ ਬੰਦ ਹੋਇਆ"
- "ਹੁਣ ਖੁੱਲ੍ਹਾ ਹੈ"
- "ਹੁਣ ਬੰਦ ਹੈ"
- "ਸ਼ੱਕੀ ਸਪੈਮ ਕਾਲਰ"
- "%1$s ਦੀ ਕਾਲ ਸਮਾਪਤ ਹੋਈ"
- "ਇਸ ਨੰਬਰ ਤੋਂ ਤੁਹਾਨੂੰ ਪਹਿਲੀ ਵਾਰ ਕਾਲ ਪ੍ਰਾਪਤ ਹੋਈ ਹੈ।"
- "ਸਾਨੂੰ ਇਹ ਕਾਲ ਇੱਕ ਸਪੈਮਰ ਜਾਪਦੀ ਸੀ।"
- "ਸਪੈਮ ਨੂੰ ਬਲੌਕ ਕਰੋ/ਰਿਪੋਰਟ ਕਰੋ"
- "ਸੰਪਰਕ ਸ਼ਾਮਲ ਕਰੋ"
- "ਸਪੈਮ ਨਹੀਂ"
-
diff --git a/InCallUI/res/values-pl/strings.xml b/InCallUI/res/values-pl/strings.xml
deleted file mode 100644
index f9f78ec79f083a1ae59ec39f559579228ae5219b..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-pl/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Wstrzymane"
- "Nieznany"
- "Numer prywatny"
- "Automat telefoniczny"
- "Połączenie konferencyjne"
- "Połączenie przerwane"
- "Głośnik"
- "Słuchawka telefonu"
- "Przewodowy zestaw słuchawkowy"
- "Bluetooth"
- "Wysłać te tony?\n"
- "Wysyłanie tonów\n"
- "Wyślij"
- "Tak"
- "Nie"
- "Zastąp symbol wieloznaczny"
- "Połączenie konferencyjne: %s"
- "Numer poczty głosowej"
- "Wybieranie"
- "Ponowne wybieranie numeru"
- "Połączenie konferencyjne"
- "Połączenie przychodzące"
- "Przychodzące połączenie służbowe"
- "Połączenie zakończone"
- "Wstrzymane"
- "Rozłączanie"
- "Trwa połączenie"
- "Mój numer to %s"
- "Rozpoczynanie rozmowy wideo"
- "Rozmowa wideo"
- "Wysyłanie żądania wideo"
- "Nie można nawiązać połączenia wideo"
- "Żądanie wideo zostało odrzucone"
- "Twój numer oddzwaniania\n %1$s"
- "Twój numer oddzwaniania dla połączeń alarmowych\n %1$s"
- "Wybieranie"
- "Nieodebrane połączenie"
- "Nieodebrane połączenia"
- "Nieodebrane połączenia: %s"
- "Nieodebrane połączenie od: %s"
- "Trwa połączenie"
- "Trwa połączenie służbowe"
- "Trwa połączenie przez Wi-Fi"
- "Trwa połączenie służbowe przez Wi-Fi"
- "Wstrzymane"
- "Połączenie przychodzące"
- "Przychodzące połączenie służbowe"
- "Przychodzące połączenie przez Wi-Fi"
- "Przychodzące połączenie służbowe przez Wi-Fi"
- "Przychodząca rozmowa wideo"
- "Przychodzące połączenie podejrzanie o spam"
- "Przychodzące żądanie wideo"
- "Nowa poczta głosowa"
- "Nowa poczta głosowa (%d)"
- "Wybierz numer %s"
- "Nieznany numer poczty głosowej"
- "Brak usługi"
- "Wybrana sieć (%s) jest niedostępna"
- "Odbierz"
- "Rozłącz"
- "Wideo"
- "Głos"
- "Zaakceptuj"
- "Odrzuć"
- "Oddzwoń"
- "Wyślij SMS-a"
- "Trwająca rozmowa na innym urządzeniu"
- "Przełącz rozmowę"
- "Aby rozpocząć połączenie, wyłącz najpierw tryb samolotowy."
- "Nie zarejestrowano w sieci."
- "Sieć komórkowa jest niedostępna."
- "Aby zadzwonić, wybierz prawidłowy numer."
- "Nie można dzwonić."
- "Rozpoczynam sekwencję MMI…"
- "Usługa nie jest obsługiwana."
- "Nie można przełączyć połączeń."
- "Nie można rozdzielić połączenia."
- "Nie można przekazać."
- "Nie można nawiązać połączenia konferencyjnego."
- "Nie można odrzucić połączenia."
- "Nie można zwolnić połączeń."
- "Połączenie SIP"
- "Połączenie alarmowe"
- "Włączam radio…"
- "Brak sieci. Próbuję ponownie…"
- "Nie można dzwonić. %s nie jest numerem alarmowym."
- "Nie można dzwonić. Wybierz numer alarmowy."
- "Aby zadzwonić, użyj klawiatury"
- "Wstrzymaj połączenie"
- "Wznów połączenie"
- "Zakończ połączenie"
- "Pokaż klawiaturę"
- "Ukryj klawiaturę"
- "Wycisz"
- "Wyłącz wyciszenie"
- "Dodaj połączenie"
- "Scal połączenia"
- "Przełącz"
- "Zarządzaj połączeniami"
- "Zarządzaj połączeniem konferencyjnym"
- "Połączenie konferencyjne"
- "Zarządzaj"
- "Dźwięk"
- "Rozmowa wideo"
- "Zmień na połączenie głosowe"
- "Przełącz kamerę"
- "Włącz kamerę"
- "Wyłącz kamerę"
- "Więcej opcji"
- "Odtwarzacz włączony"
- "Odtwarzacz zatrzymany"
- "Kamera niegotowa"
- "Kamera gotowa"
- "Nieznane zdarzenie sesji połączenia"
- "Usługa"
- "Konfiguracja"
- "<Nie ustawiono>"
- "Inne ustawienia połączeń"
- "Nawiązywanie połączenia przez %s"
- "Przychodzące z sieci %s"
- "zdjęcie kontaktu"
- "przejdź do rozmowy prywatnej"
- "wybierz kontakt"
- "Napisz własną..."
- "Anuluj"
- "Wyślij"
- "Odbierz"
- "Wyślij SMS-a"
- "Odrzuć"
- "Odbierz jako rozmowę wideo"
- "Odbierz jako rozmowę audio"
- "Zaakceptuj żądanie wideo"
- "Odrzuć żądanie wideo"
- "Zaakceptuj wysyłanie obrazu wideo"
- "Odrzuć wysyłanie obrazu wideo"
- "Zaakceptuj odbieranie obrazu wideo"
- "Odrzuć odbieranie obrazu wideo"
- "Przesuń w górę: %s."
- "Przesuń w lewo: %s."
- "Przesuń w prawo: %s."
- "Przesuń w dół: %s."
- "Wibracje"
- "Wibracje"
- "Dźwięk"
- "Domyślny dźwięk (%1$s)"
- "Dzwonek telefonu"
- "Wibracje z dzwonkiem"
- "Dzwonek i wibracje"
- "Zarządzaj połączeniem konferencyjnym"
- "Numer alarmowy"
- "Zdjęcie profilowe"
- "Kamera wyłączona"
- "z %s"
- "Notatka wysłana"
- "Ostatnie wiadomości"
- "Informacje o firmie"
- "%.1f mil(e) stąd"
- "%.1f km stąd"
- "%1$s, %2$s"
- "%1$s-%2$s"
- "%1$s, %2$s"
- "Otwarte jutro od %s"
- "Otwarte dzisiaj od %s"
- "Zamknięte od %s"
- "Zamknięte dzisiaj od %s"
- "Teraz otwarte"
- "Teraz zamknięte"
- "Podejrzenie spamu"
- "Połączenie zakończone (%1$s)"
- "To pierwsze połączenie z tego numeru."
- "Podejrzewamy, że to połączenie to spam."
- "Zablokuj/zgłoś spam"
- "Dodaj kontakt"
- "To nie spam"
-
diff --git a/InCallUI/res/values-pt-rBR/strings.xml b/InCallUI/res/values-pt-rBR/strings.xml
deleted file mode 100644
index 5271f54ccdb625154812a03d19147c03bf779078..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-pt-rBR/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefone"
- "Em espera"
- "Desconhecido"
- "Número privado"
- "Chamada a cobrar"
- "Teleconferência"
- "A chamada caiu."
- "Alto-falante"
- "Minifone do aparelho"
- "Fone de ouvido com fio"
- "Bluetooth"
- "Enviar os seguintes tons?\n"
- "Enviando tons\n"
- "Enviar"
- "Sim"
- "Não"
- "Substituir caractere curinga por"
- "Teleconferência %s"
- "Número do correio de voz"
- "Discando"
- "Rediscando"
- "Teleconferência"
- "Chamada recebida"
- "Chamada trabalho recebida"
- "Chamada encerrada"
- "Em espera"
- "Desligando"
- "Em chamada"
- "Meu número é %s"
- "Conectando vídeo"
- "Videochamada"
- "Solicitando vídeo"
- "Não é possível conectar a videochamada"
- "Solicitação de vídeo rejeitada"
- "Seu número de retorno de chamada\n %1$s"
- "Seu número de retorno de chamada de emergência\n %1$s"
- "Discando"
- "Chamada perdida"
- "Chamadas perdidas"
- "%s chamadas perdidas"
- "Chamada perdida de %s"
- "Chamanda em andamento"
- "Chamada de trabalho em andamento"
- "Chamada por Wi-Fi em andamento"
- "Chamada de trabalho por Wi-Fi em andamento"
- "Em espera"
- "Chamada recebida"
- "Chamada de trabalho recebida"
- "Chamada por Wi-Fi recebida"
- "Chamada de trabalho recebida por Wi-Fi"
- "Videochamada recebida"
- "Chamada recebida suspeita (spam)"
- "Solicitação de vídeo recebida"
- "Novo correio de voz"
- "Novo correio de voz (%d)"
- "Discar %s"
- "Número correio de voz desconhecido"
- "Sem serviço"
- "A rede selecionada (%s) está indisponível"
- "Atender"
- "Desligar"
- "Vídeo"
- "Voz"
- "Aceitar"
- "Dispensar"
- "Retor. cham."
- "Mensagem"
- "Chamada em andamento em outro dispositivo"
- "Transferir chamada"
- "Para fazer uma chamada, primeiro desative o modo avião."
- "Não registrado na rede."
- "Rede celular não disponível."
- "Para realizar uma chamada, digite um número válido."
- "Não é possível realizar chamadas."
- "Iniciando sequência MMI…"
- "Serviço não compatível."
- "Não é possível alternar as chamadas."
- "Não é possível separar a chamada."
- "Não é possível transferir a chamada."
- "Não é possível fazer uma conferência."
- "Não é possível rejeitar a chamada."
- "Não é possível liberar chamadas."
- "Chamada SIP"
- "Chamada de emergência"
- "Ativando o rádio…"
- "Sem serviço. Tentando novamente..."
- "Não é possível realizar chamadas. %s não é um número de emergência."
- "Não é possível realizar chamadas. Disque um número de emergência."
- "Use o teclado para discar"
- "Colocar chamada em espera"
- "Retomar chamada"
- "Encerrar chamada"
- "Mostrar teclado"
- "Ocultar teclado"
- "Desativar som"
- "Ativar som"
- "Adicionar chamada"
- "Juntar chamadas"
- "Trocar"
- "Gerenciar chamadas"
- "Gerenciar teleconferência"
- "Teleconferência"
- "Gerenciar"
- "Áudio"
- "Videocham."
- "Alterar para chamada de voz"
- "Alternar câmera"
- "Ativar câmera"
- "Desativar câmera"
- "Mais opções"
- "Player iniciado"
- "Player interrompido"
- "A câmera não está pronta"
- "Câmera pronta"
- "Evento de sessão de chamada desconhecido"
- "Serviço"
- "Configuração"
- "<Não definido>"
- "Outras configurações de chamada"
- "Chamando via %s"
- "Chamada de %s"
- "foto do contato"
- "conversar em particular"
- "selecionar contato"
- "Escreva sua resposta..."
- "Cancelar"
- "Enviar"
- "Atender"
- "Enviar SMS"
- "Recusar"
- "Atender como videochamada"
- "Atender como chamada de áudio"
- "Aceitar solicitação de vídeo"
- "Recusar solicitação de vídeo"
- "Aceitar solicitação de transmissão de vídeo"
- "Recusar solicitação de transmissão de vídeo"
- "Aceitar solicitação de recebimento de vídeo"
- "Recusar solicitação de recebimento de vídeo"
- "Para %s, deslize para cima."
- "Para %s, deslize para a esquerda."
- "Para %s, deslize para a direita."
- "Para %s, deslize para baixo."
- "Vibrar"
- "Vibrar"
- "Som"
- "Som padrão (%1$s)"
- "Toque do telefone"
- "Vibrar ao tocar"
- "Toque e vibração"
- "Gerenciar teleconferência"
- "Número de emergência"
- "Foto do perfil"
- "Câmera desligada"
- "via %s"
- "Nota enviada"
- "Mensagens recentes"
- "Informações sobre a empresa"
- "%.1f milhas de distância"
- "%.1f km de distância"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Abre amanhã às %s"
- "Abre hoje às %s"
- "Fecha às %s"
- "Fechou hoje às %s"
- "Aberto agora"
- "Fechado agora"
- "Autor suspeito (spam)"
- "Chamada encerra %1$s"
- "Esta é a primeira vez que este número ligou para você."
- "Suspeitamos que esta chamada seja de um criador de spams."
- "Bloq./denunciar spam"
- "Adicionar contato"
- "Não é spam"
-
diff --git a/InCallUI/res/values-pt-rPT/strings.xml b/InCallUI/res/values-pt-rPT/strings.xml
deleted file mode 100644
index 2a04556feeb4fba753b1100a0c15644969bf3002..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-pt-rPT/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefone"
- "Em espera"
- "Desconhecido"
- "Número privado"
- "Telefone público"
- "Conferência"
- "A chamada caiu"
- "Altifalante"
- "Auricular do telefone"
- "Auscultadores com fios"
- "Bluetooth"
- "Pretende enviar os seguintes tons?\n"
- "A enviar tons\n"
- "Enviar"
- "Sim"
- "Não"
- "Substituir o caráter universal por"
- "Conferência %s"
- "Número do correio de voz"
- "A marcar"
- "A remarcar"
- "Conferência"
- "Chamada recebida"
- "Chamada de trab. recebida"
- "Chamada terminada"
- "Em espera"
- "A desligar"
- "Numa chamada"
- "O meu número é %s"
- "A ligar vídeo"
- "Videochamada"
- "A solicitar vídeo"
- "Não é possível ligar a videochamada"
- "Pedido de vídeo rejeitado"
- "O seu número de retorno de chamadas\n %1$s"
- "O seu número de retorno de chamadas de emergência\n %1$s"
- "A marcar"
- "Chamada não atendida"
- "Chamadas não atendidas"
- "%s chamadas não atendidas"
- "Chamada não atendida de %s"
- "Chamada em curso"
- "Chamada de trabalho em curso"
- "Chamada Wi-Fi em curso"
- "Chamada de trabalho via Wi-Fi em curso"
- "Em espera"
- "Chamada recebida"
- "Chamada de trab. recebida"
- "Chamada Wi-Fi recebida"
- "Chamada de trabalho recebida via Wi-Fi"
- "Videochamada recebida"
- "A receber chamada spam suspeita"
- "Pedido de vídeo recebido"
- "Nova mensagem de correio de voz"
- "Nova mensagem de correio de voz (%d)"
- "Marcar %s"
- "Número do correio de voz desconhecido"
- "Sem serviço"
- "Rede selecionada (%s) indisponível"
- "Atender"
- "Desligar"
- "Vídeo"
- "Voz"
- "Aceitar"
- "Ignorar"
- "Ligar de volta"
- "Mensagem"
- "Chamada em curso noutro dispositivo"
- "Transferir chamada"
- "Para efetuar uma chamada, desative primeiro o Modo de avião."
- "Sem registo na rede."
- "Rede móvel não disponível."
- "Para efetuar uma chamada, introduza um número válido."
- "Não é possível telefonar."
- "A iniciar sequência de MMI..."
- "Serviço não suportado."
- "Não é possível alternar entre chamadas."
- "Não é possível separar a chamada."
- "Não é possível transferir."
- "Não é possível efetuar uma conferência."
- "Não é possível rejeitar a chamada."
- "Não é possível libertar as chamadas."
- "Chamada SIP"
- "Chamada de emergência"
- "A ligar o rádio..."
- "Sem serviço. A tentar novamente…"
- "Não é possível telefonar. %s não é um número de emergência."
- "Não é possível telefonar. Marque um número de emergência."
- "Utilizar o teclado para marcar"
- "Colocar chamada em espera"
- "Retomar chamada"
- "Terminar chamada"
- "Mostrar o teclado"
- "Ocultar o teclado"
- "Desativar som"
- "Reativar o som"
- "Adicionar chamada"
- "Intercalar chamadas"
- "Trocar"
- "Gerir chamadas"
- "Gerir conferência"
- "Conferência"
- "Gerir"
- "Áudio"
- "Videochamada"
- "Mudar para chamada de voz"
- "Trocar câmara"
- "Ativar câmara"
- "Desativar câmara"
- "Mais opções"
- "Leitor iniciado"
- "Leitor interrompido"
- "A câmara não está pronta"
- "Câmara pronta"
- "Evento de sessão de chamada desconhecido"
- "Serviço"
- "Configuração"
- "<Não definido>"
- "Outras definições de chamadas"
- "A telefonar através de %s"
- "Recebidas através de %s"
- "foto do contacto"
- "tornar privado"
- "selecionar contacto"
- "Escreva a sua própria..."
- "Cancelar"
- "Enviar"
- "Atender"
- "Enviar SMS"
- "Recusar"
- "Atender como videochamada"
- "Atender como chamada de áudio"
- "Aceitar pedido de vídeo"
- "Recusar pedido de vídeo"
- "Aceitar pedido para transmitir vídeo"
- "Recusar pedido para transmitir vídeo"
- "Aceitar pedido para receber vídeo"
- "Recusar pedido para receber vídeo"
- "Deslize lentamente para cima para %s."
- "Deslize lentamente para a esquerda para %s."
- "Deslize lentamente para a direita para %s."
- "Deslize lentamente para baixo para %s."
- "Vibrar"
- "Vibrar"
- "Som"
- "Som predefinido (%1$s)"
- "Toque do telemóvel"
- "Vibrar ao tocar"
- "Tocar e vibrar"
- "Gerir conferência"
- "Número de emergência"
- "Foto do perfil"
- "Câmara desligada"
- "através de %s"
- "Nota enviada"
- "Mensagens recentes"
- "Informações da empresa"
- "A %.1f milhas de distância"
- "A %.1f km de distância"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Abre amanhã às %s"
- "Abre hoje às %s"
- "Fecha às %s"
- "Fechou hoje às %s"
- "Aberto agora"
- "Fechado agora"
- "Chmd. spam suspeita"
- "Chamada terminada: %1$s"
- "É a primeira vez que este número lhe liga."
- "Suspeitamos que a pessoa que fez esta chamada seja um spammer."
- "Bloq./denunciar spam"
- "Adicionar contacto"
- "Não é spam"
-
diff --git a/InCallUI/res/values-pt/strings.xml b/InCallUI/res/values-pt/strings.xml
deleted file mode 100644
index 5271f54ccdb625154812a03d19147c03bf779078..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-pt/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefone"
- "Em espera"
- "Desconhecido"
- "Número privado"
- "Chamada a cobrar"
- "Teleconferência"
- "A chamada caiu."
- "Alto-falante"
- "Minifone do aparelho"
- "Fone de ouvido com fio"
- "Bluetooth"
- "Enviar os seguintes tons?\n"
- "Enviando tons\n"
- "Enviar"
- "Sim"
- "Não"
- "Substituir caractere curinga por"
- "Teleconferência %s"
- "Número do correio de voz"
- "Discando"
- "Rediscando"
- "Teleconferência"
- "Chamada recebida"
- "Chamada trabalho recebida"
- "Chamada encerrada"
- "Em espera"
- "Desligando"
- "Em chamada"
- "Meu número é %s"
- "Conectando vídeo"
- "Videochamada"
- "Solicitando vídeo"
- "Não é possível conectar a videochamada"
- "Solicitação de vídeo rejeitada"
- "Seu número de retorno de chamada\n %1$s"
- "Seu número de retorno de chamada de emergência\n %1$s"
- "Discando"
- "Chamada perdida"
- "Chamadas perdidas"
- "%s chamadas perdidas"
- "Chamada perdida de %s"
- "Chamanda em andamento"
- "Chamada de trabalho em andamento"
- "Chamada por Wi-Fi em andamento"
- "Chamada de trabalho por Wi-Fi em andamento"
- "Em espera"
- "Chamada recebida"
- "Chamada de trabalho recebida"
- "Chamada por Wi-Fi recebida"
- "Chamada de trabalho recebida por Wi-Fi"
- "Videochamada recebida"
- "Chamada recebida suspeita (spam)"
- "Solicitação de vídeo recebida"
- "Novo correio de voz"
- "Novo correio de voz (%d)"
- "Discar %s"
- "Número correio de voz desconhecido"
- "Sem serviço"
- "A rede selecionada (%s) está indisponível"
- "Atender"
- "Desligar"
- "Vídeo"
- "Voz"
- "Aceitar"
- "Dispensar"
- "Retor. cham."
- "Mensagem"
- "Chamada em andamento em outro dispositivo"
- "Transferir chamada"
- "Para fazer uma chamada, primeiro desative o modo avião."
- "Não registrado na rede."
- "Rede celular não disponível."
- "Para realizar uma chamada, digite um número válido."
- "Não é possível realizar chamadas."
- "Iniciando sequência MMI…"
- "Serviço não compatível."
- "Não é possível alternar as chamadas."
- "Não é possível separar a chamada."
- "Não é possível transferir a chamada."
- "Não é possível fazer uma conferência."
- "Não é possível rejeitar a chamada."
- "Não é possível liberar chamadas."
- "Chamada SIP"
- "Chamada de emergência"
- "Ativando o rádio…"
- "Sem serviço. Tentando novamente..."
- "Não é possível realizar chamadas. %s não é um número de emergência."
- "Não é possível realizar chamadas. Disque um número de emergência."
- "Use o teclado para discar"
- "Colocar chamada em espera"
- "Retomar chamada"
- "Encerrar chamada"
- "Mostrar teclado"
- "Ocultar teclado"
- "Desativar som"
- "Ativar som"
- "Adicionar chamada"
- "Juntar chamadas"
- "Trocar"
- "Gerenciar chamadas"
- "Gerenciar teleconferência"
- "Teleconferência"
- "Gerenciar"
- "Áudio"
- "Videocham."
- "Alterar para chamada de voz"
- "Alternar câmera"
- "Ativar câmera"
- "Desativar câmera"
- "Mais opções"
- "Player iniciado"
- "Player interrompido"
- "A câmera não está pronta"
- "Câmera pronta"
- "Evento de sessão de chamada desconhecido"
- "Serviço"
- "Configuração"
- "<Não definido>"
- "Outras configurações de chamada"
- "Chamando via %s"
- "Chamada de %s"
- "foto do contato"
- "conversar em particular"
- "selecionar contato"
- "Escreva sua resposta..."
- "Cancelar"
- "Enviar"
- "Atender"
- "Enviar SMS"
- "Recusar"
- "Atender como videochamada"
- "Atender como chamada de áudio"
- "Aceitar solicitação de vídeo"
- "Recusar solicitação de vídeo"
- "Aceitar solicitação de transmissão de vídeo"
- "Recusar solicitação de transmissão de vídeo"
- "Aceitar solicitação de recebimento de vídeo"
- "Recusar solicitação de recebimento de vídeo"
- "Para %s, deslize para cima."
- "Para %s, deslize para a esquerda."
- "Para %s, deslize para a direita."
- "Para %s, deslize para baixo."
- "Vibrar"
- "Vibrar"
- "Som"
- "Som padrão (%1$s)"
- "Toque do telefone"
- "Vibrar ao tocar"
- "Toque e vibração"
- "Gerenciar teleconferência"
- "Número de emergência"
- "Foto do perfil"
- "Câmera desligada"
- "via %s"
- "Nota enviada"
- "Mensagens recentes"
- "Informações sobre a empresa"
- "%.1f milhas de distância"
- "%.1f km de distância"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Abre amanhã às %s"
- "Abre hoje às %s"
- "Fecha às %s"
- "Fechou hoje às %s"
- "Aberto agora"
- "Fechado agora"
- "Autor suspeito (spam)"
- "Chamada encerra %1$s"
- "Esta é a primeira vez que este número ligou para você."
- "Suspeitamos que esta chamada seja de um criador de spams."
- "Bloq./denunciar spam"
- "Adicionar contato"
- "Não é spam"
-
diff --git a/InCallUI/res/values-ro/strings.xml b/InCallUI/res/values-ro/strings.xml
deleted file mode 100644
index ca0036d0d00f2595a01f3332aa7433b9e8eee498..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ro/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "În așteptare"
- "Necunoscut"
- "Număr privat"
- "Telefon public"
- "Conferință telefonică"
- "Apelul s-a încheiat"
- "Difuzor"
- "Casca receptorului"
- "Set căști-microfon cu fir"
- "Bluetooth"
- "Trimiteți următoarele tonuri?\n"
- "Se trimit tonuri\n"
- "Trimiteți"
- "Da"
- "Nu"
- "Înlocuiți metacaracterul cu"
- "Conferință telefonică %s"
- "Numărul mesageriei vocale"
- "Se apelează"
- "Se reapelează"
- "Conferință telefonică"
- "Apel primit"
- "Apel de serviciu primit"
- "Apel încheiat"
- "În așteptare"
- "Se încheie apelul"
- "Apel în desfășurare"
- "Numărul meu este %s"
- "Se conectează apelul video"
- "Apel video"
- "Se solicită apel video"
- "Nu se poate conecta apelul video"
- "Solicitarea pentru apel video a fost respinsă"
- "Numărul de apelare inversă\n%1$s"
- "Numărul de apelare inversă de urgență\n%1$s"
- "Se apelează"
- "Apel nepreluat"
- "Apeluri nepreluate"
- "%s (de) apeluri nepreluate"
- "Apel nepreluat de la %s"
- "Apel în desfășurare"
- "Apel de serviciu în desfășurare"
- "Apel prin Wi-Fi în desfășurare"
- "Apel de serviciu prin Wi-Fi în desfășurare"
- "În așteptare"
- "Apel primit"
- "Apel de serviciu primit"
- "Apel prin Wi-Fi primit"
- "Apel de serviciu prin Wi-Fi primit"
- "Apel video primit"
- "Un apel primit posibil spam"
- "Solicitare de trecere la apel video"
- "Mesaj vocal nou"
- "Mesaj vocal nou (%d)"
- "Apelați %s"
- "Numărul mesageriei vocale este necunoscut"
- "Fără semnal"
- "Rețeaua selectată (%s) nu este disponibilă"
- "Răspundeți"
- "Încheiați apelul"
- "Apel video"
- "Apel vocal"
- "Acceptați"
- "Refuzați"
- "Apelați înapoi"
- "Trimiteți mesaj"
- "Apel în curs pe alt dispozitiv"
- "Transferați apelul"
- "Pentru a apela, mai întâi dezactivați modul Avion."
- "Neînregistrat în rețea."
- "Rețeaua mobilă nu este disponibilă."
- "Pentru a apela, introduceți un număr valid."
- "Nu se poate apela."
- "Se pornește secvența MMI…"
- "Serviciul nu este acceptat."
- "Apelurile nu pot fi comutate."
- "Apelul nu poate fi separat."
- "Nu se poate transfera."
- "Conferința telefonică nu poate fi inițiată."
- "Apelul nu poate fi respins."
- "Apelurile nu pot fi eliberate."
- "Apel SIP"
- "Apel de urgență"
- "Se activează radio…"
- "Fără semnal. Se încearcă din nou…"
- "Nu se poate apela. %s nu este un număr de urgență."
- "Nu se poate apela. Formați un număr de urgență."
- "Folosiți tastatura pentru a apela"
- "Puneți apelul în așteptare"
- "Reluați apelul"
- "Încheiați apelul"
- "Afișează tastatura numerică"
- "Ascunde tastatura numerică"
- "Dezactivează sunetul"
- "Activează sunetul"
- "Adăugați un apel"
- "Îmbinați apelurile"
- "Schimbați"
- "Gestionați apelurile"
- "Gestionați conferința telefonică"
- "Conferință telefonică"
- "Gestionați"
- "Audio"
- "Apel video"
- "Treceți la apel vocal"
- "Comutați camera foto"
- "Activați camera"
- "Dezactivați camera"
- "Mai multe opțiuni"
- "Playerul a pornit"
- "Playerul s-a oprit"
- "Camera foto nu este pregătită"
- "Camera foto este pregătită"
- "Eveniment necunoscut privind o sesiune de apeluri"
- "Furnizor de servicii"
- "Configurați"
- "<Nesetat>"
- "Alte setări de apel"
- "Se apelează prin %s"
- "Primite prin %s"
- "fotografia persoanei de contact"
- "treceți în modul privat"
- "selectați o persoană de contact"
- "Scrieți propriul răspuns…"
- "Anulați"
- "Trimiteți"
- "Răspundeți"
- "Trimiteți SMS"
- "Refuzați"
- "Răspundeți ca apel video"
- "Răspundeți ca apel audio"
- "Acceptați solicitarea de a trece la apel video"
- "Refuzați solicitarea de a trece la apel video"
- "Acceptați solicitarea de a transmite conținut video"
- "Refuzați solicitarea de a transmite conținut video"
- "Acceptați solicitarea de a primi conținut video"
- "Refuzați solicitarea de a primi conținut video"
- "Glisați în sus ca să %s."
- "Glisați spre stânga ca să %s."
- "Glisați spre dreapta ca să %s."
- "Glisați în jos ca să %s."
- "Vibrații"
- "Vibrații"
- "Sunet"
- "Sunet prestabilit (%1$s)"
- "Ton de sonerie pentru telefon"
- "Vibrează când sună"
- "Ton de sonerie și vibrații"
- "Gestionați conferința telefonică"
- "Număr de urgență"
- "Fotografie de profil"
- "Camera foto este oprită"
- "pe %s"
- "Nota a fost trimisă"
- "Mesaje recente"
- "Informații despre companie"
- "%.1f mi distanță"
- "%.1f km distanță"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Deschide mâine la %s"
- "Deschide astăzi la %s"
- "Închide la %s"
- "A închis astăzi la %s"
- "Acum este deschis"
- "Acum este închis"
- "Posibil apelant spam"
- "Apelul s-a încheiat %1$s"
- "Aceasta este prima dată când ați primit apel de la acest număr."
- "Suspectăm că acesta este un apel spam."
- "Blocați/raportați"
- "Adăugați persoana"
- "Nu este spam"
-
diff --git a/InCallUI/res/values-ru/strings.xml b/InCallUI/res/values-ru/strings.xml
deleted file mode 100644
index 552ad4d0265d24529c366697f6df9f9862f5b9b9..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ru/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Телефон"
- "На удержании"
- "Неизвестный абонент"
- "Скрытый номер"
- "Телефон-автомат"
- "Конференц-вызов"
- "Звонок сброшен"
- "Динамик"
- "Динамик гарнитуры"
- "Проводная гарнитура"
- "Bluetooth"
- "Отправить следующие тоны?\n"
- "Отправка тональных сигналов\n"
- "Отправить"
- "Да"
- "Нет"
- "Заменить универсальный символ на"
- "Конференц-вызов: %s"
- "Номер голосовой почты"
- "Набор номера…"
- "Повторный вызов"
- "Конференц-вызов"
- "Входящий вызов"
- "Входящий вызов (работа)"
- "Вызов завершен"
- "На удержании"
- "Завершение разговора"
- "Вызов"
- "Мой номер: %s"
- "Подключение видео"
- "Видеовызов"
- "Запрос видео"
- "Не удалось совершить видеовызов"
- "Видеовызов отклонен"
- "Номер обратного вызова:\n%1$s"
- "Номер обратного вызова для экстренных служб:\n%1$s"
- "Набор номера…"
- "Пропущенный вызов"
- "Пропущенные вызовы"
- "Пропущенных вызовов: %s"
- "Пропущенные вызовы от абонента %s"
- "Текущий вызов"
- "Текущий звонок (работа)"
- "Текущий Wi-Fi-звонок"
- "Текущий Wi-Fi-звонок (работа)"
- "На удержании"
- "Входящий вызов"
- "Входящий вызов (работа)"
- "Входящий Wi-Fi-звонок"
- "Входящий Wi-Fi-звонок (работа)"
- "Входящий видеовызов"
- "Входящий вызов: подозрение на спам"
- "Входящий видеовызов"
- "Новое сообщение голосовой почты"
- "Новое сообщение голосовой почты (%d)"
- "Набрать номер %s"
- "Номер голосовой почты неизвестен"
- "Нет сигнала"
- "Выбранная сеть (%s) недоступна."
- "Ответить"
- "Завершить"
- "Видео"
- "Голос"
- "Разрешить"
- "Закрыть"
- "Перезвонить"
- "Написать SMS"
- "Вы участвуете в разговоре на другом устройстве"
- "Перевести на это устройство"
- "Отключите режим полета."
- "Нет регистрации в сети."
- "Мобильная сеть недоступна."
- "Недействительный номер."
- "Не удалось позвонить."
- "Запуск последовательности MMI..."
- "Сервис не поддерживается."
- "Не удалось переключить вызов."
- "Не удалось разделить вызов."
- "Не удалось перенести."
- "Не удалось выполнить конференц-вызов."
- "Не удалось отклонить вызов."
- "Не удалось разъединить."
- "Вызов SIP"
- "Экстренный вызов"
- "Включение радио…"
- "Нет сигнала. Повторная попытка…"
- "Не удалось позвонить. Номер %s не принадлежит экстренным службам."
- "Не удалось позвонить. Наберите номер экстренных служб."
- "Используйте клавиатуру для набора номера"
- "Удерживать вызов"
- "Возобновить вызов"
- "Завершить вызов"
- "Показать панель набора номера"
- "Скрыть панель набора номера"
- "Выключить звук"
- "Включить звук"
- "Добавить вызов"
- "Объединить вызовы"
- "Перевести звонок"
- "Управление вызовами"
- "Настройка конференц-связи"
- "Конференц-вызов"
- "Управление"
- "Аудио"
- "Видеовызов"
- "Отключить видео"
- "Сменить камеру"
- "Включить камеру"
- "Выключить камеру"
- "Другие настройки"
- "Видеоплеер включен"
- "Видеоплеер отключен"
- "Камера недоступна"
- "Камера доступна"
- "Неизвестное событие сеанса связи"
- "Служба"
- "Настройка"
- "<Не задано>"
- "Другие настройки вызовов"
- "Звонок через %s"
- "Входящий вызов (оператор: %s)"
- "фотография контакта"
- "приватная конференция"
- "выбрать контакт"
- "Ваш ответ…"
- "Отмена"
- "Отправить"
- "Ответить"
- "Отправить SMS"
- "Отклонить"
- "Ответить с видео"
- "Ответить на голосовой вызов"
- "Ответить на видеовызов"
- "Отклонить видеовызов"
- "Разрешить передачу видео"
- "Отклонить передачу видео"
- "Принять видео"
- "Отклонить видео"
- "Проведите вверх, чтобы %s."
- "Проведите влево, чтобы %s."
- "Проведите вправо, чтобы %s."
- "Проведите вниз, чтобы %s."
- "Вибросигнал"
- "Вибросигнал"
- "Звук"
- "По умолчанию (%1$s)"
- "Рингтон"
- "Вибросигнал и рингтон"
- "Мелодия звонка и вибросигнал"
- "Настройка конференц-связи"
- "Экстренная служба"
- "Фото профиля"
- "Камера отключена"
- "через %s"
- "Сообщение отправлено"
- "Недавние сообщения"
- "Информация о компании"
- "%.1f мил."
- "%.1f км"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Откроется завтра в %s"
- "Откроется сегодня в %s"
- "Работает до %s"
- "Сегодня не работает с %s"
- "Сейчас открыто"
- "Сейчас закрыто"
- "Подозрение на спам"
- "Вызов завершен (%1$s)"
- "Это первый вызов с этого номера."
- "Похоже, этот вызов – спам."
- "Заблокировать/в спам"
- "Добавить контакт"
- "Не спам"
-
diff --git a/InCallUI/res/values-si/strings.xml b/InCallUI/res/values-si/strings.xml
deleted file mode 100644
index de0267a586dc560deb3a4b42d972414a169541b0..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-si/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "දුරකථනය"
- "රඳවා ගනිමින්"
- "නොදනී"
- "රහසිගත අංකය"
- "පේෆෝනය"
- "සම්මන්ත්රණ ඇමතුම"
- "ඇමතුම නැවතුණි"
- "නාදකය"
- "හෑන්ඩ්සෙටයේ සවන් කඬ"
- "රැහැන් සහිත හෙඩ්සෙටය"
- "බ්ලූටූත්"
- "පහත නාද යවන්නද?\n"
- "නාද යවමින්\n"
- "යවන්න"
- "ඔව්"
- "නැත"
- "අනුලකුණ ප්රතිස්ථාපනය කරන්නේ"
- "සම්මන්ත්රණ ඇමතුම %s"
- "හඬ තැපැල් අංකය"
- "ඩයල් කරමින්"
- "නැවත ඩයල් කරමින්"
- "සම්මන්ත්රණ ඇමතුම"
- "එන ඇමතුම"
- "එන කාර්යාල ඇමතුම"
- "ඇමතුම අවසන් විය"
- "රඳවා ගනිමින්"
- "විසන්ධි කරමින්"
- "ඇමතුමක"
- "මගේ අංකය %s"
- "වීඩියෝවකට සම්බන්ධ කරමින්"
- "වීඩියෝ ඇමතුම"
- "වීඩියෝවක් ඉල්ලමින්"
- "වීඩියෝ ඇමතුම සම්බන්ධ කළ නොහැක"
- "වීඩියෝ ඉල්ලීම ප්රතික්ෂේප කරන ලදී"
- "ඔබේ පසුඇමතුම් අංකය\n %1$s"
- "ඔබගේ හදිසි පසුඇමතුම් අංකය\n %1$s"
- "ඩයල් කරමින්"
- "මඟ හැරුණු ඇමතුම"
- "මඟ හැරුණු ඇමතුම්"
- "මඟ හැරුණු ඇමතුම් %s"
- "%s වෙතින් මඟ හැරුණු ඇමතුම"
- "කරගෙන යන ඇමතුම"
- "කරගෙන යන කාර්යාල ඇමතුම"
- "දැනට කරගෙන යන Wi-Fi ඇමතුම"
- "කරගෙන යන Wi-Fi කාර්යාල ඇමතුම"
- "රඳවා ගනිමින්"
- "එන ඇමතුම"
- "එන කාර්යාල ඇමතුම"
- "එන Wi-Fi ඇමතුම"
- "එන Wi-Fi කාර්යාල ඇමතුම"
- "එන වීඩියෝ ඇමතුම"
- "එන සැකසහිත අයාචිත තැපැල් ඇමතුම"
- "එන වීඩියෝ ඉල්ලීම"
- "නව හඬ තැපෑල"
- "නව හඬ තැපැල් (%d)"
- "%s ඩයල් කරන්න"
- "හඬ තැපැල් අංකය නොදනී"
- "සේවාව නැත"
- "තෝරා ඇති ජාලය (%s) නොමැත"
- "පිළිතුරු දෙන්න"
- "විසන්ධි කරන්න"
- "වීඩියෝව"
- "හඬ"
- "පිළිගන්න"
- "අස් කරන්න"
- "පසුඇමතුම"
- "පණිවිඩය"
- "වෙනත් උපාංගයක සිදු වන ඇමතුම"
- "ඇමතුම මාරු කරන්න"
- "ඇමතුමක් ගැනීමට, මුලින්ම ගුවන් යානා ප්රකාරය ක්රියාවිරහිත කරන්න."
- "ජාලය මත ලියාපදිංචි වී නැත."
- "සෙලියුලර් ජාලය නොතිබේ."
- "ඇමතුමක් ගැනීමට, වලංගු අංකයක් ඇතුළු කරන්න."
- "ඇමතුම් ගැනීමට නොහැක."
- "MMI අනුපිළිවෙළ ආරම්භ කරමින්…"
- "සේවාවට සහාය දක්වන්නේ නැත."
- "ඇමතුම් මාරු කිරීම කළ නොහැක."
- "ඇමතුම වෙන් කිරීම කළ නොහැක."
- "මාරු කිරීමට නොහැක."
- "සම්මන්ත්රණය කළ නොහැක."
- "ඇමතුම ප්රතික්ෂේප කළ නොහැක."
- "ඇමතුම(ම්) මුදාහැරීම කළ නොහැක."
- "SIP ඇමතුම"
- "හදිසි ඇමතුම"
- "රේඩියෝව ක්රියාත්මක කරමින්…"
- "සේවාව නැත. නැවත උත්සාහ කරමින්…"
- "ඇමතීමට නොහැකිය. %s මෙය හදිසි ඇමතුම් අංකයක් නොවේ."
- "ඇමතිය නොහැක. හදිසි අංකයක් අමතන්න."
- "ඩයල් කිරීමට යතුරු පුවරුව භාවිත කරන්න"
- "ඇමතුම රඳවා ගන්න"
- "ඇමතුම නැවත පටන් ගන්න"
- "ඇමතුම අවසන් කරන්න"
- "ඇමතුම් පෑඩය පෙන්වන්න"
- "ඇමතුම් පෑඩය සඟවන්න"
- "නිහඬ කරන්න"
- "නිහඬ කිරීම ඉවත් කරන්න"
- "ඇමතුමක් එක් කරන්න"
- "ඇමතුම් ඒකාබද්ධ කරන්න"
- "මාරු කරන්න"
- "ඇමතුම් කළමනාකරණය කරන්න"
- "සම්මන්ත්රණ ඇමතුම කළමනාකරණය කරන්න"
- "සම්මන්ත්රණ ඇමතුම"
- "කළමනාකරණය කරන්න"
- "ශ්රව්යය"
- "වීඩියෝ ඇමතුම"
- "හඬ ඇමතුමක් වෙත මාරු කරන්න"
- "කැමරාව මාරු කරන්න"
- "කැමරාව ක්රියාත්මක කරන්න"
- "කැමරාව ක්රියා විරහිත කරන්න"
- "තවත් විකල්ප"
- "ධාවකය ආරම්භ කරන ලදි"
- "ධාවකය නැවතුණි"
- "කැමරාව සූදානම් නැහැ"
- "කැමරාව සූදානම්"
- "නොදන්නා ඇමතුම් සැසි සිදුවීම"
- "සේවාව"
- "පිහිටුවීම"
- "<පිහිටුවා නැත>"
- "වෙනත් ඇමතුම් සැකසීම්"
- "%s හරහා අමතමින්"
- "%s හරහා එන"
- "සම්බන්ධතා ඡායාරූපය"
- "රහසිගත වන්න"
- "සම්බන්ධතාවය තෝරාගන්න"
- "ඔබේම එකක් ලියන්න..."
- "අවලංගු කරන්න"
- "යවන්න"
- "පිළිතුරු දෙන්න"
- "SMS යවන්න"
- "ප්රතික්ෂේප කිරීම"
- "වීඩියෝ ඇමතුමට පිළිතුරු දෙන්න"
- "ශ්රව්ය ඇමතුමට පිළිතුරු දෙන්න"
- "වීඩියෝ ඉල්ලීම පිළිගන්න"
- "වීඩියෝ ඉල්ලීම ප්රතික්ෂේප කරන්න"
- "වීඩියෝ සම්ප්ර්ෂණ ඉල්ලීම පිළිගන්න"
- "වීඩියෝ සම්ප්ර්ෂණ ඉල්ලීම ප්රතික්ෂේප කරන්න"
- "වීඩියෝ ලැබීමේ ඉල්ලීම පිළිගන්නා ලදි"
- "වීඩියෝ ලැබීමේ ඉල්ලීම ප්රතික්ෂේප කරන්න"
- "%s සඳහා උඩට සර්පණය කරන්න."
- "%s සඳහා වමට සර්පණය කරන්න."
- "%s සඳහා දකුණට සර්පණය කරන්න."
- "%s සඳහා පහළට සර්පණය කරන්න."
- "කම්පනය"
- "කම්පනය"
- "හඬ"
- "පෙරනිමි ශබ්දය (%1$s)"
- "දුරකථන රිගින්ටෝනය"
- "රිගින් වන විට කම්පන වන්න"
- "රිගින් ටෝන් සහ කම්පනය කරන්න"
- "සම්මන්ත්රණ ඇමතුම කළමනාකරණය කරන්න"
- "හදිසි ඇමතුම් අංකය"
- "පැතිකඩ ඡායාරූපය"
- "කැමරාව ක්රියාවිරහිතයි"
- "%s හරහා"
- "සටහන යවන ලදී"
- "මෑත පණිවිඩ"
- "ව්යාපාර තොරතුරු"
- "සැතපුම් %.1fක් ඈතින්"
- "කි.මි. %.1fක් ඈතින්"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "හෙට %sට විවෘත කෙරේ"
- "අද %sට විවෘත කෙරේ"
- "%sට වසයි"
- "අද %sට වසන ලදී"
- "දැන් විවෘතයි"
- "දැන් වසා ඇත"
- "සැකසහිත අයාචිත තැපැල් අමතන්නා"
- "ඇමතුම අවසන් විය %1$s"
- "මෙය ඔබට මෙම අංකයෙන් ඇමතුමක් ලැබුණ පළමු අවස්ථාව වේ."
- "මෙම ඇමතුම අයාචිත එවන්නෙකු අපි සැක කළෙමු."
- "අවහිර ක./අයාචිත වා."
- "සම්බන්ධතාව එක් කරන්න"
- "අයාචිත තැපෑලක් නොවේ"
-
diff --git a/InCallUI/res/values-sk/strings.xml b/InCallUI/res/values-sk/strings.xml
deleted file mode 100644
index 07e8de67147eb59e075e7e704985f29056f868db..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sk/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefón"
- "Podržaný hovor"
- "Neznáme"
- "Súkromné číslo"
- "Telefónny automat"
- "Konferenčný hovor"
- "Hovor bol prerušený"
- "Reproduktor"
- "Slúchadlo"
- "Náhlavná súprava s káblom"
- "Bluetooth"
- "Odoslať nasledujúce tóny?\n"
- "Odosielanie tónov\n"
- "Odoslať"
- "Áno"
- "Nie"
- "Nahradiť zástupný znak znakom"
- "Konferenčný hovor %s"
- "Číslo hlasovej schránky"
- "Vytáča sa"
- "Znova sa vytáča"
- "Konferenčný hovor"
- "Prichádzajúci hovor"
- "Prichádzajúci prac. hovor"
- "Hovor bol ukončený"
- "Podržaný hovor"
- "Ukončovanie hovoru"
- "Prebieha hovor"
- "Moje číslo je %s"
- "Pripája sa video"
- "Videohovor"
- "Žiada sa video"
- "Videohovor nie je možné pripojiť"
- "Žiadosť o video bola odmietnutá"
- "Vaše číslo na spätné volanie\n %1$s"
- "Vaše číslo na spätné tiesňové volanie\n %1$s"
- "Vytáča sa"
- "Zmeškaný hovor"
- "Zmeškané hovory"
- "Zmeškané hovory: %s"
- "Zmeškaný hovor od volajúceho %s"
- "Prebiehajúci hovor"
- "Prebiehajúci pracovný hovor"
- "Odchádzajúci hovor cez Wi-Fi"
- "Prebiehajúci pracovný hovor cez Wi-Fi"
- "Podržaný hovor"
- "Prichádzajúci hovor"
- "Prichádzajúci pracovný hovor"
- "Prichádzajúci hovor cez Wi-Fi"
- "Prichádzajúci pracovný hovor cez Wi-Fi"
- "Prichádzajúci videohovor"
- "Prichádzajúci hovor, pri ktorom je podozrenie, že ide o spam"
- "Prichádzajúca žiadosť o video"
- "Nová hlasová správa"
- "Nová hlasová správa (%d)"
- "Zavolať hlasovú schránku %s"
- "Číslo hlasovej schránky je neznáme"
- "Žiadny signál"
- "Vybraná sieť (%s) nie je k dispozícii"
- "Prijať"
- "Položiť"
- "Video"
- "Hlas"
- "Prijať"
- "Odmietnuť"
- "Zavolať späť"
- "Správa"
- "Prebiehajúci hovor v inom zariadení"
- "Prepojiť hovor"
- "Ak chcete volať, vypnite najprv režim v lietadle."
- "Prihlásenie do siete nebolo úspešné."
- "Mobilná sieť nie je k dispozícii."
- "Ak chcete volať, zadajte platné číslo."
- "Hovor sa nedá uskutočniť."
- "Prebieha spúšťanie sekvencie MMI…"
- "Služba nie je podporovaná."
- "Nedajú sa prepínať hovory."
- "Nedá sa rozdeliť hovor."
- "Nedá sa preniesť."
- "Konferenčný hovor sa nedá uskutočniť."
- "Nedá sa odmietnuť hovor."
- "Nedajú sa ukončiť hovory."
- "Hovor SIP"
- "Tiesňové volanie"
- "Zapína sa rádio..."
- "Žiadny signál. Prebieha ďalší pokus…"
- "Hovor sa nedá uskutočniť. %s nie je číslo tiesňového volania."
- "Hovor nie je možné uskutočniť. Vytočte číslo tiesňového volania."
- "Číslo vytočíte pomocou klávesnice"
- "Podržať hovor"
- "Obnoviť hovor"
- "Ukončiť hovor"
- "Zobraziť číselnú klávesnicu"
- "Skryť číselnú klávesnicu"
- "Vypnúť zvuk"
- "Zapnúť zvuk"
- "Pridať hovor"
- "Zlúčiť hovory"
- "Zameniť"
- "Spravovať hovory"
- "Spravovať konferenčný hovor"
- "Konferenčný hovor"
- "Spravovať"
- "Zvuk"
- "Videohovor"
- "Zmeniť na hlasový hovor"
- "Zapnúť kameru"
- "Zapnúť fotoaparát"
- "Vypnúť fotoaparát"
- "Ďalšie možnosti"
- "Prehrávač bol spustený"
- "Prehrávač bol zastavený"
- "Kamera nie je pripravená"
- "Kamera je pripravená"
- "Neznáma udalosť relácie volania"
- "Služba"
- "Nastavenie"
- "<Nenastavené>"
- "Ďalšie nastavenia hovorov"
- "Voláte prostredníctvom poskytovateľa %s"
- "Prichádz. hovor prostred. poskytovateľa %s"
- "fotka kontaktu"
- "prepnúť na súkromné"
- "vybrať kontakt"
- "Napísať vlastnú..."
- "Zrušiť"
- "Odoslať"
- "Prijať"
- "Odoslať SMS"
- "Odmietnuť"
- "Prijať ako videohovor"
- "Prijať ako zvukový hovor"
- "Prijať žiadosť o videohovor"
- "Odmietnuť žiadosť o videohovor"
- "Prijať žiadosť o prenos videa"
- "Odmietnuť žiadosť o prenos videa"
- "Povoliť žiadosť o prijatie videa"
- "Odmietnuť žiadosť o prijatie videa"
- "Prejdite prstom nahor: %s."
- "Prejdite prstom doľava: %s."
- "Prejdite prstom doprava: %s."
- "Prejdite prstom nadol: %s."
- "Vibrovanie"
- "Vibrovanie"
- "Zvuk"
- "Predvolený zvuk (%1$s)"
- "Tón zvonenia telefónu"
- "Vibrovať pri zvonení"
- "Vyzváňací tón a vibrovanie"
- "Správa konferenčného hovoru"
- "Číslo tiesňového volania"
- "Profilová fotka"
- "Kamera je vypnutá"
- "na čísle %s"
- "Poznámka bola odoslaná"
- "Nedávne správy"
- "Informácie o firme"
- "Vzdialené %.1f mi"
- "Vzdialené %.1f km"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Zajtra sa otvára o %s"
- "Dnes sa otvára o %s"
- "Zatvára sa o %s"
- "Dnes bolo zatvorené o %s"
- "Otvorené"
- "Zatvorené"
- "Podozrenie na spam"
- "Hovor sa skončil %1$s"
- "Toto bol prvý hovor z tohto čísla."
- "Mali sme podozrenie, že tento hovor bol od šíriteľa spamu."
- "Blok./nahlásiť spam"
- "Pridať kontakt"
- "Toto nie je spam"
-
diff --git a/InCallUI/res/values-sl/strings.xml b/InCallUI/res/values-sl/strings.xml
deleted file mode 100644
index a2cf2102b18cb40d991374e791f39196b437ae2d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sl/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Zadržan"
- "Neznan"
- "Zasebna številka"
- "Telefonska govorilnica"
- "Konferenčni klic"
- "Klic je bil prekinjen"
- "Zvočnik"
- "Slušalka"
- "Žične slušalke"
- "Bluetooth"
- "Ali želite poslati naslednje tone?\n"
- "Pošiljanje tonov\n"
- "Pošlji"
- "Da"
- "Ne"
- "Zamenjaj nadomestni znak z"
- "Konferenčni klic: %s"
- "Številka odzivnika"
- "Klicanje"
- "Vnovično klicanje"
- "Konferenčni klic"
- "Dohodni klic"
- "Dohodni delovni klic"
- "Klic je končan"
- "Zadržan"
- "Prekinjanje"
- "Klic poteka"
- "Moja številka je %s"
- "Povezovanje videa"
- "Videoklic"
- "Zahtevanje videa"
- "Videoklica ni mogoče vzpostaviti"
- "Zavrnjena zahteva za videoklic"
- "Vaša številka za povratni klic:\n %1$s"
- "Vaša številka za povratni klic v sili:\n %1$s"
- "Klicanje"
- "Neodgovorjeni klic"
- "Neodgovorjeni klici"
- "Št. neodgovorjenih klicev: %s"
- "Neodgovorjeni klic od: %s"
- "Aktivni klic"
- "Aktivni delovni klic"
- "Aktivni klic prek omrežja Wi-Fi"
- "Aktivni delovni klic prek omrežja Wi-Fi"
- "Zadržan"
- "Dohodni klic"
- "Dohodni delovni klic"
- "Dohodni klic Wi-Fi"
- "Dohodni delovni klic prek omrežja Wi-Fi"
- "Dohodni videoklic"
- "Domnevno neželeni dohodni klic"
- "Zahteva za dohodni video"
- "Novo sporočilo v odzivniku"
- "Novo sporočilo v odzivniku (%d)"
- "Klic: %s"
- "Neznana številka odzivnika"
- "Ni signala"
- "Izbrano omrežje (%s) ni na voljo"
- "Odgovor"
- "Prekinitev"
- "Video"
- "Govor"
- "Sprejmem"
- "Opusti"
- "Povrat. klic"
- "SMS"
- "Aktivni klic v drugi napravi"
- "Prenos klica"
- "Če želite poklicati, najprej izklopite način za letalo."
- "Ni registrirano v omrežju."
- "Mobilno omrežje ni na voljo."
- "Če želite opraviti klic, vnesite veljavno številko."
- "Klicanje ni mogoče."
- "Začetek zaporedja MMI ..."
- "Storitev ni podprta."
- "Preklop med klici ni mogoč."
- "Ločitev klica ni mogoča."
- "Prenos ni mogoč."
- "Konferenčni klic ni mogoč."
- "Zavrnitev klica ni mogoča."
- "Prekinitev klica ni mogoča."
- "Klic SIP"
- "Klic v sili"
- "Vklop radia …"
- "Ni signala. Vnovičen poskus …"
- "Klicanje ni mogoče. %s ni številka za klic v sili."
- "Klicanje ni mogoče. Opravite klic v sili."
- "Za izbiranje številke uporabite tipkovnico"
- "Zadrži klic"
- "Nadaljuj klic"
- "Končaj klic"
- "Prikaži tipkovnico"
- "Skrij tipkovnico"
- "Izklopi zvok"
- "Vklopi zvok"
- "Dodaj klic"
- "Združi klice"
- "Zamenjaj"
- "Upravljaj klice"
- "Upravljaj konferenčne klice"
- "Konferenčni klic"
- "Upravljaj"
- "Zvok"
- "Videoklic"
- "Preklopi na glasovni klic"
- "Preklopi med fotoaparati"
- "Vklopi kamero"
- "Izklopi kamero"
- "Več možnosti"
- "Predvajanje začeto"
- "Predvajanje ustavljeno"
- "Fotoaparat ni pripravljen"
- "Fotoaparat je pripravljen"
- "Neznan dogodek seje klica"
- "Storitev"
- "Nastavitev"
- "<Ni nastavljeno>"
- "Druge klicne nastavitve"
- "Klicanje prek ponudnika %s"
- "Dohodni prek %s"
- "fotografija stika"
- "zasebno"
- "izbira stika"
- "Napišite lasten odgovor …"
- "Prekliči"
- "Pošlji"
- "Odgovor"
- "Pošiljanje SMS-ja"
- "Zavrnitev"
- "Odgovor z video povezavo"
- "Odgovor z zvočno povezavo"
- "Sprejemanje zahteve za video"
- "Zavrnitev zahteve za video"
- "Sprejemanje zahteve za pošiljanje videa"
- "Zavrnitev zahteve za pošiljanje videa"
- "Sprejemanje zahteve za prejem videa"
- "Zavrnitev zahteve za prejem videa"
- "Povlecite navzgor za %s."
- "Povlecite v levo za %s."
- "Povlecite v desno za %s."
- "Povlecite navzdol za %s."
- "Vibriranje"
- "Vibriranje"
- "Zvok"
- "Privzeti zvok (%1$s)"
- "Ton zvonjenja telefona"
- "Vibriranje ob zvonjenju"
- "Zvonjenje in vibriranje"
- "Upravljanje konferenčnih klicev"
- "Številka za klic v sili"
- "Fotografija profila"
- "Fotoaparat je izklopljen"
- "prek %s"
- "Opomba poslana"
- "Nedavna sporočila"
- "Podatki o podjetju"
- "%.1f mi stran"
- "%.1f km stran"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Odpre se jutri ob %s"
- "Odpre se danes ob %s"
- "Zapre se ob %s"
- "Zaprto danes ob %s"
- "Trenutno odprto"
- "Trenutno zaprto"
- "Neželeni klicatelj"
- "Klic je bil končan %1$s"
- "To je prvi klic, ki ste ga prejeli s te številke."
- "Predvidevali smo, da je to neželeni klic."
- "Blok./prij. než. kl."
- "Dodaj stik"
- "Ni neželeni klic"
-
diff --git a/InCallUI/res/values-sq/strings.xml b/InCallUI/res/values-sq/strings.xml
deleted file mode 100644
index 43fd2263d17ec42f7f7d14d6a3597f58b567d226..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sq/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefoni"
- "Në pritje"
- "I panjohur"
- "Numër privat"
- "Telefon me pagesë"
- "Telefonatë konferencë"
- "Telefonata ra"
- "Altoparlant"
- "Kufje për vesh"
- "Kufje me tel"
- "Bluetooth"
- "Dërgo tonet e mëposhtme?\n"
- "Po dërgon tone\n"
- "Dërgo"
- "Po"
- "Jo"
- "Zëvendëso karakterin variabël me"
- "Telefonatë konferencë %s"
- "Numri i postës zanore"
- "Po formon numrin"
- "Po riformon numrin"
- "Telefonatë konferencë"
- "Telefonatë hyrëse"
- "Telefonatë pune hyrëse"
- "Telefonata përfundoi"
- "Në pritje"
- "Mbyllja"
- "Në telefonatë"
- "Numri im është %s"
- "Po rilidh videon"
- "Telefonatë me video"
- "Po kërkon video"
- "Nuk mund të lidhë telefonatën me video"
- "Kërkesa me video u refuzua"
- "Numri i kthimit të telefonatës\n %1$s"
- "Numri i kthimit të telefonatës së urgjencës\n %1$s"
- "Po formon numrin"
- "Telefonatë e humbur"
- "Telefonata të humbura"
- "%s telefonata të humbura"
- "Telefonatë e humbur nga %s"
- "Telefonatë në vazhdim"
- "Telefonatë pune dalëse"
- "Telefonatë me Wi-Fi në vazhdim"
- "Telefonatë pune dalëse me Wi-Fi"
- "Në pritje"
- "Telefonatë hyrëse"
- "Telefonatë pune hyrëse"
- "Telefonatë hyrëse me Wi-Fi"
- "Telefonatë pune hyrëse me Wi-Fi"
- "Telefonatë hyrëse me video"
- "Telefonatë e dyshuar si e padëshiruar"
- "Kërkesë për video hyrëse"
- "Postë e re zanore"
- "Postë e re zanore (%d)"
- "Formo numrin %s"
- "Numri i postës zanore është i panjohur"
- "Nuk ka shërbim"
- "Rrjeti i zgjedhur (%s) i padisponueshëm"
- "Përgjigju"
- "Mbyll"
- "Video"
- "Zanore"
- "Prano"
- "Largoje"
- "Ri-telefono"
- "Mesazh"
- "Telefonatë në vazhdim në një pajisje tjetër"
- "Transfero telefonatën"
- "Për të kryer telefonatë, së pari çaktivizo modalitetin e aeroplanit."
- "I paregjistruar në rrjet."
- "Rrjeti celular nuk mundësohet."
- "Për të kryer një telefonatë, fut një numër të vlefshëm."
- "Nuk mund të telefonojë."
- "Po fillon sekuencën MMI…"
- "Shërbimi nuk mbështetet."
- "Nuk mund të ndryshojë telefonatat."
- "Nuk mund të ndajë telefonatën."
- "Nuk mund të transferojë."
- "Nuk mund të kryejë telefonatë konference."
- "Nuk mund të refuzojë telefonatën."
- "Nuk mund të lëshojë telefonatën(at)."
- "Telefonatë SIP"
- "Telefonata e urgjencës"
- "Po aktivizon radion…"
- "Nuk ka shërbim. Po provon sërish…"
- "Nuk mund të telefonohet. %s nuk është një numër urgjence."
- "Nuk mund të telefonohet. Formo një numër urgjence."
- "Përdor tastierën për të formuar numrin"
- "Vendose në pritje telefonatën"
- "Rifillo telefonatën"
- "Mbylle telefonatën"
- "Shfaq bllokun e formimit të numrit"
- "Fshih bllokun e formimit të numrit"
- "Çaktivizo audion"
- "Aktivizo audion"
- "Shto telefonatë"
- "Shkri telefonatat"
- "Shkëmbe"
- "Menaxho telefonatat"
- "Menaxho telefonatën konferencë"
- "Telefonatë konferencë"
- "Menaxho"
- "Audioja"
- "Telefonatë me video"
- "Ndërro në telefonatë me video"
- "Ndërro kamerën"
- "Aktivizo kamerën"
- "Çaktivizo kamerën"
- "Opsione të tjera"
- "Luajtësi filloi"
- "Luajtësi ndaloi"
- "Kamera nuk është gati"
- "Kamera është gati"
- "Ngjarje e panjohur në sesionin e telefonatës"
- "Shërbimi"
- "Konfigurimi"
- "<I pavendosur>"
- "Cilësime të tjera të telefonatës"
- "Telefonatë nëpërmjet %s"
- "Hyrëse nëpërmjet %s"
- "fotografia e kontaktit"
- "bëje private"
- "përzgjidh kontaktin"
- "Shkruaj përgjigjen tënde..."
- "Anulo"
- "Dërgo"
- "Përgjigju"
- "Dërgo SMS"
- "Refuzo"
- "Përgjigju si telefonatë me video"
- "Përgjigju si telefonatë me audio"
- "Prano kërkesën për video"
- "Refuzo kërkesën për video"
- "Prano kërkesën për transmetimin e videos"
- "Refuzo kërkesën për transmetimin e videos"
- "Prano kërkesën për marrjen e videos"
- "Refuzo kërkesën për marrjen e videos"
- "Rrëshqit lart për %s."
- "Rrëshqit majtas për %s"
- "Rrëshqit djathtas për %s"
- "Rrëshqit poshtë për %s."
- "Dridhja"
- "Dridhja"
- "Tingulli"
- "Tingulli i parazgjedhur (%1$s)"
- "Toni i ziles i telefonit"
- "Dridhje edhe kur bie zilja"
- "Me zile dhe me dridhje"
- "Menaxho telefonatën konferencë"
- "Numri i urgjencës"
- "Fotografia e profilit"
- "Kamera joaktive"
- "përmes %s"
- "Shënimi u dërgua"
- "Mesazhet e fundit"
- "Informacioni i biznesit"
- "%.1f milje larg"
- "%.1f km larg"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Hapet nesër në %s"
- "Hapet sot në %s"
- "Mbyllet në %s"
- "Mbyllur sot në %s"
- "Tani është hapur"
- "Tani është mbyllur"
- "I padëshirueshëm"
- "Telefonata përfundoi %1$s"
- "Kjo është hera e parë që ky numër ka telefonuar."
- "Ne dyshojmë që kjo telefonatë të jetë e padëshirueshme."
- "Blloko/raporto të padëshiruar"
- "Shto një kontakt"
- "Jo i padëshiruar"
-
diff --git a/InCallUI/res/values-sr/strings.xml b/InCallUI/res/values-sr/strings.xml
deleted file mode 100644
index 3a3820d8c4751722e0a08576c34233399aa2ebf0..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sr/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Телефон"
- "На чекању"
- "Непознат"
- "Приватан број"
- "Телефонска говорница"
- "Конференцијски позив"
- "Позив је прекинут"
- "Звучник"
- "Слушалица телефона"
- "Жичане наглавне слушалице"
- "Bluetooth"
- "Желите ли да пошаљете следеће тонове?\n"
- "Тонови се шаљу\n"
- "Пошаљи"
- "Да"
- "Не"
- "Замените џокер знак са"
- "Конференцијски позив %s"
- "Број говорне поште"
- "Позива се"
- "Поново се бира"
- "Конференцијски позив"
- "Долазни позив"
- "Долазни позив за Work"
- "Позив је завршен"
- "На чекању"
- "Веза се прекида"
- "Позив је у току"
- "Мој број је %s"
- "Повезује се видео позив"
- "Видео позив"
- "Захтева се видео позив"
- "Повезивање видео позива није успело"
- "Захтев за видео позив је одбијен"
- "Број за повратни позив\n %1$s"
- "Број за хитан повратни позив\n %1$s"
- "Позива се"
- "Пропуштен позив"
- "Пропуштени позиви"
- "Број пропуштених позива: %s"
- "Пропуштен позив од: %s"
- "Текући позив"
- "Текући позив за Work"
- "Текући Wi-Fi позив"
- "Текући позив за Work преко Wi-Fi-ја"
- "На чекању"
- "Долазни позив"
- "Долазни позив за Work"
- "Долазни Wi-Fi позив"
- "Долазни позив за Work преко Wi-Fi-ја"
- "Долазни видео позив"
- "Сумња на непожељан долазни позив"
- "Захтев за долазни видео позив"
- "Нова порука говорне поште"
- "Нова порука говорне поште (%d)"
- "Позови %s"
- "Непознат број говорне поште"
- "Мобилна мрежа није доступна"
- "Изабрана мрежа (%s) није доступна"
- "Одговори"
- "Прекини везу"
- "Видео"
- "Гласовни"
- "Прихватам"
- "Одбаци"
- "Узврати позив"
- "Пошаљи SMS"
- "Позив је у току на другом уређају"
- "Пребаци позив"
- "Да бисте упутили позив, прво искључите режим рада у авиону."
- "Није регистровано на мрежи."
- "Мобилна мрежа није доступна."
- "Да бисте упутили позив, унесите важећи број."
- "Позив није успео."
- "Покреће се MMI секвенца..."
- "Услуга није подржана."
- "Замена позива није успела."
- "Раздвајање позива није успело."
- "Пребацивање није успело."
- "Конференцијски позив није успео."
- "Одбијање позива није успело."
- "Успостављање позива није успело."
- "SIP позив"
- "Хитни позив"
- "Укључује се радио…"
- "Мобилна мрежа није доступна. Покушавамо поново…"
- "Позив није успео. %s није број за хитне случајеве."
- "Позив није успео. Позовите број за хитне случајеве."
- "Користите тастатуру за позивање"
- "Стави позив на чекање"
- "Настави позив"
- "Заврши позив"
- "Прикажи нумеричку тастатуру"
- "Сакриј нумеричку тастатуру"
- "Искључи звук"
- "Укључи звук"
- "Додај позив"
- "Обједини позиве"
- "Замени"
- "Управљај позивима"
- "Управљај конференцијским позивом"
- "Конференцијски позив"
- "Управљај"
- "Аудио"
- "Видео позив"
- "Промени у гласовни позив"
- "Промени камеру"
- "Укључи камеру"
- "Искључи камеру"
- "Још опција"
- "Плејер је покренут"
- "Плејер је заустављен"
- "Камера није спремна"
- "Камера је спремна"
- "Непознат догађај сесије позива"
- "Услуга"
- "Подешавање"
- "<Није подешено>"
- "Друга подешавања позива"
- "Позива се преко добављача %s"
- "Долазни позив преко %s"
- "слика контакта"
- "иди на приватно"
- "изаберите контакт"
- "Напишите сами…"
- "Откажи"
- "Пошаљи"
- "Одговори"
- "Пошаљи SMS"
- "Одбиј"
- "Одговори видео позивом"
- "Одговори аудио-позивом"
- "Прихвати захтев за видео"
- "Одбиј захтев за видео"
- "Прихвати захтев за одлазни видео позив"
- "Одбиј захтев за одлазни видео позив"
- "Прихвати захтев за долазни видео позив"
- "Одбиј захтев за долазни видео позив"
- "Превуците нагоре за %s."
- "Превуците улево за %s."
- "Превуците удесно за %s."
- "Превуците надоле за %s."
- "Вибрација"
- "Вибрација"
- "Звук"
- "Подразумевани звук (%1$s)"
- "Мелодија звона телефона"
- "Вибрирај када звони"
- "Мелодија звона и вибрација"
- "Управљај конференцијским позивом"
- "Број за хитне случајеве"
- "Слика профила"
- "Камера је искључена"
- "на %s"
- "Белешка је послата"
- "Недавне поруке"
- "Информације о предузећу"
- "Удаљеност је %.1f mi"
- "Удаљеност је %.1f km"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Отвара се сутра у %s"
- "Отвара се данас у %s"
- "Затвара се у %s"
- "Затворило се данас у %s"
- "Тренутно отворено"
- "Тренутно затворено"
- "Непожељан позивалац"
- "Позив се завршио у %1$s"
- "Ово је био први позив са овог броја."
- "Сумњамо да је овај позив непожељан."
- "Блокирај/пријави"
- "Додај контакт"
- "Није непожељан"
-
diff --git a/InCallUI/res/values-sv/strings.xml b/InCallUI/res/values-sv/strings.xml
deleted file mode 100644
index 980ecdb07e01878ef1bfa4c249274fe3c33f4201..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sv/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Parkerat"
- "Okänd"
- "Privat nummer"
- "Telefonautomat"
- "Konferenssamtal"
- "Samtalet avbröts"
- "Högtalare"
- "Telefonlur"
- "Trådanslutet headset"
- "Bluetooth"
- "Ska följande toner skickas?\nBREAK"
- "Skickar signaler\n"
- "Skicka"
- "Ja"
- "Nej"
- "Ersätt jokertecknet med"
- "Konferenssamtal %s"
- "Nummer till röstbrevlåda"
- "Ringer"
- "Ringer upp igen"
- "Konferenssamtal"
- "Inkommande samtal"
- "Inkommande jobbsamtal"
- "Samtal avslutat"
- "Parkerat"
- "Lägger på"
- "I samtal"
- "Mitt telefonnummer är %s"
- "Ansluter video"
- "Videosamtal"
- "Begär video"
- "Det gick inte att ansluta till videosamtalet"
- "Videobegäran avslogs"
- "Ditt nummer för återuppringning\n %1$s"
- "Ditt nummer för återuppringning vid nödsamtal\n %1$s"
- "Ringer"
- "Missat samtal"
- "Missade samtal"
- "%s missade samtal"
- "Missat samtal från %s"
- "Pågående samtal"
- "Pågående jobbsamtal"
- "Pågående Wi-Fi-samtal"
- "Pågående jobbsamtal via Wi-Fi"
- "Parkerat"
- "Inkommande samtal"
- "Inkommande jobbsamtal"
- "Inkommande Wi-Fi-samtal"
- "Inkommande jobbsamtal via Wi-Fi"
- "Inkommande videosamtal"
- "Inkommande misstänkt spamsamtal"
- "Inkommande begäran om videosamtal"
- "Nytt röstmeddelande"
- "Nytt röstmeddelande (%d)"
- "Ring %s"
- "Nummer till röstbrevlåda okänt"
- "Ingen tjänst"
- "Det valda nätverket (%s) är inte tillgängligt"
- "Svara"
- "Lägg på"
- "Video"
- "Röstsamtal"
- "Godkänn"
- "Ignorera"
- "Ring upp"
- "Meddelande"
- "Pågående samtal på en annan enhet"
- "Överför samtal"
- "Om du vill ringa måste du först inaktivera flygplansläge."
- "Inte registrerat på nätverk."
- "Det finns inget mobilnät tillgängligt."
- "Ange ett giltigt nummer om du vill ringa ett samtal."
- "Det gick inte att ringa."
- "Startar sekvens för MMI-kod …"
- "Tjänsten stöds inte."
- "Det gick inte att växla mellan samtal."
- "Det gick inte att koppla isär samtalen."
- "Det gick inte att överföra."
- "Det gick inte att starta ett konferenssamtal."
- "Det gick inte att avvisa samtalet."
- "Det gick inte att släppa samtal."
- "SIP-samtal"
- "Nödsamtal"
- "Sätter på radion …"
- "Ingen tjänst. Försöker igen …"
- "Det gick inte att ringa. %s är inget nödnummer."
- "Det gick inte att ringa. Slå ett nödnummer."
- "Använd tangentbordet om du vill ringa"
- "Parkera samtal"
- "Återuppta samtal"
- "Avsluta samtal"
- "Visa knappsats"
- "Dölj knappsats"
- "Ljud av"
- "Sluta ignorera"
- "Lägg till samtal"
- "Koppla ihop samtal"
- "Byt"
- "Hantera samtal"
- "Hantera konferenssamtal"
- "Konferenssamtal"
- "Hantera"
- "Ljud"
- "Videosamt."
- "Byt till röstsamtal"
- "Byt kamera"
- "Slå på kameran"
- "Stäng av kameran"
- "Fler alternativ"
- "Videospelaren har startats"
- "Videospelaren har stoppats"
- "Kameran är inte klar"
- "Kameran är klar"
- "Okänd händelse vid samtalssession"
- "Tjänst"
- "Konfiguration"
- "<Har inte angetts>"
- "Övriga samtalsinställningar"
- "Ringer via %s"
- "Inkommande via %s"
- "kontaktbild"
- "gör privat"
- "välj kontakt"
- "Skriv ett eget svar …"
- "Avbryt"
- "Skicka"
- "Svara"
- "Skicka sms"
- "Avvisa"
- "Svara som videosamtal"
- "Svara som röstsamtal"
- "Godkänn videobegäran"
- "Avvisa videobegäran"
- "Godkänn begäran om att skicka video"
- "Avvisa begäran om att skicka video"
- "Godkänn begäran om att ta emot video"
- "Avvisa begäran om att ta emot video"
- "%s genom att dra uppåt."
- "%s genom att dra åt vänster."
- "%s genom att dra åt höger."
- "%s genom att dra nedåt."
- "Vibrera"
- "Vibrera"
- "Ljud"
- "Standardsignal (%1$s)"
- "Ringsignal"
- "Enheten vibrerar vid samtal"
- "Ringsignal och vibration"
- "Hantera konferenssamtal"
- "Nödsamtalsnummer"
- "Profilbild"
- "Kamera av"
- "via %s"
- "Anteckningen har skickats"
- "Senaste meddelandena"
- "Företagsuppgifter"
- "%.1f miles bort"
- "%.1f km bort"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Öppnar i morgon kl. %s"
- "Öppnar i dag kl. %s"
- "Stänger kl. %s"
- "Stängde i dag kl. %s"
- "Öppet"
- "Stängt"
- "Misstänkt spamsamtal"
- "Samtalet avslutat %1$s"
- "Det här är första gången det här numret ringde dig."
- "Vi misstänkte att det här samtalet var en spammare."
- "Blockera/rapp. spam"
- "Lägg till kontakt"
- "Inte spam"
-
diff --git a/InCallUI/res/values-sw/strings.xml b/InCallUI/res/values-sw/strings.xml
deleted file mode 100644
index d60c4901a76e033fa382a7d52dddf1a38da48d07..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sw/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Simu"
- "Inangoja"
- "Isiyojulikana"
- "Nambari ya faragha"
- "Simu ya kulipia"
- "Simu ya mkutano"
- "Simu imekatwa"
- "Spika"
- "Kipaza sauti cha kichwani"
- "Vifaa vya sauti visivyo na waya"
- "Bluetooth"
- "Ungependa kutuma milio ya sauti inayofuata? \n"
- "Inatuma milio ya simu\n"
- "Tuma"
- "Ndiyo"
- "Hapana"
- "Badilisha herufi inayojitegemea kwa"
- "Simu ya mkutano %s"
- "Nambari ya ujumbe wa sauti"
- "Inapiga"
- "Inapiga simu tena"
- "Simu ya mkutano"
- "Unapigiwa simu"
- "Simu ya kazi inayoingia"
- "Simu imekamilika"
- "Inangoja"
- "Kukata simu"
- "Katika simu"
- "Nambari yangu ni %s"
- "Inaunganisha video"
- "Hangout ya Video"
- "Inaomba video"
- "Haiwezi kuunganisha Hangout ya video"
- "Ombi la video limekataliwa"
- "Nambari yako ya kupigiwa simu\n%1$s"
- "Nambari yako ya dharura ya kupigiwa simu\n%1$s"
- "Inapiga"
- "Simu ambayo hukujibu"
- "Simu ambazo hukujibu"
- "Simu %s ambazo hukujibu"
- "Simu ambayo hukujibu kutoka %s"
- "Simu inayoendelea"
- "Simu ya kazi inayoendelea"
- "Simu ya Wi-Fi inayoendelea"
- "Simu ya Wi-Fi ya kazi inayoendelea"
- "Inangoja"
- "Unapigiwa simu"
- "Unapigiwa simu ya kazi"
- "Unapigiwa simu kupitia Wi-Fi"
- "Unapigiwa simu ya kazini kupitia Wi-Fi"
- "Hangout ya Video inayoingia"
- "Simu inayoingia inashukiwa kuwa taka"
- "Ombi linaloingia la video"
- "Ujumbe mpya wa sauti"
- "Ujumbe (%d) mpya wa sauti"
- "Piga %s"
- "Nambari ya ujumbe wa sauti haijulikani."
- "Hakuna huduma"
- "Mtandao uliochaguliwa (%s) haupatikani"
- "Jibu"
- "Kata simu"
- "Video"
- "Sauti"
- "Kubali"
- "Ondoa"
- "Mpigie"
- "Ujumbe"
- "Una Hangout inayoendelea kwenye kifaa kingine"
- "Hamisha Hangout"
- "Ili upige simu kwanza, zima Hali ya ndegeni."
- "Haijasajiliwa kwenye mtandao."
- "Mitandao ya simu za mkononi haipatikani."
- "Ili upige simu, weka nambari sahihi."
- "Haiwezi kupiga simu."
- "Inaanzisha msururu wa MMI…"
- "Huduma haitumiki."
- "Haiwezi kubadili simu."
- "Haiwezi kutenganisha simu."
- "Haiwezi kuhamisha."
- "Haiwezi kushiriki katika simu ya mkutano."
- "Haiwezi kukataa simu."
- "Haiwezi kutoa simu."
- "Simu ya SIP"
- "Simu ya dharura"
- "Inawasha redio..."
- "Hakuna huduma. Inajaribu tena..."
- "Haiwezi kupiga simu. %s si nambari ya dharura."
- "Haiwezi kupiga simu. Piga simu nambari ya dharura."
- "Tumia kibodi kubonyeza"
- "Shikilia Simu"
- "Endelea na Simu"
- "Kata Simu"
- "Onyesha Vitufe vya Kupiga Simu"
- "Ficha Vitufe vya Kupiga Simu"
- "Zima Sauti"
- "Rejesha sauti"
- "Ongeza simu"
- "Unganisha simu"
- "Badili"
- "Dhibiti simu"
- "Dhibiti simu ya mkutano"
- "Mkutano kwenye simu"
- "Dhibiti"
- "Sauti"
- "Hangout ya Video"
- "Badilisha iwe simu ya sauti"
- "Badilisha kamera"
- "Washa kamera"
- "Zima kamera"
- "Chaguo zaidi"
- "Kichezaji Kimeanzishwa"
- "Kichezaji Kimekomeshwa"
- "Kamera haiko tayari"
- "Kamera iko tayari"
- "Tukio lisilojulikana la kipindi cha simu"
- "Huduma"
- "Weka mipangilio"
- "<Haijawekwa>"
- "Mipangilio mingine ya simu"
- "Kupiga simu kupitia %s"
- "Simu zinazoingia kupitia %s"
- "picha ya anwani"
- "tumia kwa faragha"
- "chagua anwani"
- "Andika yako binafsi..."
- "Ghairi"
- "Tuma"
- "Jibu"
- "Tuma SMS"
- "Kataa"
- "Pokea kama Hangout ya Video"
- "Pokea kama simu ya sauti"
- "Kubali ombi la video"
- "Kataa ombi la video"
- "Kubali ombi la kutuma kupitia hangout ya video"
- "Kataa ombi la kutuma kupitia hangout ya video"
- "Kubali ombi la kupokea kupitia hangout ya video"
- "Kataa ombi la kupokea kupitia hangout ya video"
- "Telezesha kidole juu ili %s ."
- "Telezesha kidole kushoto ili %s."
- "Telezesha kidole kulia ili %s."
- "Telezesha kidole chini ili %s."
- "Mtetemo"
- "Mtetemo"
- "Mlio"
- "Sauti chaguo-msingi (%1$s)"
- "Mlio wa simu"
- "Tetema wakati wa kuita"
- "Mlio wa simu na Mtetemo"
- "Dhibiti simu ya mkutano"
- "Nambari ya dharura"
- "Picha ya wasifu"
- "Kamera imezimwa"
- "kupitia %s"
- "Dokezo limetumwa"
- "Ujumbe wa hivi majuzi"
- "Maelezo ya biashara"
- "Umbali wa maili %.1f"
- "Umbali wa kilomita %.1f"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Itafunguliwa kesho saa %s"
- "Itafunguliwa leo saa %s"
- "Hufungwa saa %s"
- "Imefungwa leo saa %s"
- "Sasa imefunguliwa"
- "Sasa imefungwa"
- "Mpiga simu taka"
- "Simu imekatwa %1$s"
- "Hii ndiyo mara ya kwanza nambari hii imekupigia."
- "Tunashuku kwamba simu hii ni taka."
- "Zuia/ripoti taka"
- "Ongeza anwani"
- "Si barua taka"
-
diff --git a/InCallUI/res/values-sw360dp/dimens.xml b/InCallUI/res/values-sw360dp/dimens.xml
deleted file mode 100644
index 9fbcd605b454e022885c518496a6da0f33c86e6f..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sw360dp/dimens.xml
+++ /dev/null
@@ -1,35 +0,0 @@
-
-
-
-
-
-
-
- 22sp
- 18sp
- 45dp
- 34sp
- 18sp
-
-
- @dimen/dialpad_key_number_default_margin_bottom
-
- @dimen/dialpad_zero_key_number_default_margin_bottom
- @dimen/dialpad_digits_text_size
- @dimen/dialpad_digits_height
- @dimen/dialpad_key_numbers_default_size
-
diff --git a/InCallUI/res/values-sw410dp/config.xml b/InCallUI/res/values-sw410dp/config.xml
deleted file mode 100644
index a57f867849f85dd4f35e5a6b22a603c56b1c6ff3..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-sw410dp/config.xml
+++ /dev/null
@@ -1,21 +0,0 @@
-
-
-
-
- 6
-
\ No newline at end of file
diff --git a/InCallUI/res/values-ta/strings.xml b/InCallUI/res/values-ta/strings.xml
deleted file mode 100644
index 1ee57b4bac88db7b9690c26fd7568003b768f6a3..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ta/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ஃபோன்"
- "ஹோல்டில் உள்ளது"
- "தெரியாத எண்"
- "தனிப்பட்ட எண்"
- "கட்டணத் தொலைபேசி"
- "குழு அழைப்பு"
- "அழைப்பு நிறுத்தப்பட்டது"
- "ஸ்பீக்கர்"
- "ஹேண்ட்செட் இயர்ஃபீஸ்"
- "வயருள்ள ஹெட்செட்"
- "புளூடூத்"
- "பின்வரும் டோன்களை அனுப்பவா?\n"
- "டோன்களை அனுப்புகிறது\n"
- "அனுப்பு"
- "ஆம்"
- "வேண்டாம்"
- "சிறப்புக்குறியை இதன் மூலம் மாற்றியமை"
- "குழு அழைப்பு: %s"
- "குரலஞ்சல் எண்"
- "அழைக்கிறது"
- "மீண்டும் டயல் செய்கிறது"
- "குழு அழைப்பு"
- "உள்வரும் அழைப்பு"
- "உள்வரும் அழைப்பு (பணி)"
- "அழைப்பு முடிந்தது"
- "ஹோல்டில் உள்ளது"
- "துண்டிக்கிறது"
- "அழைப்பில்"
- "எனது எண்: %s"
- "வீடியோவை இணைக்கிறது"
- "வீடியோ அழைப்பு"
- "வீடியோவைக் கோருகிறது"
- "வீடியோ அழைப்பை இணைக்க முடியவில்லை"
- "வீடியோ கோரிக்கை நிராகரிக்கப்பட்டது"
- "உங்களைத் திரும்ப அழைப்பதற்கான எண்\n %1$s"
- "அவசர அழைப்பு எண்\n %1$s"
- "அழைக்கிறது"
- "தவறிய அழைப்பு"
- "தவறிய அழைப்புகள்"
- "%s தவறிய அழைப்புகள்"
- "%s இடமிருந்து தவறிய அழைப்பு"
- "செயலில் இருக்கும் அழைப்பு"
- "செயலில் இருக்கும் அழைப்பு (பணி)"
- "செயலில் இருக்கும் வைஃபை அழைப்பு"
- "செயலில் இருக்கும் வைஃபை அழைப்பு"
- "ஹோல்டில் உள்ளது"
- "உள்வரும் அழைப்பு"
- "உள்வரும் அழைப்பு (பணி)"
- "உள்வரும் வைஃபை அழைப்பு"
- "உள்வரும் வைஃபை அழைப்பு (பணி)"
- "உள்வரும் வீடியோ அழைப்பு"
- "உள்வரும் சந்தேகத்திற்குரிய ஸ்பேம் அழைப்பு"
- "உள்வரும் வீடியோ கோரிக்கை"
- "புதிய குரலஞ்சல்"
- "புதிய குரலஞ்சல் (%d)"
- "%sஐ அழை"
- "குரலஞ்சல் எண் அறியப்படவில்லை"
- "சேவை இல்லை"
- "தேர்ந்தெடுத்த நெட்வொர்க் (%s) கிடைக்கவில்லை"
- "பதிலளி"
- "துண்டி"
- "வீடியோ"
- "குரல்"
- "ஏற்கிறேன்"
- "நிராகரி"
- "திரும்ப அழை"
- "செய்தி அனுப்பு"
- "மற்றொரு சாதனத்தில் செயலில் இருக்கும் அழைப்பு"
- "அழைப்பை இடமாற்று"
- "அழைப்பதற்கு, முதலில் விமானப் பயன்முறையை முடக்கவும்."
- "நெட்வொர்க்கில் பதிவுசெய்யப்படவில்லை."
- "செல்லுலார் நெட்வொர்க் கிடைக்கவில்லை."
- "அழைக்க, சரியான எண்ணை உள்ளிடவும்."
- "அழைக்க முடியாது."
- "MMI வரிசையைத் தொடங்குகிறது..."
- "சேவை ஆதரிக்கப்படவில்லை."
- "அழைப்புகளில் மாற முடியாது."
- "அழைப்பைப் பிரிக்க முடியாது."
- "மாற்ற முடியாது."
- "குழு அழைப்பு செய்ய முடியாது."
- "அழைப்பை நிராகரிக்க முடியாது."
- "அழைப்பை(அழைப்புகளை) விடுவிக்க முடியாது."
- "SIP அழைப்பு"
- "அவசர அழைப்பு"
- "ரேடியோவை இயக்குகிறது…"
- "சேவை இல்லை. மீண்டும் முயல்கிறது…"
- "%s என்பது அவசர அழைப்பு எண் இல்லை என்பதால் அழைக்க முடியாது."
- "அழைக்க முடியாது. அவசர அழைப்பு எண்ணை அழைக்கவும்."
- "டயல் செய்ய, விசைப்பலகையைப் பயன்படுத்தவும்"
- "அழைப்பை ஹோல்டில் வை"
- "அழைப்பை மீண்டும் தொடங்கு"
- "அழைப்பை முடி"
- "டயல்பேடைக் காட்டு"
- "டயல்பேடை மறை"
- "ஒலியடக்கு"
- "ஒலி இயக்கு"
- "அழைப்பைச் சேர்"
- "அழைப்புகளை இணை"
- "மாற்று"
- "அழைப்புகளை நிர்வகி"
- "குழு அழைப்பை நிர்வகி"
- "குழு அழைப்பு"
- "நிர்வகி"
- "ஆடியோ"
- "வீடியோ அழைப்பு"
- "குரல் அழைப்பிற்கு மாறு"
- "கேமராவை மாற்று"
- "கேமராவை இயக்கு"
- "கேமராவை முடக்கு"
- "கூடுதல் விருப்பங்கள்"
- "வீடியோ பிளேயர் துவங்கியது"
- "வீடியோ பிளேயர் நிறுத்தப்பட்டது"
- "கேமரா தயாராக இல்லை"
- "கேமரா தயார்"
- "தெரியாத அழைப்பு நேர நிகழ்வு"
- "சேவை"
- "அமை"
- "<அமைக்கப்படவில்லை>"
- "பிற அழைப்பு அமைப்புகள்"
- "%s வழியாக அழைக்கிறது"
- "%s மூலம் உள்வரும் அழைப்புகள்"
- "தொடர்புப் படம்"
- "தனிப்பட்டதிற்குச் செல்"
- "தொடர்பைத் தேர்ந்தெடுக்கவும்"
- "சொந்தமாக எழுதவும்..."
- "ரத்துசெய்"
- "அனுப்பு"
- "பதிலளி"
- "SMS அனுப்பு"
- "நிராகரி"
- "வீடியோ அழைப்பில் பதிலளி"
- "ஆடியோ அழைப்பில் பதிலளி"
- "வீடியோ கோரிக்கையை அனுமதி"
- "வீடியோ கோரிக்கையை நிராகரி"
- "வீடியோவைப் பரிமாற்றும் கோரிக்கையை அனுமதி"
- "வீடியோவைப் பரிமாற்றும் கோரிக்கையை நிராகரி"
- "வீடியோவைப் பெறும் கோரிக்கையை அனுமதி"
- "வீடியோவைப் பெறும் கோரிக்கையை நிராகரி"
- "%s, மேலே ஸ்லைடு செய்க."
- "%s, இடப்புறம் ஸ்லைடு செய்க."
- "%s, வலப்புறம் ஸ்லைடு செய்க."
- "%s, கீழே ஸ்லைடு செய்க."
- "அதிர்வுறு"
- "அதிர்வுறு"
- "ஒலி"
- "இயல்பு ஒலி (%1$s)"
- "ஃபோனின் ரிங்டோன்"
- "அழைக்கும் போது அதிர்வுறு"
- "ரிங்டோன் & அதிர்வு"
- "குழு அழைப்பை நிர்வகி"
- "அவசர அழைப்பு எண்"
- "சுயவிவரப் படம்"
- "கேமரா முடக்கப்பட்டது"
- "%s வழியாக"
- "குறிப்பு அனுப்பப்பட்டது"
- "சமீபத்திய செய்திகள்"
- "வணிகத் தகவல்"
- "%.1f மைல் தொலைவில்"
- "%.1f கிமீ தொலைவில்"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "நாளை %sக்குத் திறக்கப்படும்"
- "இன்று %sக்குத் திறக்கப்படும்"
- "%sக்கு மூடப்படும்"
- "இன்று %sக்கு மூடப்பட்டது"
- "இப்போது திறக்கப்பட்டுள்ளது"
- "இப்போது மூடப்பட்டுள்ளது"
- "சந்தேகத்திற்குரிய ஸ்பேம் அழைப்பாளர்"
- "அழைப்பு துண்டிக்கப்பட்டது %1$s"
- "இந்த எண்ணிலிருந்து உங்களுக்கு அழைப்பு வந்தது இதுவே முதல் முறை."
- "இந்த அழைப்பு ஸ்பேமராக இருக்கக்கூடும் என சந்தேகிக்கிறோம்."
- "தடு/ஸ்பேமென புகாரளி"
- "தொடர்பைச் சேர்"
- "ஸ்பேமில்லை"
-
diff --git a/InCallUI/res/values-te/strings.xml b/InCallUI/res/values-te/strings.xml
deleted file mode 100644
index 936f1be7cc18761af5287b873c5c3a20d77bcd31..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-te/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "ఫోన్"
- "హోల్డ్లో ఉంది"
- "తెలియదు"
- "ప్రైవేట్ నంబర్"
- "పే ఫోన్"
- "కాన్ఫరెన్స్ కాల్"
- "కాల్ కట్ అయింది"
- "స్పీకర్"
- "హ్యాండ్సెట్ ఇయర్పీస్"
- "వైర్ గల హెడ్సెట్"
- "బ్లూటూత్"
- "కింది టోన్లను పంపాలా?\n"
- "టోన్లు పంపుతోంది\n"
- "పంపు"
- "అవును"
- "వద్దు"
- "దీనితో వైల్డ అక్షరాన్ని భర్తీ చేయండి"
- "కాన్ఫరెన్స్ కాల్ %s"
- "వాయిస్ మెయిల్ నంబర్"
- "డయల్ చేస్తోంది"
- "మళ్లీ డయల్ చేస్తోంది"
- "కాన్ఫరెన్స్ కాల్"
- "ఇన్కమింగ్ కాల్"
- "ఇన్కమింగ్ కార్యాలయ కాల్"
- "కాల్ ముగిసింది"
- "హోల్డ్లో ఉంది"
- "ముగిస్తోంది"
- "కాల్లో ఉంది"
- "నా నంబర్ %s"
- "వీడియోను కనెక్ట్ చేస్తోంది"
- "వీడియో కాల్"
- "వీడియో కోసం అభ్యర్థిస్తోంది"
- "వీడియో కాల్ను కనెక్ట్ చేయలేరు"
- "వీడియో అభ్యర్థన తిరస్కరించబడింది"
- "మీ కాల్బ్యాక్ నంబర్\n %1$s"
- "మీ అత్యవసర కాల్బ్యాక్ నంబర్\n %1$s"
- "డయల్ చేస్తోంది"
- "సమాధానం ఇవ్వని కాల్"
- "సమాధానం ఇవ్వని కాల్లు"
- "%s సమాధానం ఇవ్వని కాల్లు"
- "%s నుండి సమాధానం ఇవ్వని కాల్"
- "కాల్ కొనసాగుతోంది"
- "కార్యాలయ కాల్ కొనసాగుతోంది"
- "Wi-Fi కాల్ కొనసాగుతోంది"
- "Wi-Fi కార్యాలయ కాల్ కొనసాగుతోంది"
- "హోల్డ్లో ఉంది"
- "ఇన్కమింగ్ కాల్"
- "ఇన్కమింగ్ కార్యాలయ కాల్"
- "ఇన్కమింగ్ Wi-Fi కాల్"
- "ఇన్కమింగ్ Wi-Fi కార్యాలయ కాల్"
- "ఇన్కమింగ్ వీడియో కాల్"
- "అనుమానాస్పద స్పామ్ కాల్ వస్తోంది"
- "ఇన్కమింగ్ వీడియో అభ్యర్థన"
- "కొత్త వాయిస్ మెయిల్"
- "కొత్త వాయిస్ మెయిల్ (%d)"
- "%sకు డయల్ చేయండి"
- "వాయిస్ మెయిల్ నంబర్ తెలియదు"
- "సేవ లేదు"
- "ఎంచుకున్న నెట్వర్క్ (%s) అందుబాటులో లేదు"
- "సమాధానం"
- "కాల్ ముగించు"
- "వీడియో"
- "వాయిస్"
- "ఆమోదిస్తున్నాను"
- "తీసివేయి"
- "తిరిగి కాల్ చేయి"
- "సందేశం పంపు"
- "మరో పరికరంలో కాల్ జరుగుతోంది"
- "కాల్ను బదిలీ చేయి"
- "కాల్ చేయడానికి, ముందుగా ఎయిర్ప్లైన్ మోడ్ను ఆపివేయండి."
- "నెట్వర్క్లో నమోదు కాలేదు."
- "సెల్యులార్ నెట్వర్క్ అందుబాటులో లేదు."
- "కాల్ చేయడానికి, చెల్లుబాటు అయ్యే నంబర్ను నమోదు చేయండి."
- "కాల్ చేయలేరు."
- "MMI శ్రేణిని ప్రారంభిస్తోంది…"
- "సేవకు మద్దతు లేదు."
- "కాల్లను మార్చలేరు."
- "కాల్ను వేరు చేయలేరు."
- "బదిలీ చేయలేరు."
- "కాన్ఫరెన్స్ కాల్ కుదరదు."
- "కాల్ను తిరస్కరించలేరు."
- "కాల్(ల)ను విడిచిపెట్టలేరు."
- "SIP కాల్"
- "అత్యవసర కాల్"
- "రేడియోను ఆన్ చేస్తోంది…"
- "సేవ లేదు. మళ్లీ ప్రయత్నిస్తోంది…"
- "కాల్ చేయలేరు. %s అత్యవసర నంబర్ కాదు."
- "కాల్ చేయలేరు. అత్యవసర నంబర్కు డయల్ చేయండి."
- "డయల్ చేయడానికి కీబోర్డ్ను ఉపయోగించండి"
- "కాల్ను హోల్డ్లో ఉంచు"
- "కాల్ను పునఃప్రారంభించు"
- "కాల్ని ముగించు"
- "డయల్ప్యాడ్ను చూపు"
- "డయల్ప్యాడ్ను దాచు"
- "మ్యూట్ చేయి"
- "అన్మ్యూట్ చేయి"
- "కాల్ను జోడించు"
- "కాల్లను విలీనం చేయి"
- "స్వాప్ చేయి"
- "కాల్లను నిర్వహించు"
- "కాన్ఫరెన్స్ కాల్ను నిర్వహించు"
- "కాన్ఫరెన్స్ కాల్"
- "నిర్వహించు"
- "ఆడియో"
- "వీడియో కాల్"
- "వాయిస్ కాల్కి మార్చు"
- "కెమెరాను మార్చు"
- "కెమెరాను ఆన్ చేయి"
- "కెమెరాను ఆఫ్ చేయి"
- "మరిన్ని ఎంపికలు"
- "ప్లేయర్ ప్రారంభమైంది"
- "ప్లేయర్ ఆపివేయబడింది"
- "కెమెరా సిద్ధంగా లేదు"
- "కెమెరా సిద్ధంగా ఉంది"
- "తెలియని కాల్ సెషన్ ఉదంతం"
- "సేవ"
- "సెటప్ చేయండి"
- "<సెట్ చేయలేదు>"
- "ఇతర కాల్ సెట్టింగ్లు"
- "%s ద్వారా కాల్ చేయబడుతోంది"
- "%s ద్వారా ఇన్కమింగ్"
- "పరిచయం ఫోటో"
- "ప్రైవేట్గా వెళ్లు"
- "పరిచయాన్ని ఎంచుకోండి"
- "మీ స్వంతంగా వ్రాయండి…"
- "రద్దు చేయి"
- "పంపు"
- "సమాధానం"
- "SMSని పంపుతుంది"
- "తిరస్కరిస్తుంది"
- "వీడియో కాల్ రూపంలో సమాధానం"
- "ఆడియో కాల్ రూపంలో సమాధానం"
- "వీడియో అభ్యర్థనను ఆమోదిస్తుంది"
- "వీడియో అభ్యర్థనను తిరస్కరిస్తుంది"
- "వీడియో ప్రసరణ అభ్యర్థనను ఆమోదిస్తుంది"
- "వీడియో ప్రసరణ అభ్యర్థనను తిరస్కరిస్తుంది"
- "వీడియో స్వీకరణ అభ్యర్థనను ఆమోదిస్తుంది"
- "వీడియో స్వీకరణ అభ్యర్థనను తిరస్కరిస్తుంది"
- "%s కోసం పైకి స్లైడ్ చేయండి."
- "%s కోసం ఎడమవైపుకు స్లైడ్ చేయండి."
- "%s కోసం కుడివైపుకు స్లైడ్ చేయండి."
- "%s కోసం కిందికి స్లైడ్ చేయండి."
- "వైబ్రేట్"
- "వైబ్రేట్"
- "ధ్వని"
- "డిఫాల్ట్ ధ్వని (%1$s)"
- "ఫోన్ రింగ్టోన్"
- "రింగ్ అయ్యేప్పుడు వైబ్రేషన్"
- "రింగ్టోన్ & వైబ్రేట్"
- "కాన్ఫరెన్స్ కాల్ను నిర్వహించు"
- "అత్యవసర నంబర్"
- "ప్రొఫైల్ ఫోటో"
- "కెమెరా ఆఫ్లో ఉంది"
- "%s ద్వారా"
- "గమనిక పంపబడింది"
- "ఇటీవలి సందేశాలు"
- "వ్యాపార సంస్థ సమాచారం"
- "%.1f మై దూరంలో ఉంది"
- "%.1f కి.మీ దూరంలో ఉంది"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "రేపు %sకి తెరవబడుతుంది"
- "ఈరోజు %sకి తెరవబడుతుంది"
- "%sకి మూసివేయబడుతుంది"
- "ఈరోజు %sకి మూసివేయబడి ఉంటుంది"
- "ఇప్పుడు తెరిచి ఉంది"
- "ఇప్పుడు మూసివేయబడింది"
- "అనుమానిత స్పామ్ కాలర్"
- "కాల్ ముగిసింది %1$s"
- "ఈ నంబర్ నుండి మీకు కాల్ రావడం ఇదే మొదటిసారి."
- "ఈ కాల్ స్పామర్ కావచ్చని మేము అనుమానిస్తున్నాము."
- "బ్లాక్/స్పామ్ నివే."
- "పరిచయాన్ని జోడించు"
- "స్పామ్ కాదు"
-
diff --git a/InCallUI/res/values-th/strings.xml b/InCallUI/res/values-th/strings.xml
deleted file mode 100644
index 69ae44d07e69b673a69a661dd45af6fda70960e2..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-th/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "โทรศัพท์"
- "พักสาย"
- "ไม่ทราบ"
- "หมายเลขส่วนตัว"
- "โทรศัพท์สาธารณะ"
- "การประชุมสาย"
- "สายหลุด"
- "ลำโพง"
- "ชุดหูฟังโทรศัพท์"
- "ชุดหูฟังแบบมีสาย"
- "บลูทูธ"
- "ส่งหมายเลขต่อไปไหม\n"
- "กำลังส่งหมายเลข\n"
- "ส่ง"
- "ใช่"
- "ไม่"
- "แทนที่อักขระแทนด้วย"
- "การประชุมสาย %s"
- "หมายเลขข้อความเสียง"
- "กำลังโทรออก"
- "โทรใหม่"
- "การประชุมสาย"
- "สายเรียกเข้า"
- "มีสายเรียกเข้าจากที่ทำงาน"
- "วางสายแล้ว"
- "พักสาย"
- "กำลังวางสาย"
- "กำลังใช้สาย"
- "หมายเลขของฉันคือ %s"
- "กำลังเชื่อมต่อวิดีโอ"
- "แฮงเอาท์วิดีโอ"
- "กำลังขอวิดีโอ"
- "ไม่สามารถเชื่อมต่อแฮงเอาท์วิดีโอได้"
- "คำขอวิดีโอถูกปฏิเสธ"
- "หมายเลขโทรกลับของคุณ\n %1$s"
- "หมายเลขโทรกลับฉุกเฉินของคุณ\n %1$s"
- "กำลังโทรออก"
- "สายที่ไม่ได้รับ"
- "สายที่ไม่ได้รับ"
- "ไม่ได้รับ %s สาย"
- "สายที่ไม่ได้รับจาก %s"
- "โทรต่อเนื่อง"
- "กำลังอยู่ในสายจากที่ทำงาน"
- "กำลังโทรผ่าน Wi-Fi"
- "กำลังอยู่ในสายจากที่ทำงานผ่าน Wi-Fi"
- "พักสาย"
- "สายเรียกเข้า"
- "มีสายเรียกเข้าจากที่ทำงาน"
- "สายโทรเข้าผ่าน Wi-Fi"
- "มีสายเรียกเข้าจากที่ทำงานผ่าน Wi-Fi"
- "แฮงเอาท์วิดีโอเรียกเข้า"
- "สายเรียกเข้าที่สงสัยว่าเป็นสแปม"
- "คำขอโทรเข้าเป็นวิดีโอ"
- "ข้อความเสียงใหม่"
- "ข้อความเสียงใหม่ (%d)"
- "หมุนหมายเลข %s"
- "ไม่ทราบหมายเลขข้อความเสียง"
- "ไม่มีบริการ"
- "เครือข่ายที่เลือกไว้ (%s) ไม่พร้อมใช้งาน"
- "รับสาย"
- "วางสาย"
- "วิดีโอ"
- "เสียง"
- "ยอมรับ"
- "ปิด"
- "โทรกลับ"
- "ข้อความ"
- "กำลังใช้สายบนอุปกรณ์อื่น"
- "โอนสาย"
- "หากต้องการโทรออก ให้ปิดโหมดบนเครื่องบินก่อน"
- "ยังไม่ได้ลงทะเบียนบนเครือข่าย"
- "เครือข่ายมือถือใช้งานไม่ได้"
- "หากต้องการโทรออก โปรดป้อนหมายเลขที่ถูกต้อง"
- "ไม่สามารถโทรได้"
- "กำลังเริ่มต้นลำดับ MMI..."
- "ไม่สนับสนุนบริการนี้"
- "ไม่สามารถสลับสายได้"
- "ไม่สามารถแยกสายได้"
- "ไม่สามารถโอนได้"
- "ไม่สามารถประชุมได้"
- "ไม่สามารถปฏิเสธสายได้"
- "ไม่สามารถเริ่มการโทรได้"
- "โทรแบบ SIP"
- "หมายเลขฉุกเฉิน"
- "กำลังเปิดวิทยุ…"
- "ไม่มีบริการ โปรดลองอีกครั้ง…"
- "โทรออกไม่ได้ %s ไม่ใช่หมายเลขฉุกเฉิน"
- "ไม่สามารถโทรออก โทรหมายเลขฉุกเฉิน"
- "ใช้แป้นพิมพ์กดหมายเลขโทรศัพท์"
- "พักสาย"
- "โทรต่อ"
- "วางสาย"
- "แสดงแป้นหมายเลข"
- "ซ่อนแป้นหมายเลข"
- "ปิดเสียง"
- "เปิดเสียง"
- "เพิ่มการโทร"
- "รวมสาย"
- "สลับ"
- "จัดการการโทร"
- "จัดการการประชุมสาย"
- "การประชุมสาย"
- "จัดการ"
- "เสียง"
- "แฮงเอาท์วิดีโอ"
- "เปลี่ยนเป็นการโทรด้วยเสียง"
- "เปลี่ยนกล้อง"
- "เปิดกล้อง"
- "ปิดกล้อง"
- "ตัวเลือกเพิ่มเติม"
- "โปรแกรมเล่นเริ่มทำงานแล้ว"
- "โปรแกรมเล่นหยุดแล้ว"
- "กล้องไม่พร้อมทำงาน"
- "กล้องพร้อมทำงาน"
- "เหตุการณ์เซสชันการโทรที่ไม่รู้จัก"
- "บริการ"
- "ตั้งค่า"
- "<ไม่ได้ตั้งค่า>"
- "การตั้งค่าการโทรอื่นๆ"
- "โทรผ่าน %s"
- "สายเรียกเข้าผ่าน %s"
- "ภาพของรายชื่อติดต่อ"
- "เข้าสู่โหมดส่วนตัว"
- "เลือกรายชื่อติดต่อ"
- "เขียนคำตอบของคุณเอง..."
- "ยกเลิก"
- "ส่ง"
- "รับสาย"
- "ส่ง SMS"
- "ปฏิเสธ"
- "รับสายเป็นแฮงเอาท์วิดีโอ"
- "รับสายเป็นการโทรด้วยเสียง"
- "ยอมรับคำขอวิดีโอ"
- "ปฏิเสธคำขอวิดีโอ"
- "ยอมรับคำขอให้ส่งวิดีโอ"
- "ปฏิเสธคำขอให้ส่งวิดีโอ"
- "ยอมรับคำขอให้รับวิดีโอ"
- "ปฏิเสธคำขอให้รับวิดีโอ"
- "เลื่อนไปข้างบนเพื่อ %s"
- "เลื่อนไปทางซ้ายเพื่อ %s"
- "เลื่อนไปทางขวาเพื่อ %s"
- "เลื่อนลงเพื่อ %s"
- "สั่น"
- "สั่น"
- "เสียง"
- "เสียงเริ่มต้น (%1$s)"
- "เสียงเรียกเข้าโทรศัพท์"
- "สั่นเมื่อมีสายเข้า"
- "เสียงเรียกเข้าและสั่น"
- "จัดการการประชุมสาย"
- "หมายเลขฉุกเฉิน"
- "รูปโปรไฟล์"
- "ปิดกล้อง"
- "ผ่านหมายเลข %s"
- "ส่งโน้ตแล้ว"
- "ข้อความล่าสุด"
- "ข้อมูลธุรกิจ"
- "อยู่ห่างออกไป %.1f ไมล์"
- "อยู่ห่างออกไป %.1f กม."
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "เปิดให้บริการพรุ่งนี้เวลา %s"
- "เปิดให้บริการวันนี้เวลา %s"
- "ปิดให้บริการเวลา %s"
- "ปิดให้บริการแล้ววันนี้เวลา %s"
- "ขณะนี้เปิดทำการ"
- "ขณะนี้ปิดทำการ"
- "ผู้โทรที่สงสัยว่าเป็นสแปม"
- "วางสายแล้ว %1$s"
- "หมายเลขนี้โทรหาคุณเป็นครั้งแรก"
- "เราสงสัยว่าสายนี้จะเป็นนักส่งสแปม"
- "บล็อก/รายงานสแปม"
- "เพิ่มผู้ติดต่อ"
- "ไม่ใช่สแปม"
-
diff --git a/InCallUI/res/values-tl/strings.xml b/InCallUI/res/values-tl/strings.xml
deleted file mode 100644
index b5658d705d43b9941e48061b27a8163c3f48ac58..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-tl/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telepono"
- "Naka-hold"
- "Hindi alam"
- "Pribadong numero"
- "Payphone"
- "Conference call"
- "Naputol ang tawag"
- "Speaker"
- "Handset earpiece"
- "Wired na headset"
- "Bluetooth"
- "Ipapadala ba ang mga sumusunod na tono?\n"
- "Nagpapadala ng mga tono\n"
- "Ipadala"
- "Oo"
- "Hindi"
- "Palitan ang wild character ng"
- "Conference call %s"
- "Numero ng voicemail"
- "Dina-dial"
- "Muling dina-dial"
- "Conference call"
- "Papasok na tawag"
- "Papasok na tawag sa trabaho"
- "Ibinaba ang tawag"
- "Naka-hold"
- "Binababa"
- "Nasa tawag"
- "Ang aking numero ay %s"
- "Ikinokonekta ang video"
- "Mag-video call"
- "Humihiling ng video"
- "Hindi makakonekta sa video call"
- "Tinanggihan ang kahilingan sa video"
- "Ang iyong numero ng callback\n %1$s"
- "Ang iyong emergency na numero ng callback\n %1$s"
- "Dina-dial"
- "Hindi nasagot na tawag"
- "Mga hindi nasagot na tawag"
- "%s (na) hindi nasagot na tawag"
- "Hindi nasagot ang tawag mula kay %s"
- "Kasalukuyang tawag"
- "Kasalukuyang tawag sa trabaho"
- "Kasalukuyang tawag sa Wi-Fi"
- "Kasalukuyang tawag sa trabaho sa pamamagitan ng Wi-Fi"
- "Naka-hold"
- "Papasok na tawag"
- "Papasok na tawag sa trabaho"
- "Papasok na tawag sa Wi-Fi"
- "Papasok na tawag sa trabaho sa pamamagitan ng Wi-Fi"
- "Papasok na video call"
- "Papasok na pinaghihinalaang spam na tawag"
- "Papasok na kahilingan ng video"
- "Bagong voicemail"
- "Bagong voicemail (%d)"
- "I-dial ang %s"
- "Hindi kilala ang numero ng voicemail"
- "Walang serbisyo"
- "Hindi available ang piniling network (%s)"
- "Sagutin"
- "Ibaba"
- "Video"
- "Boses"
- "Tanggapin"
- "I-dismiss"
- "Tawagan"
- "Mensahe"
- "Kasalukuyang tawag sa isa pang device"
- "Ilipat ang Tawag"
- "Upang tumawag, paki-off muna ang Airplane mode."
- "Hindi nakarehistro sa network."
- "Hindi available ang cellular network."
- "Upang tumawag, maglagay ng wastong numero."
- "Hindi makatawag."
- "Sinisimulan ang pagkakasunud-sunod ng MMI…"
- "Hindi sinusuportahan ang serbisyo."
- "Hindi mailipat ang mga tawag."
- "Hindi mapaghiwalay ang tawag."
- "Hindi mailipat."
- "Hindi makapag-conference."
- "Hindi matanggihan ang tawag."
- "Hindi mailabas ang (mga) tawag."
- "Tawag sa SIP"
- "Emergency na tawag"
- "Ino-on ang radyo…"
- "Walang serbisyo. Sinusubukang muli…"
- "Hindi makatawag. Ang %s ay hindi isang pang-emergency na numero."
- "Hindi makatawag. Mag-dial ng pang-emergency na numero."
- "Gamitin ang keyboard upang mag-dial"
- "I-hold ang Tawag"
- "Ituloy ang Tawag"
- "Ibaba ang Tawag"
- "Ipakita ang Dialpad"
- "Itago ang Dialpad"
- "I-mute"
- "Alisin sa pagkaka-mute"
- "Magdagdag ng tawag"
- "Pagsamahin ang mga tawag"
- "Pagpalitin"
- "Pamahalaan ang mga tawag"
- "Pamahalaan ang conference call"
- "Conference call"
- "Pamahalaan"
- "Audio"
- "Mag-video call"
- "Gawing voice call"
- "Lumipat ng camera"
- "I-on ang camera"
- "I-off ang camera"
- "Higit pang mga opsyon"
- "Nagsimula na ang Player"
- "Huminto ang Player"
- "Hindi pa handa ang camera"
- "Handa na ang camera"
- "Hindi alam na kaganapan ng session ng tawag"
- "Serbisyo"
- "I-setup"
- "<Hindi nakatakda>"
- "Iba pang mga setting ng tawag"
- "Tumatawag sa pamamagitan ng %s"
- "Papasok sa pamamagitan ng %s"
- "larawan ng contact"
- "maging pribado"
- "pumili ng contact"
- "Sumulat ng sarili mong tugon…"
- "Kanselahin"
- "Ipadala"
- "Sagutin"
- "Magpadala ng SMS"
- "Tanggihan"
- "Sagutin bilang video call"
- "Sagutin bilang audio call"
- "Tanggapin ang kahilingan sa video"
- "Tanggihan ang kahilingan sa video"
- "Tanggapin ang kahilingan sa pagpapadala ng video"
- "Tanggihan ang kahilingan sa pagpapadala ng video"
- "Tanggapin ang kahilingan sa pagtanggap ng video"
- "Tanggihan ang kahilingan sa pagtanggap ng video"
- "Mag-slide pataas para sa %s."
- "Mag-slide pakaliwa para sa %s."
- "Mag-slide pakanan para sa %s."
- "Mag-slide pababa para sa %s."
- "Mag-vibrate"
- "Mag-vibrate"
- "Tunog"
- "Default na tunog (%1$s)"
- "Ringtone ng telepono"
- "Mag-vibrate kapag nagri-ring"
- "Ringtone at Pag-vibrate"
- "Pamahalaan ang conference call"
- "Pang-emergency na numero"
- "Larawan sa profile"
- "Naka-off ang camera"
- "sa pamamagitan ng %s"
- "Naipadala ang tala"
- "Mga kamakailang mensahe"
- "Impormasyon ng negosyo"
- "%.1f (na) milya ang layo"
- "%.1f (na) kilometro ang layo"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Magbubukas bukas nang %s"
- "Magbubukas ngayon nang %s"
- "Magsasara nang %s"
- "Sarado ngayon nang %s"
- "Bukas ngayon"
- "Sarado ngayon"
- "Hinihinalang spam na tumatawag"
- "Natapos ang tawag %1$s"
- "Ito ang unang beses na tinawagan ka ng numerong ito."
- "Pinaghihinalaan naming isang spammer ang tawag na ito."
- "I-block/iulat na spam"
- "Magdagdag ng contact"
- "Hindi spam"
-
diff --git a/InCallUI/res/values-tr/strings.xml b/InCallUI/res/values-tr/strings.xml
deleted file mode 100644
index 405bab8db21cbc0a52dfb9f88a48463f89c18ff7..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-tr/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Beklemede"
- "Bilinmiyor"
- "Gizli numara"
- "Ankesörlü telefon"
- "Konferans görüşmesi"
- "Çağrı kesildi"
- "Hoparlör"
- "Mobil cihaz kulaklığı"
- "Kablolu kulaklık"
- "Bluetooth"
- "Aşağıdaki zil sesleri gönderilsin mi?\n"
- "Numara tonları gönderiliyor\n"
- "Gönder"
- "Evet"
- "Hayır"
- "Joker karakteri şununla değiştir:"
- "Konferans görüşmesi %s"
- "Sesli mesaj numarası"
- "Numara çevriliyor"
- "Yeniden çevriliyor"
- "Konferans görüşmesi"
- "Gelen çağrı"
- "İşle ilgili gelen çağrı"
- "Çağrı sonlandırıldı"
- "Beklemede"
- "Sonlandırılıyor"
- "Görüşmede"
- "Numaram: %s"
- "Video bağlanıyor"
- "Video görüşmesi"
- "Video isteniyor"
- "Video görüşmesi bağlantısı yapılamıyor"
- "Video isteği reddedildi"
- "Geri aranacağınız numara\n %1$s"
- "Acil durumda geri aranacağınız numara\n %1$s"
- "Numara çevriliyor"
- "Cevapsız çağrı"
- "Cevapsız çağrılar"
- "%s cevapsız çağrı"
- "Cevapsız çağrı: %s"
- "Devam eden çağrı"
- "İşle ilgili devam eden çağrı"
- "Devam eden kablosuz çağrı"
- "İşle ilgili devam eden kablosuz çağrı"
- "Beklemede"
- "Gelen çağrı"
- "İşle ilgili gelen çağrı"
- "Gelen kablosuz çağrı"
- "İşle ilgili gelen kablosuz çağrı"
- "Gelen video görüşmesi isteği"
- "Spam olabilecek gelen arama"
- "Gelen video isteği"
- "Yeni sesli mesaj"
- "Yeni sesli mesaj (%d)"
- "Çevir: %s"
- "Sesli mesaj numarası bilinmiyor"
- "Servis yok"
- "Seçili ağ (%s) kullanılamıyor"
- "Yanıtla"
- "Kapat"
- "Video"
- "Ses"
- "Kabul et"
- "Yok say"
- "Geri ara"
- "İleti"
- "Başka bir cihazda devam eden çağrı"
- "Çağrıyı Aktar"
- "Çağrı yapmak için öncelikle Uçak modunu kapatın."
- "Ağda kayıtlı değil."
- "Hücresel ağ kullanılamıyor."
- "Çağrı yapmak için geçerli bir numara girin."
- "Çağrı yapılamıyor."
- "MMI dizisi başlatılıyor…"
- "Service desteklenmiyor"
- "Çağrı geçişi yapılamıyor."
- "Çağrı ayrılamıyor."
- "Aktarılamıyor."
- "Konferans çağrısı yapılamıyor."
- "Çağrı reddedilemiyor."
- "Çağrılar bırakılamıyor."
- "SIP çağrısı"
- "Acil durum çağrısı"
- "Radyo açılıyor…"
- "Servis yok. Tekrar deneniyor…"
- "Çağrı yapılamıyor. %s bir acil durum numarası değil."
- "Çağrı yapılamıyor. Acil durum numarasını çevirin."
- "Çevirmek için klavyeyi kullan"
- "Çağrıyı Beklet"
- "Çağrıyı Devam Ettir"
- "Çağrıyı Sonlandır"
- "Tuş Takımını Göster"
- "Tuş Takımını Gizle"
- "Sesi kapat"
- "Sesi aç"
- "Çağrı ekle"
- "Çağrıları birleştir"
- "Değiştir"
- "Çağrıları yönet"
- "Konferans çağrısını yönet"
- "Konferans çağrısı"
- "Yönet"
- "Ses"
- "Vid. görşm"
- "Sesli çağrıya geç"
- "Kamerayı değiştir"
- "Kamerayı aç"
- "Kamerayı kapat"
- "Diğer seçenekler"
- "Oynatıcı Başlatıldı"
- "Oynatıcı Durduruldu"
- "Kamera hazır değil"
- "Kamera hazır"
- "Bilinmeyen çağrı oturumu etkinliği"
- "Hizmet"
- "Kurulum"
- "<Ayarlanmadı>"
- "Diğer çağrı ayarları"
- "%s üzerinden çağrı yapılıyor"
- "%s adlı sağlayıcı üzerinden gelen çağrı"
- "kişi fotoğrafı"
- "özel görüşmeye geç"
- "kişi seçin"
- "Kendi yanıtınızı oluşturun…"
- "İptal"
- "Gönder"
- "Yanıtla"
- "SMS gönder"
- "Reddet"
- "Video görüşmesi olarak yanıtla"
- "Sesli görüşme olarak yanıtla"
- "Video isteğini kabul et"
- "Video isteğini reddet"
- "Video aktarma isteğini kabul et"
- "Video aktarma isteğini reddet"
- "Video alma isteğini kabul et"
- "Video alma isteğini reddet"
- "%s için yukarı kaydırın."
- "%s için sola kaydırın."
- "%s için sağa kaydırın."
- "%s için aşağı kaydırın."
- "Titreşim"
- "Titreşim"
- "Ses"
- "Varsayılan ses (%1$s)"
- "Telefon zil sesi"
- "Çalarken titret"
- "Zil Sesi ve Titreşim"
- "Konferans çağrısını yönetin"
- "Acil durum numarası"
- "Profil fotoğrafı"
- "Kamera kapalı"
- "%s üzerinden"
- "Not gönderildi"
- "Son iletiler"
- "İşletme bilgileri"
- "%.1f mil uzakta"
- "%.1f km uzakta"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Yarın açılış saati: %s"
- "Bugün açılış saati: %s"
- "Kapanış saati: %s"
- "Bugün kapanış saati: %s"
- "Şu an açık"
- "Şu an kapalı"
- "Spam olabilck arayan"
- "Arama sona erdi %1$s"
- "Bu, bu numaradan ilk aranışınız."
- "Bu aramanın spam olduğundan şüpheleniliyor."
- "Engelle/spam bildir"
- "Kişi ekle"
- "Spam değil"
-
diff --git a/InCallUI/res/values-uk/strings.xml b/InCallUI/res/values-uk/strings.xml
deleted file mode 100644
index b323acd0437098cea7a6d93605c7f111eb5ad56d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-uk/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Номер телефону"
- "Очікування"
- "Невідомо"
- "Приватний номер"
- "Таксофон"
- "Конференц-зв’язок"
- "Виклик перервано"
- "Динамік"
- "Динамік гарнітури"
- "Дротова гарнітура"
- "Bluetooth"
- "Надіслати вказані нижче сигнали?\n"
- "Надсилання сигналів\n"
- "Надіслати"
- "Так"
- "Ні"
- "Замінити довільний символ на"
- "Конференц-зв’язок %s"
- "Номер голосової пошти"
- "Набір номера"
- "Повторний набір"
- "Конференц-зв’язок"
- "Вхідний виклик"
- "Вхідний робочий виклик"
- "Виклик завершено"
- "Очікування"
- "Завершення виклику"
- "Триває виклик"
- "Мій номер: %s"
- "Відеодзвінок: з’єднання"
- "Відеодзвінок"
- "Надсилання запиту на відеодзвінок"
- "Не вдалося здійснити відеодзвінок"
- "Запрошення на відеодзвінок відхилено"
- "Номер для зв’язку:\n%1$s"
- "Екстрений номер:\n%1$s"
- "Набір номера"
- "Пропущений виклик"
- "Пропущені виклики"
- "Пропущено викликів: %s"
- "Пропущений виклик: %s"
- "Поточний виклик"
- "Поточний виклик на робочий телефон"
- "Поточний виклик через Wi-Fi"
- "Поточний виклик на робочий телефон через Wi-Fi"
- "Очікування"
- "Вхідний виклик"
- "Вхідний виклик на робочий телефон"
- "Вхідний виклик через Wi-Fi"
- "Вхідний виклик на робочий телефон через Wi-Fi"
- "Вхідний відеодзвінок"
- "Цей дзвінок може бути спамом"
- "Запит на вхідний відеодзвінок"
- "Нові голосові повідомлення"
- "Нові голосові повідомлення (%d)"
- "Набрати %s"
- "Невідомий номер голосової пошти"
- "Немає зв’язку"
- "Вибрана мережа (%s) недоступна"
- "Відповісти"
- "Завершити"
- "Відео"
- "Гол. виклик"
- "Прийняти"
- "Відхилити"
- "Передзвонити"
- "Написати SMS"
- "Поточний виклик на іншому пристрої"
- "Передати виклик"
- "Щоб зателефонувати, вимкніть режим польоту."
- "Не зареєстровано в мережі."
- "Мобільна мережа недоступна."
- "Щоб зателефонувати, введіть дійсний номер."
- "Не вдається зателефонувати."
- "Запуск ряду MMI…"
- "Служба не підтримується."
- "Неможливо переключитися між викликами."
- "Неможливо розділити виклик."
- "Неможливо перенести."
- "Конференц-зв’язок недоступний."
- "Неможливо відхилити виклик."
- "Неможливо телефонувати."
- "Виклик через протокол SIP"
- "Екстрений виклик"
- "Увімкнення радіо…"
- "Немає зв’язку. Повторна спроба…"
- "Не вдається зателефонувати. %s не є екстреним номером."
- "Не вдається зателефонувати. Наберіть екстрений номер."
- "Використовуйте для набору клавіатуру"
- "Призупинити виклик"
- "Відновити виклик"
- "Завершити виклик"
- "Показати цифрову клавіатуру"
- "Сховати цифрову клавіатуру"
- "Ігнорувати"
- "Не ігнорувати"
- "Додати виклик"
- "Об’єднати виклики"
- "Поміняти виклики"
- "Керувати викликами"
- "Керувати конференц-зв’язком"
- "Конференц-зв’язок"
- "Керувати"
- "Аудіо"
- "Відеодзвінок"
- "Перейти в режим голосового виклику"
- "Вибрати камеру"
- "Увімкнути камеру"
- "Вимкнути камеру"
- "Інші опції"
- "Програвач запущено"
- "Програвач зупинено"
- "Камера неготова"
- "Камера готова"
- "Невідомий сеанс виклику"
- "Служба"
- "Налаштування"
- "<Не налаштовано>"
- "Інші налаштування виклику"
- "Виклик здійснюється через оператора %s"
- "Вхідні виклики через оператора %s"
- "фото контакта"
- "приватна розмова"
- "вибрати контакт"
- "Напишіть власну відповідь…"
- "Скасувати"
- "Надіслати"
- "Відповісти"
- "Надіслати SMS"
- "Відхилити"
- "Відповісти в режимі відеодзвінка"
- "Відповісти в режимі аудіодзвінка"
- "Прийняти запит на відео"
- "Відхилити запит на відео"
- "Прийняти запит на передавання відео"
- "Відхилити запит на передавання відео"
- "Прийняти запит на отримання відео"
- "Відхилити запит на отримання відео"
- "Проведіть пальцем угору, щоб %s."
- "Проведіть пальцем ліворуч, щоб %s."
- "Проведіть пальцем праворуч, щоб %s."
- "Проведіть пальцем донизу, щоб %s."
- "Вібросигнал"
- "Вібросигнал"
- "Звук"
- "Звук за умовчанням (%1$s)"
- "Сигнал дзвінка телефона"
- "Вібрувати під час виклику"
- "Сигнал дзвінка та вібросигнал"
- "Керування конференц-зв’язком"
- "Екстрений номер"
- "Фотографія профілю"
- "Камеру вимкнено"
- "на номер %s"
- "Нотатку надіслано"
- "Нещодавні повідомлення"
- "Інформація про компанію"
- "За %.1f мил."
- "За %.1f км"
- "%1$s, %2$s"
- "%1$s–%2$s"
- "%1$s, %2$s"
- "Відчиняється завтра о %s"
- "Відчиняється сьогодні о %s"
- "Зачиняється о %s"
- "Зачинено сьогодні о %s"
- "Відчинено"
- "Зачинено"
- "Може бути спамом"
- "Дзвінок завершено %1$s"
- "З цього номера вам телефонують уперше."
- "Ми підозрюємо, що телефонував спамер."
- "Заблокувати/це спам"
- "Додати контакт"
- "Не спам"
-
diff --git a/InCallUI/res/values-ur/strings.xml b/InCallUI/res/values-ur/strings.xml
deleted file mode 100644
index 32e0d45aab631b209688bf8debf2002a95818383..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-ur/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "فون"
- "ہولڈ پر ہے"
- "نامعلوم"
- "نجی نمبر"
- "پے فون"
- "کانفرنس کال"
- "کال ختم ہو گئی"
- "اسپیکر"
- "ہینڈسیٹ ایئرپیس"
- "تار والا ہیڈسیٹ"
- "بلوٹوتھ"
- "درج ذیل ٹونز بھیجیں؟\n"
- "ٹونز بھیج رہا ہے\n"
- "بھیجیں"
- "ہاں"
- "نہیں"
- "وائلڈ کریکٹر کو اس کے ساتھ بدلیں"
- "کانفرنس کال %s"
- "صوتی میل نمبر"
- "ڈائل ہو رہا ہے"
- "دوبارہ ڈائل ہو رہا ہے"
- "کانفرنس کال"
- "آنے والی کال"
- "کام سے متعلق آنے والی کال"
- "کال ختم ہوگئی"
- "ہولڈ پر ہے"
- "کال منقطع ہو رہی ہے"
- "کال میں"
- "میرا نمبر ہے %s"
- "ویڈیو منسلک ہو رہی ہے"
- "ویڈیو کال"
- "ویڈیو کی درخواست کی جا رہی ہے"
- "ویڈیو کال منسلک نہیں ہو سکتی"
- "ویڈیو کی درخواست مسترد ہو گئی"
- "آپ کا کال بیک نمبر\n %1$s"
- "آپ کا ہنگامی کال بیک نمبر\n %1$s"
- "ڈائل ہو رہا ہے"
- "چھوٹی ہوئی کال"
- "چھوٹی ہوئی کالیں"
- "%s چھوٹی ہوئی کالیں"
- "%s کی جانب سے چھوٹی ہوئی کال"
- "جاری کال"
- "کام سے متعلق جاری کال"
- "Wi-Fi کال جاری ہے"
- "کام سے متعلق جاری Wi-Fi کال"
- "ہولڈ پر ہے"
- "آنے والی کال"
- "کام سے متعلق آنے والی کال"
- "آنے والی Wi-Fi کال"
- "کام سے متعلق آنے والی Wi-Fi کال"
- "آنے والی ویڈیو کال"
- "آنے والی مشتبہ سپام کال"
- "آنے والی ویڈیو کی درخواست"
- "نیا صوتی میل"
- "نیا صوتی میل (%d)"
- "%s ڈائل کریں"
- "صوتی میل نمبر نامعلوم ہے"
- "کوئی سروس نہیں ہے"
- "منتخب کردہ نیٹ ورک (%s) دستیاب نہیں ہے"
- "جواب"
- "کال منقطع کریں"
- "ویڈیو"
- "آواز"
- "قبول کریں"
- "برخاست کریں"
- "واپس کال کریں"
- "پیغام"
- "ایک اور آلے پر جاری کال"
- "کال منتقل کریں"
- "کال کرنے کیلئے، پہلے ہوائی جہاز طرز کو آف کریں۔"
- "نیٹ ورک پر رجسٹرڈ نہیں ہے۔"
- "سیلولر نیٹ ورک دستیاب نہیں ہے۔"
- "کال کرنے کیلئے، ایک درست نمبر درج کریں۔"
- "کال نہیں ہو سکتی۔"
- "MMI ترتیب شروع ہو رہی ہے…"
- "سروس تعاون یافتہ نہیں ہے۔"
- "کالز سوئچ نہیں ہو سکتیں۔"
- "کال الگ نہیں ہو سکتی۔"
- "منتقل نہیں ہو سکتی۔"
- "کانفرنس نہیں ہو سکتی۔"
- "کال مسترد نہیں ہو سکتی۔"
- "کال(ز) ریلیز نہیں ہو سکتیں۔"
- "SIP کال"
- "ہنگامی کال"
- "ریڈیو آن ہو رہا ہے…"
- "کوئی سروس نہیں ہے۔ دوبارہ کوشش کی جا رہی ہے…"
- "کال نہیں کی جا سکتی۔ %s ایک ہنگامی نمبر نہیں ہے۔"
- "کال نہیں کی جا سکتی۔ ایک ہنگامی نمبر ڈائل کریں۔"
- "ڈائل کرنے کیلئے کی بورڈ استعمال کریں"
- "کال کو ہولڈ کریں"
- "کال کو دوبارہ شروع کریں"
- "کال ختم کریں"
- "ڈائل پیڈ دکھائیں"
- "ڈائل پیڈ چھپائیں"
- "خاموش کریں"
- "آواز چالو کریں"
- "کال شامل کریں"
- "کالز کو ضم کریں"
- "تبادلہ کریں"
- "کالز کا نظم کریں"
- "کانفرنس کال کا نظم کریں"
- "کانفرنس کال"
- "نظم کریں"
- "آڈیو"
- "ویڈیو کال"
- "صوتی کال میں تبدیل کریں"
- "کیمرا سوئچ کریں"
- "کیمرا آن کریں"
- "کیمرا آف کریں"
- "مزید اختیارات"
- "پلیئر شروع ہوگیا"
- "پلیئر بند ہوگیا"
- "کیمرا تیار نہیں ہے"
- "کیمرا تیار ہے"
- "نامعلوم کال سیشن ایونٹ"
- "سروس"
- "ترتیب دیں"
- "<سیٹ نہیں ہے>"
- "کال کی دیگر ترتیبات"
- "کالنگ بذریعہ %s"
- "%s کے ذریعے آنے والی"
- "رابطہ کی تصویر"
- "نجی ہوجائیں"
- "رابطہ منتخب کریں"
- "اپنا ذاتی تحریر کریں…"
- "منسوخ کریں"
- "بھیجیں"
- "جواب دیں"
- "SMS بھیجیں"
- "مسترد کریں"
- "ویڈیو کال کے بطور جواب دیں"
- "آڈیو کال کے بطور جواب دیں"
- "ویڈیو کی درخواست قبول کریں"
- "ویڈیو کی درخواست مسترد کریں"
- "ویڈیو منتقل کرنے کی درخواست قبول کریں"
- "ویڈیو منتقل کرنے کی درخواست مسترد کریں"
- "ویڈیو موصول کرنے کی درخواست قبول کریں"
- "ویڈیو موصول کرنے کی درخواست مسترد کریں"
- "%s کیلئے اوپر سلائیڈ کریں۔"
- "%s کیلئے بائیں سلائیڈ کریں۔"
- "%s کیلئے دائیں سلائیڈ کریں۔"
- "%s کیلئے نیچے سلائیڈ کریں۔"
- "ارتعاش"
- "ارتعاش"
- "آواز"
- "ڈیفالٹ آواز (%1$s)"
- "فون رِنگ ٹون"
- "رِنگ کے وقت مرتعش کریں"
- "رنگ ٹون اور ارتعاش"
- "کانفرنس کال کا نظم کریں"
- "ہنگامی نمبر"
- "پروفائل کی تصویر"
- "کیمرا آف ہے"
- "بذریعہ %s"
- "نوٹ بھیج دیا گیا"
- "حالیہ پیغامات"
- "کاروباری معلومات"
- "%.1f میل دور"
- "%.1f کلومیٹر دور"
- "%1$s، %2$s"
- "%1$s - %2$s"
- "%1$s، %2$s"
- "کل %s بجے کھلے گا"
- "آج %s بجے کھلے گا"
- "%s بجے بند ہوگا"
- "آج %s بجے بند ہوا"
- "ابھی کھلا ہے"
- "اب بند ہے"
- "مشتبہ سپام کالر"
- "کال ختم ہو گئی %1$s"
- "اس نمبر سے پہلی بار آپ کو کال آئی ہے۔"
- "ہمیں شک ہے کہ یہ کال سپامر تھی۔"
- "مسدود کریں/سپام کی اطلاع دیں"
- "رابطہ شامل کریں"
- "سپام نہیں ہے"
-
diff --git a/InCallUI/res/values-uz/strings.xml b/InCallUI/res/values-uz/strings.xml
deleted file mode 100644
index 15d534d25373cbad40ce8c9a6870faeadb1e9f62..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-uz/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Telefon"
- "Kutilmoqda"
- "Noma’lum"
- "Maxfiy raqam"
- "Taksofon"
- "Konferens-aloqa"
- "Chaqiruv uzilib qoldi"
- "Karnay"
- "Telefon quloqchini"
- "Simli garnitura"
- "Bluetooth"
- "Quyidagi tovush signallari yuborilsinmi?\n"
- "Tovush signallari yuborilmoqda\n"
- "Yuborish"
- "Ha"
- "Yo‘q"
- "Universal belgini bunga almashtirish"
- "Konferens-aloqa: %s"
- "Ovozli pochta raqami"
- "Chaqiruv"
- "Qayta terilmoqda"
- "Konferens-aloqa"
- "Kiruvchi qo‘ng‘iroq"
- "Kiruvchi qo‘ng‘iroq (ish)"
- "Chaqiruv tugadi"
- "Kutilmoqda"
- "Suhbat tugatilmoqda"
- "Suhbat"
- "Mening raqamim – %s"
- "Videoga ulanmoqda"
- "Video qo‘ng‘iroq"
- "Video so‘ralmoqda"
- "Video qo‘ng‘iroqqa ulanib bo‘lmadi"
- "Video qo‘ng‘iroq so‘rovi rad etildi"
- "Teskari qo‘ng‘iroq raqamingiz\n %1$s"
- "Favqulodda holatlar uchun teskari qo‘ng‘iroq raqamingiz\n %1$s"
- "Chaqiruv"
- "Javobsiz qo‘ng‘iroq"
- "Javobsiz qo‘ng‘iroqlar"
- "%s ta javobsiz qo‘ng‘iroq"
- "%s qo‘ng‘irog‘i javobsiz qoldirildi"
- "Joriy qo‘ng‘iroq"
- "Joriy qo‘ng‘iroq (ish)"
- "Joriy Wi-Fi qo‘ng‘iroq"
- "Joriy Wi-Fi qo‘ng‘iroq (ish)"
- "Kutilmoqda"
- "Kiruvchi qo‘ng‘iroq"
- "Kiruvchi qo‘ng‘iroq (ish)"
- "Kiruvchi Wi-Fi qo‘ng‘iroq"
- "Kiruvchi Wi-Fi qo‘ng‘iroq (ish)"
- "Kiruvchi video qo‘ng‘iroq"
- "Shubhali kiruvchi qo‘ng‘iroq"
- "Kiruvchi video qo‘ng‘iroq"
- "Yangi ovozli xabar"
- "Yangi ovozli xabar (%d)"
- "%s raqamini terish"
- "Ovozli pochta raqami noma’lum"
- "Xizmat mavjud emas"
- "Tanlangan tarmoq (%s) mavjud emas"
- "Javob berish"
- "Tugatish"
- "Video aloqa"
- "Ovozli aloqa"
- "Qabul qilish"
- "Rad etish"
- "Telefon qilish"
- "SMS yuborish"
- "Boshqa qurilmada hozir qo‘ng‘iroq amalga oshirilmoqda."
- "Qo‘ng‘iroqni o‘tkazish"
- "Parvoz rejimini o‘chirib qo‘ying."
- "Tarmoqda ro‘yxatdan o‘tmagan."
- "Uyali tarmoq mavjud emas."
- "Raqam noto‘g‘ri."
- "Qo‘ng‘iroq qilib bo‘lmadi."
- "MMI tartibi ishga tushmoqda…"
- "Xizmat qo‘llab-quvvatlanmaydi."
- "Qo‘ng‘iroqlarni almashtirib bo‘lmadi."
- "Qo‘ng‘iroqni ajratib bo‘lmadi."
- "O‘tkazib bo‘lmadi."
- "Konferens-aloqa o‘rnatib bo‘lmadi."
- "Qo‘ng‘iroqni rad qilib bo‘lmadi."
- "Qo‘ng‘iroq(lar)ni chiqarib bo‘lmadi."
- "SIP qo‘ng‘iroq"
- "Favqulodda chaqiruv"
- "Radio yoqilmoqda…"
- "Aloqa yo‘q. Qayta urinilmoqda…"
- "Qo‘ng‘iroq qilib bo‘lmadi. %s favqulodda raqam emas."
- "Qo‘ng‘iroq qilib bo‘lmadi. Favqulodda raqamga tering."
- "Terish uchun klaviaturadan foydalaning"
- "Qo‘ng‘iroqni ushlab turish"
- "Qo‘ng‘iroqni davom ettirish"
- "Chaqiruvni tugatish"
- "Raqam terish panelini ochish"
- "Raqam terish panelini yopish"
- "Ovozni o‘chirish"
- "Ovozni yoqish"
- "Chaqiruv qo‘shish"
- "Qo‘ng‘iroqlarni birlashtirish"
- "Almashtirish"
- "Qo‘ng‘iroqlarni boshqarish"
- "Konferens-aloqani sozlash"
- "Konferens-aloqa"
- "Boshqarish"
- "Audio"
- "Video qo‘ng‘iroq"
- "Ovozli qo‘ng‘iroqqa o‘zgartirish"
- "Kamerani almashtirish"
- "Kamerani yoqish"
- "Kamerani o‘chirish"
- "Boshqa sozlamalar"
- "Pleyer ishga tushirildi"
- "Pleyer to‘xtatildi"
- "Kamera tayyor emas"
- "Kamera tayyor"
- "Aloqa seansining noma’lum hodisasi"
- "Xizmat"
- "Sozlash"
- "<Ko‘rsatilmagan>"
- "Boshqa qo‘ng‘iroq sozlamalari"
- "%s orqali qo‘ng‘rioq qilinmoqda"
- "%s orqali kiruvchi qo‘ng‘iroqlar"
- "kontakt rasmi"
- "alohida suhbatga o‘tish"
- "kontaktni tanlash"
- "O‘z javobingizni yozing…"
- "Bekor qilish"
- "Yuborish"
- "Javob berish"
- "SMS yuborish"
- "Rad etish"
- "Video qo‘ng‘iroqqa javob berish"
- "Ovozli qo‘ng‘iroqqa javob berish"
- "Video qo‘ng‘iroq so‘rovini qabul qilish"
- "Video qo‘ng‘iroq so‘rovini rad etish"
- "Video uzatishga ruxsat berish"
- "Video uzatishga ruxsat bermaslik"
- "Kiruvchi video qo‘ng‘iroqni qabul qilish"
- "Kiruvchi video qo‘ng‘iroqni rad etish"
- "%s uchun tepaga suring."
- "%s uchun chapga suring."
- "%s uchun o‘ngga suring."
- "%s uchun pastga suring."
- "Tebranish"
- "Tebranish"
- "Ovoz"
- "Standart ovoz (%1$s)"
- "Telefon ringtoni"
- "Jiringlash vaqtida tebranish"
- "Qo‘ng‘iroq ohangi va tebranish"
- "Konferens-aloqani sozlash"
- "Favqulodda qo‘ng‘iroq raqami"
- "Profil rasmi"
- "Kamera o‘chiq"
- "%s orqali"
- "Xabar yuborildi"
- "So‘nggi xabarlar"
- "Kompaniya haqida ma’lumot"
- "%.1f mil masofada"
- "%.1f km masofada"
- "%1$s, %2$s"
- "%1$s – %2$s"
- "%1$s, %2$s"
- "Ertaga %s da ochiladi"
- "Bugun %s da ochiladi"
- "%s da yopiladi"
- "Bugun %s da yopiladi"
- "Ochiq"
- "Yopiq"
- "Shubhali abonent"
- "Qo‘ng‘iroq yakunlandi (%1$s)"
- "Sizga bu raqamdan birinchi marta qo‘ng‘iroq qilishdi."
- "Bu spam-qo‘ng‘iroqqa o‘xshayapti."
- "Bloklash/spamga"
- "Kontaktni qo‘shish"
- "Spam emas"
-
diff --git a/InCallUI/res/values-vi/strings.xml b/InCallUI/res/values-vi/strings.xml
deleted file mode 100644
index 58a50c278208b8914a6199d63281f970c8df2102..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-vi/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Điện thoại"
- "Đang chờ"
- "Không xác định"
- "Số cá nhân"
- "Điện thoại trả tiền"
- "Cuộc gọi nhiều bên"
- "Cuộc gọi bị gián đoạn"
- "Loa"
- "Tai nghe ĐTDĐ"
- "Tai nghe có dây"
- "Bluetooth"
- "Gửi các âm sau?\n"
- "Đang gửi âm\n"
- "Gửi"
- "Có"
- "Không"
- "Thay thế ký tự tự do bằng"
- "Cuộc gọi nhiều bên %s"
- "Số thư thoại"
- "Đang gọi"
- "Đang quay số lại"
- "Cuộc gọi nhiều bên"
- "Cuộc gọi đến"
- "Cuộc gọi đến về công việc"
- "Cuộc gọi đã kết thúc"
- "Đang chờ"
- "Kết thúc cuộc gọi"
- "Trong cuộc gọi"
- "Số điện thoại của tôi là %s"
- "Đang kết nối video"
- "Cuộc gọi điện video"
- "Đang yêu cầu video"
- "Không kết nối được cuộc gọi điện video"
- "Đã từ chối yêu cầu video"
- "Số gọi lại của bạn\n %1$s"
- "Số gọi lại khẩn cấp của bạn\n %1$s"
- "Đang gọi"
- "Cuộc gọi nhỡ"
- "Cuộc gọi nhỡ"
- "%s cuộc gọi nhỡ"
- "Cuộc gọi nhỡ từ %s"
- "Cuộc gọi đang thực hiện"
- "Cuộc gọi đang diễn ra về công việc"
- "Cuộc gọi đang diễn ra qua Wi-Fi"
- "Cuộc gọi đang diễn ra qua Wi-Fi về công việc"
- "Đang chờ"
- "Cuộc gọi đến"
- "Cuộc gọi đến về công việc"
- "Cuộc gọi đến qua Wi-Fi"
- "Cuộc gọi đến qua Wi-Fi về công việc"
- "Cuộc gọi điện video đến"
- "Cuộc gọi spam đến bị nghi ngờ"
- "Yêu cầu video đến"
- "Thư thoại mới"
- "Thư thoại mới (%d)"
- "Quay số %s"
- "Số thư thoại không xác định"
- "Không có dịch vụ"
- "Mạng được chọn (%s) không khả dụng"
- "Trả lời"
- "Gác máy"
- "Video"
- "Thoại"
- "Chấp nhận"
- "Loại bỏ"
- "Gọi lại"
- "Tin nhắn"
- "Cuộc gọi đang diễn ra trên một thiết bị khác"
- "Chuyển cuộc gọi"
- "Để thực hiện cuộc gọi, trước tiên, hãy tắt chế độ trên Máy bay."
- "Chưa được đăng ký trên mạng."
- "Không có mạng di động."
- "Để thực hiện cuộc gọi, hãy nhập một số hợp lệ."
- "Không thực hiện được cuộc gọi."
- "Đang khởi động chuỗi MMI…"
- "Dịch vụ không được hỗ trợ."
- "Không chuyển đổi được cuộc gọi."
- "Không tách được cuộc gọi."
- "Không chuyển được cuộc gọi."
- "Không thực hiện được cuộc gọi nhiều bên."
- "Không từ chối được cuộc gọi."
- "Không thực hiện được cuộc gọi."
- "Cuộc gọi qua SIP"
- "Cuộc gọi khẩn cấp"
- "Đang bật radio..."
- "Không có dịch vụ nào. Đang thử lại…"
- "Không thực hiện được cuộc gọi. %s không phải là số khẩn cấp."
- "Không thực hiện được cuộc gọi. Hãy quay số khẩn cấp."
- "Sử dụng bàn phím để quay số"
- "Giữ cuộc gọi"
- "Tiếp tục cuộc gọi"
- "Kết thúc cuộc gọi"
- "Hiển thị bàn phím số"
- "Ẩn bàn phím số"
- "Tắt tiếng"
- "Bật tiếng"
- "Thêm cuộc gọi"
- "Hợp nhất cuộc gọi"
- "Hoán đổi"
- "Quản lý cuộc gọi"
- "Quản lý cuộc gọi nhiều bên"
- "Cuộc gọi nhiều bên"
- "Quản lý"
- "Âm thanh"
- "Cuộc gọi điện video"
- "Thay đổi thành cuộc gọi thoại"
- "Chuyển máy ảnh"
- "Bật máy ảnh"
- "Tắt máy ảnh"
- "Tùy chọn khác"
- "Đã khởi động trình phát"
- "Đã dừng trình phát"
- "Máy ảnh chưa sẵn sàng"
- "Máy ảnh đã sẵn sàng"
- "Sự kiện phiên cuộc gọi không xác định"
- "Dịch vụ"
- "Thiết lập"
- "<Chưa được đặt>"
- "Cài đặt cuộc gọi khác"
- "Gọi điện qua %s"
- "Cuộc gọi đến qua %s"
- "ảnh liên hệ"
- "chuyển thành riêng tư"
- "chọn địa chỉ liên hệ"
- "Viết trả lời của riêng bạn..."
- "Hủy"
- "Gửi"
- "Trả lời"
- "Gửi SMS"
- "Từ chối"
- "Trả lời là cuộc gọi điện video"
- "Trả lời là cuộc gọi âm thanh"
- "Chấp nhận yêu cầu cuộc gọi video"
- "Từ chối yêu cầu cuộc gọi video"
- "Chấp nhận yêu cầu truyền video"
- "Từ chối yêu cầu truyền video"
- "Chấp nhận yêu cầu nhận video"
- "Từ chối yêu cầu nhận video"
- "Trượt lên để %s."
- "Trượt sang trái để %s."
- "Trượt sang phải để %s."
- "Trượt xuống để %s."
- "Rung"
- "Rung"
- "Âm thanh"
- "Âm thanh mặc định (%1$s)"
- "Nhạc chuông điện thoại"
- "Rung khi đổ chuông"
- "Nhạc chuông và rung"
- "Quản lý cuộc gọi nhiều bên"
- "Số khẩn cấp"
- "Ảnh hồ sơ"
- "Tắt máy ảnh"
- "qua %s"
- "Đã gửi ghi chú"
- "Tin nhắn gần đây"
- "Thông tin doanh nghiệp"
- "Cách %.1f dặm"
- "Cách %.1f km"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Mở cửa lúc %s ngày mai"
- "Mở cửa lúc %s hôm nay"
- "Đóng cửa lúc %s"
- "Đã đóng cửa lúc %s hôm nay"
- "Mở ngay bây giờ"
- "Hiện đã đóng cửa"
- "Người gọi spam bị nghi ngờ"
- "Đã kết thúc cuộc gọi %1$s"
- "Đây là lần đầu tiên số điện thoại này gọi điện cho bạn."
- "Chúng tôi đã nghi ngờ cuộc gọi này là người gửi spam."
- "Chặn/báo cáo spam"
- "Thêm liên hệ"
- "Không phải là spam"
-
diff --git a/InCallUI/res/values-w500dp-land/colors.xml b/InCallUI/res/values-w500dp-land/colors.xml
deleted file mode 100644
index 77eea2e6804f342bf4923766947f26ba321d4cef..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-w500dp-land/colors.xml
+++ /dev/null
@@ -1,21 +0,0 @@
-
-
-
-
-
- #000000
-
diff --git a/InCallUI/res/values-w500dp-land/dimens.xml b/InCallUI/res/values-w500dp-land/dimens.xml
deleted file mode 100644
index 112ec5f09b1fc8480a771095a9d4cfb2723054b9..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-w500dp-land/dimens.xml
+++ /dev/null
@@ -1,35 +0,0 @@
-
-
-
-
-
- true
-
-
- true
-
-
- 40dp
-
-
- 30dp
-
- 2dp
-
- 20dp
-
diff --git a/InCallUI/res/values-zh-rCN/strings.xml b/InCallUI/res/values-zh-rCN/strings.xml
deleted file mode 100644
index f9c43764d78aa3c32929ca679601fb61fdf53aaf..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-zh-rCN/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "电话"
- "保持"
- "未知"
- "私密号码"
- "公用电话"
- "电话会议"
- "通话中断"
- "扬声器"
- "手机听筒"
- "有线耳机"
- "蓝牙"
- "发送以下信号音?\n"
- "正在发送信号音\n"
- "发送"
- "是"
- "否"
- "将通配符替换为"
- "电话会议(%s)"
- "语音信箱号码"
- "正在拨号"
- "正在重拨"
- "电话会议"
- "来电"
- "工作来电"
- "通话已结束"
- "保持"
- "正在挂断"
- "正在通话"
- "我的电话号码:%s"
- "正在接通视频"
- "视频通话"
- "正在发出视频请求"
- "无法接通视频通话"
- "视频请求遭拒"
- "您的回拨号码如下:\n%1$s"
- "您的紧急回拨号码如下:\n%1$s"
- "正在拨号"
- "未接电话"
- "未接电话"
- "%s 个未接电话"
- "来自%s的未接电话"
- "通话进行中"
- "工作通话进行中"
- "WLAN 通话进行中"
- "WLAN 工作通话进行中"
- "保持"
- "来电"
- "工作来电"
- "WLAN 来电"
- "WLAN 工作来电"
- "视频通话来电"
- "有疑似骚扰来电"
- "收到视频通话请求"
- "新语音邮件"
- "新语音邮件 (%d)"
- "拨打 %s"
- "语音信箱号码未知"
- "没有服务"
- "所选网络(%s)不可用"
- "接听"
- "挂断"
- "视频"
- "语音"
- "接受"
- "拒绝"
- "回电"
- "发短信"
- "其他设备上有正在进行的通话"
- "转接通话"
- "要拨打电话,请先关闭飞行模式。"
- "尚未注册网络。"
- "无法连接到移动网络。"
- "要拨打电话,请输入有效的电话号码。"
- "无法拨打该电话。"
- "正在启动 MMI 序列…"
- "服务不受支持。"
- "无法切换通话。"
- "无法单独通话。"
- "无法转移呼叫。"
- "无法进行电话会议。"
- "无法拒接来电。"
- "无法挂断。"
- "SIP 通话"
- "紧急呼救"
- "正在开启无线装置…"
- "找不到服务信号,正在重试…"
- "无法拨打该电话。%s 不是紧急呼救号码。"
- "无法拨打该电话。请拨打紧急呼救号码。"
- "使用键盘拨号"
- "保持通话"
- "恢复通话"
- "结束通话"
- "显示拨号键盘"
- "隐藏拨号键盘"
- "静音"
- "取消静音"
- "添加通话"
- "合并通话"
- "切换"
- "管理通话"
- "管理电话会议"
- "电话会议"
- "管理"
- "音频"
- "视频通话"
- "改为语音通话"
- "切换摄像头"
- "开启摄像头"
- "关闭摄像头"
- "更多选项"
- "播放器已启动"
- "播放器已停止"
- "摄像头尚未准备就绪"
- "摄像头已准备就绪"
- "未知通话事件"
- "服务"
- "设置"
- "<未设置>"
- "其他通话设置"
- "正在通过%s进行通话"
- "有人通过%s来电"
- "联系人照片"
- "单独通话"
- "选择联系人"
- "自行撰写回复…"
- "取消"
- "发送"
- "接听"
- "发送短信"
- "拒绝"
- "以视频通话的形式接听"
- "以音频通话的形式接听"
- "接受视频请求"
- "拒绝视频请求"
- "接受视频传输请求"
- "拒绝视频传输请求"
- "接受视频接收请求"
- "拒绝视频接收请求"
- "向上滑动即可%s。"
- "向左滑动即可%s。"
- "向右滑动即可%s。"
- "向下滑动即可%s。"
- "振动"
- "振动"
- "提示音"
- "默认提示音(%1$s)"
- "手机铃声"
- "响铃时振动"
- "铃声和振动"
- "管理电话会议"
- "紧急呼救号码"
- "个人资料照片"
- "摄像头已关闭"
- "通过 %s"
- "已发送备注"
- "最近的信息"
- "商家信息"
- "%.1f 英里远"
- "%.1f 公里远"
- "%2$s%1$s"
- "%1$s - %2$s"
- "%1$s,%2$s"
- "将于明天%s开始营业"
- "将于今天%s开始营业"
- "将于%s结束营业"
- "已于今天%s结束营业"
- "营业中"
- "现已结束营业"
- "疑似骚扰电话号码"
- "通话已结束 %1$s"
- "这是此号码的第一次来电。"
- "我们怀疑这是骚扰电话。"
- "屏蔽/举报骚扰电话号码"
- "添加联系人"
- "非骚扰电话号码"
-
diff --git a/InCallUI/res/values-zh-rHK/strings.xml b/InCallUI/res/values-zh-rHK/strings.xml
deleted file mode 100644
index bf6f016cba9872e427589aba854a93c9b063fe14..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-zh-rHK/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "電話"
- "保留通話"
- "不明"
- "私人號碼"
- "公共電話"
- "會議通話"
- "通話已中斷"
- "喇叭"
- "免提聽筒"
- "有線耳機"
- "藍牙"
- "要傳送以下訊號音嗎?\n"
- "正在傳送訊號音\n"
- "傳送"
- "是"
- "否"
- "將萬用字元改為"
- "會議通話:%s"
- "留言號碼"
- "正在撥號"
- "正在重撥"
- "會議通話"
- "來電"
- "工作來電"
- "通話已結束"
- "保留通話"
- "正在掛斷電話"
- "正在通話"
- "我的電話號碼:%s"
- "正在建立視像通話連線"
- "視像通話"
- "正在提出視像通話要求"
- "無法建立視像通話連線"
- "視像通話要求被拒"
- "您的回撥號碼:\n%1$s"
- "您的緊急回撥號碼:\n%1$s"
- "正在撥號"
- "未接來電"
- "未接來電"
- "%s 個未接來電"
- "來自 %s 的未接來電"
- "通話中"
- "正在進行工作通話"
- "正在進行 Wi-Fi 通話"
- "正在進行 Wi-Fi 工作通話"
- "保留通話"
- "來電"
- "工作來電"
- "Wi-Fi 來電"
- "Wi-Fi 工作來電"
- "視像通話來電"
- "疑似收到垃圾來電"
- "收到視像通話要求"
- "新留言"
- "新留言 (%d 個)"
- "撥打 %s"
- "留言號碼不明"
- "沒有服務"
- "您選取的網絡 (%s) 無法使用"
- "接聽"
- "掛斷電話"
- "視像通話"
- "語音通話"
- "接受"
- "拒絕"
- "回電"
- "短訊"
- "其他裝置上有正在進行的通話"
- "轉接來電"
- "如要撥打電話,請先關閉飛行模式。"
- "未在網絡上註冊。"
- "無法連線至流動網絡。"
- "如要撥打電話,請輸入有效的號碼。"
- "無法通話。"
- "開始 MMI 序列…"
- "不支援此服務。"
- "無法切換通話。"
- "無法分開通話。"
- "無法轉接。"
- "無法進行會議通話。"
- "無法拒接來電。"
- "無法結束通話。"
- "SIP 通話"
- "緊急電話"
- "正在開啟無線電…"
- "找不到服務,請再試一次…"
- "無法通話。%s 不是緊急電話號碼。"
- "無法通話。請撥打緊急電話號碼。"
- "使用鍵盤撥號"
- "保留通話"
- "恢復通話"
- "結束通話"
- "顯示撥號鍵盤"
- "隱藏撥號鍵盤"
- "略過"
- "取消靜音"
- "新增通話"
- "合併通話"
- "切換"
- "管理通話"
- "管理會議通話"
- "會議通話"
- "管理"
- "音訊"
- "視像通話"
- "變更為語音通話"
- "切換鏡頭"
- "開啟攝影機"
- "關閉攝影機"
- "更多選項"
- "已啟動播放器"
- "已停止播放器"
- "相機未準備好"
- "相機已準備就緒"
- "不明的通話工作階段活動"
- "服務"
- "設定"
- "<未設定>"
- "其他通話設定"
- "正在透過 %s 撥號"
- "有人透過 %s 來電"
- "聯絡人相片"
- "私人通話"
- "選取聯絡人"
- "自行撰寫回覆..."
- "取消"
- "傳送"
- "接聽"
- "傳送短訊"
- "拒絕"
- "接聽視像通話"
- "接聽語音通話"
- "接受視像通話要求"
- "拒絕視像通話要求"
- "接受視像通話轉駁要求"
- "拒絕視像通話轉駁要求"
- "接受視像接收要求"
- "拒絕視像接收要求"
- "向上滑動即可%s。"
- "向左滑動即可%s。"
- "向右滑動即可%s。"
- "向下滑動即可%s。"
- "震動"
- "震動"
- "音效"
- "預設音效 (%1$s)"
- "手機鈴聲"
- "響鈴時震動"
- "鈴聲和震動"
- "管理會議通話"
- "緊急電話號碼"
- "個人檔案相片"
- "相機已關閉"
- "透過 %s"
- "已傳送筆記"
- "最近的訊息"
- "公司資料"
- "%.1f 英里外"
- "%.1f 公里外"
- "%2$s%1$s"
- "%1$s - %2$s"
- "%1$s,%2$s"
- "將於明天%s開始營業"
- "將於今天%s開始營業"
- "將於%s關門"
- "已於今天%s關門"
- "營業中"
- "目前休息"
- "疑似垃圾來電者"
- "通話結束 %1$s"
- "這是此號碼的第一次來電。"
- "我們懷疑此來電為垃圾來電。"
- "封鎖/舉報為垃圾來電"
- "新增聯絡人"
- "非垃圾來電"
-
diff --git a/InCallUI/res/values-zh-rTW/strings.xml b/InCallUI/res/values-zh-rTW/strings.xml
deleted file mode 100644
index e316c7d40c8ab81e92a7c17aa02a22536578c238..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-zh-rTW/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "電話"
- "保留"
- "不明"
- "私人號碼"
- "公用電話"
- "電話會議"
- "通話已中斷"
- "喇叭"
- "手機聽筒"
- "有線耳機"
- "藍牙"
- "要傳送以下的信號音嗎?\n"
- "正在傳送信號音\n"
- "傳送"
- "是"
- "否"
- "將萬用字元替換為"
- "電話會議 %s"
- "語音留言號碼"
- "撥號中"
- "重撥中"
- "電話會議"
- "來電"
- "公司來電"
- "通話已結束"
- "保留"
- "掛斷中"
- "通話中"
- "我的電話號碼:%s"
- "正在建立視訊通話連線"
- "視訊通話"
- "正在提出視訊通話要求"
- "無法建立視訊通話連線"
- "視訊通話要求遭拒"
- "您的回撥號碼如下\n %1$s"
- "您的緊急回撥號碼如下\n %1$s"
- "撥號中"
- "未接來電"
- "未接來電"
- "%s 通未接來電"
- "來自 %s 的未接來電"
- "進行中的通話"
- "進行中的公司通話"
- "進行中的通話 (透過 Wi-Fi)"
- "進行中的公司通話 (透過 Wi-Fi)"
- "保留"
- "來電"
- "公司來電"
- "來電 (透過 Wi-Fi)"
- "公司來電 (透過 Wi-Fi)"
- "視訊通話來電"
- "可疑的騷擾/廣告來電"
- "收到視訊通話要求"
- "新的語音留言"
- "新的語音留言 (%d)"
- "撥打 %s"
- "語音留言號碼不明"
- "沒有服務"
- "您所選取的網路 (%s) 無法使用"
- "接聽"
- "掛斷"
- "視訊通話"
- "語音通話"
- "接受"
- "拒絕"
- "回撥"
- "傳送簡訊"
- "其他裝置上有進行中的通話"
- "轉接來電"
- "撥號前,請先關閉飛航模式。"
- "尚未註冊網路。"
- "無法連線到行動網路。"
- "如要撥打電話,請輸入有效的號碼。"
- "無法通話。"
- "開始 MMI 序列…"
- "不支援的服務。"
- "無法切換通話。"
- "無法分割通話。"
- "無法轉接。"
- "無法進行電話會議。"
- "無法拒接來電。"
- "無法掛斷電話。"
- "SIP 通話"
- "緊急電話"
- "正在開啟無線通訊…"
- "找不到服務訊號,重試中…"
- "無法通話。%s 不是緊急電話號碼。"
- "無法通話。只能撥打緊急號碼。"
- "使用鍵盤撥號"
- "保留通話"
- "恢復通話"
- "結束通話"
- "顯示撥號鍵盤"
- "隱藏撥號鍵盤"
- "忽略"
- "取消忽略"
- "新增通話"
- "合併通話"
- "切換"
- "管理通話"
- "管理電話會議"
- "電話會議"
- "管理"
- "音訊"
- "視訊通話"
- "變更為語音通話"
- "切換鏡頭"
- "開啟攝影機"
- "關閉攝影機"
- "更多選項"
- "已啟動播放器"
- "已停止播放器"
- "相機尚未就緒"
- "相機已準備就緒"
- "不明的通話工作階段事件"
- "服務"
- "設定"
- "<未設定>"
- "其他通話設定"
- "正在透過 %s 撥號"
- "有人透過 %s 來電"
- "聯絡人相片"
- "私人通話"
- "選取聯絡人"
- "自行撰寫回應…"
- "取消"
- "傳送"
- "接聽"
- "傳送簡訊"
- "拒絕"
- "接聽視訊通話"
- "接聽語音通話"
- "接受視訊通話要求"
- "拒絕視訊通話要求"
- "接受視訊傳送要求"
- "拒絕視訊傳送要求"
- "接受視訊接收要求"
- "拒絕視訊接收要求"
- "向上滑動即可%s。"
- "向左滑動即可%s。"
- "向右滑動即可%s。"
- "向下滑動即可%s。"
- "震動"
- "震動"
- "音效"
- "預設音效 (%1$s)"
- "手機鈴聲"
- "鈴響時震動"
- "鈴聲與震動"
- "管理電話會議"
- "緊急電話號碼"
- "個人資料相片"
- "相機已停用"
- "透過 %s"
- "備註已送出"
- "最近的訊息"
- "商家資訊"
- "%.1f 英里遠"
- "%.1f 公里遠"
- "%2$s,%1$s"
- "%1$s - %2$s"
- "%1$s,%2$s"
- "將於明日%s開始營業"
- "將於本日%s開始營業"
- "將於%s結束營業"
- "已於本日%s結束營業"
- "營業中"
- "本日已結束營業"
- "可疑的騷擾/廣告來電者"
- "通話結束 %1$s"
- "這組號碼首次致電給您。"
- "我們懷疑這通來電是騷擾/廣告電話。"
- "封鎖/回報為騷擾/廣告電話"
- "新增聯絡人"
- "非騷擾/廣告電話"
-
diff --git a/InCallUI/res/values-zu/strings.xml b/InCallUI/res/values-zu/strings.xml
deleted file mode 100644
index 46bf5afbb38b6b382f89bc7dc54bdeb9a8412d49..0000000000000000000000000000000000000000
--- a/InCallUI/res/values-zu/strings.xml
+++ /dev/null
@@ -1,195 +0,0 @@
-
-
-
-
- "Ifoni"
- "Ibanjiwe"
- "Akwaziwa"
- "Inombolo eyimfihlo"
- "Ucingo olufakwa imali"
- "Ikholi yenkomfa"
- "Ikholi ivaliwe"
- "Isipikha"
- "Isipikha sendlebe sama-ear phone"
- "Ama-earphone anezintambo"
- "I-Bluetooth"
- "Thumela amathoni alandelayo?\n"
- "Ithumela amathoni\n"
- "Thumela"
- "Yebo"
- "Cha"
- "Miselela uhlamvu lwasendle nge"
- "Ikholi yenkomfa engu-%s"
- "Inombolo yevoyisimeyili"
- "Iyadayela"
- "Iphinda iyadayela"
- "Ikholi yenkomfa"
- "Ikholi engenayo"
- "Ikholi engenayo yomsebenzi"
- "Ikholi iqediwe"
- "Ibanjiwe"
- "Iyavala"
- "Ukukholi"
- "Inombolo yami ngu-%s"
- "Ixhuma ividiyo"
- "Ikholi yevidiyo"
- "Icela ividiyo"
- "Ayikwazi ukuxhuma ikholi yevidiyo"
- "Isicelo sevidiyo sinqatshelwe"
- "Inombolo yakho yokuphinda ushaye\n%1$s"
- "Inombolo yakho yokuphinda ushayelwe yesimo esiphuthumayo\n%1$s"
- "Iyadayela"
- "Ikholi ephuthelwe"
- "Amakholi akuphuthele"
- "%s amakholi akulahlekele"
- "Uphuthelwe ikholi kusukela ku-%s"
- "Ikholi eqhubekayo"
- "Ikholi yomsebenzi eqhubekayo"
- "Ikholi ye-Wi-Fi eqhubekayo"
- "Ikholi yomsebenzi eqhubekayo ye-Wi-Fi"
- "Ibanjiwe"
- "Ikholi engenayo"
- "Ikholi engenayo yomsebenzi"
- "Ikholi ye-Wi-Fi engenayo"
- "Ikholi engenayo yomsebenzi ye-Wi-Fi"
- "Ikholi yevidiyo engenayo"
- "Ikholi engenayo osolisayo kagaxekile"
- "Isicelo sevidiyo engenayo"
- "Ivoyisimeyili entsha"
- "Ivoyisimeyili entsha (%d)"
- "Dayela u-%s"
- "Inombolo yevoyisimeyili ayaziwa"
- "Ayikho isevisi"
- "Inethiwekhi ekhethiwe (%s) ayitholakali"
- "Phendula"
- "Vala ikholi"
- "Ividiyo"
- "Izwi"
- "Yamukela"
- "Cashisa"
- "Phinda ushayele"
- "Umlayezo"
- "Ikholi eqhubekayo kwenye idivayisi"
- "Dlulisela ikholi"
- "Ukwenza ikholi, vala kuqala imodi Yendiza."
- "Ayibhalisiwe kwinethiwekhi."
- "Inethiwekhi yeselula ayitholakali."
- "Ukuze wenze ikholi, faka inombolo evumelekile."
- "Ayikwazi ukushaya."
- "Iqalisa ukulandelana kwe-MMI..."
- "Isevisi ayisekelwe."
- "Ayikwazi ukushintsha amakholi."
- "Ayikwazi ukuhlukanisa ikholi."
- "Ayikwazi ukudlulisela."
- "Ayikwazi ukwenza inkomfa."
- "Ayikwazi ukunqabela ikholi."
- "Ayikwazi ukukhipha amakholi."
- "Ikholi ye-SIP"
- "Ikholi ephuthumayo"
- "Ivula irediyo..."
- "Ayikho isevisi. Iyazama futhi…"
- "Ayikwazi ukushaya. U-%s akuyona inombolo yesimo esiphuthumayo."
- "Ayikwazi ukushaya. Shayela inombolo yesimo esiphuthumayo."
- "Sebenzisa ikhibhodi ukudayela"
- "Bamba ikholi"
- "Qalisa kabusha ikholi"
- "Qeda ikholi"
- "Bonisa iphedi yokudayela"
- "Fihla iphedi yokudayela"
- "Thulisa"
- "Susa ukuthula"
- "Engeza ikholi"
- "Hlanganisa amakholi"
- "Shintsha"
- "Phatha amakholi"
- "Phatha ucingo lwengqungquthela"
- "Ikholi yenkomfa"
- "Phatha"
- "Umsindo"
- "Ikholi yevidiyo"
- "Shintshela kukholi yezwi"
- "Shintsha Ikhamera"
- "Vula ikhamera"
- "Vala ikhamera"
- "Izinketho eziningi"
- "Umdlali uqalile"
- "Umdlali umisiwe"
- "Ikhamera ayilungile"
- "Ikhamera ilungile"
- "Umcimbi wesikhathi sekholi ongaziwa"
- "Isevisi"
- "Ukusetha"
- "<Ayisethiwe>"
- "Ezinye izilungiselelo zekholi"
- "Ishaya nge-%s"
- "Ingena nge-%s"
- "isithombe soxhumana naye"
- "yenza kube imfihlo"
- "khetha othintana naye"
- "Bhala okwakho…"
- "Khansela"
- "Thumela"
- "Phendula"
- "Thumela i-SMS"
- "Yenqaba"
- "Phendula njengekholi yevidiyo"
- "Phendula njengekholi yomsindo"
- "Yamukela isicelo sevidiyo"
- "Yenqaba isicelo sevidiyo"
- "Yamukela isicelo sokudlulisa ividiyo"
- "Yenqaba isicelo sokudlulisa ividiyo"
- "Yamukela isicelo sokwamukela ividiyo"
- "Yenqaba isicelo sokwamukela ividiyo"
- "Slayidela phezulu ku-%s."
- "Slayida ngakwesokunxele ku-%s."
- "Slayida ngakwesokudla ku-%s."
- "Slayida ngezansi ku-%s."
- "Dlidlizela"
- "Dlidlizela"
- "Umsindo"
- "Umsindo ozenzakalelayo (%1$s)"
- "Ithoni yokukhala yefoni"
- "Dlidlizisa uma ikhala"
- "Ithoni yokukhala nokudlidliza"
- "Phatha ucingo lwengqungquthela"
- "Inombolo ephuthumayo"
- "Isithombe sephrofayela"
- "Ikhamera ivaliwe"
- "nge-%s"
- "Inothi lithunyelwe"
- "Imilayezo yakamuva"
- "Ulwazi lwebhizinisi"
- "%.1f amamitha kude"
- "%.1f amakhilomitha kude"
- "%1$s, %2$s"
- "%1$s - %2$s"
- "%1$s, %2$s"
- "Kuvulwa kusasa ngo-%s"
- "Kuvulwa namuhla ngo-%s"
- "Kuvalwa ngo-%s"
- "Kuvalwe namuhla ngo-%s"
- "Kuvuliwe manje"
- "Kuvaliwe manje"
- "Ofonayo osolisayo wogaxekile"
- "Ikholi iphelile %1$s"
- "Lesi isikhathi sokuqala le nombolo ikushayela."
- "Sisolele le kholi ukuthi ugaxekile."
- "Vimba/bika ugaxekile"
- "Engeza oxhumana naye"
- "Akusiko okugaxekile"
-
diff --git a/InCallUI/res/values/animation_constants.xml b/InCallUI/res/values/animation_constants.xml
deleted file mode 100644
index 8df6a7281bc385f340a48dc12eb2cd51b890170c..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/animation_constants.xml
+++ /dev/null
@@ -1,22 +0,0 @@
-
-
-
-
- 333
- 333
- 257
-
diff --git a/InCallUI/res/values/array.xml b/InCallUI/res/values/array.xml
deleted file mode 100644
index 7877ec8f3517fa03f6a0136e60249b9e6f4f15cd..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/array.xml
+++ /dev/null
@@ -1,135 +0,0 @@
-
-
-
-
-
-
-
-
-
- @drawable/ic_lockscreen_answer
- @null
- @drawable/ic_lockscreen_decline
- @null"
-
-
- @string/description_target_answer
- @null
- @string/description_target_decline
- @null"
-
-
- @string/description_direction_right
- @null
- @string/description_direction_left
- @null
-
-
-
-
- @drawable/ic_lockscreen_answer
- @drawable/ic_lockscreen_text
- @drawable/ic_lockscreen_decline
- @null"
-
-
- @string/description_target_answer
- @string/description_target_send_sms
- @string/description_target_decline
- @null"
-
-
- @string/description_direction_right
- @string/description_direction_up
- @string/description_direction_left
- @null
-
-
-
-
- @drawable/ic_lockscreen_answer
- @null
- @drawable/ic_lockscreen_decline
- @drawable/ic_lockscreen_answer_video
-
-
- @string/description_target_answer_video_call
- @null
- @string/description_target_decline
- @string/description_target_answer_audio_call
-
-
- @string/description_direction_right
- @null
- @string/description_direction_left
- @string/description_direction_down
-
-
-
-
- @drawable/ic_lockscreen_answer_video
- @drawable/ic_lockscreen_text
- @drawable/ic_lockscreen_decline
- @drawable/ic_lockscreen_answer
-
-
- @string/description_target_answer_video_call
- @string/description_target_send_sms
- @string/description_target_decline
- @string/description_target_answer_audio_call
-
-
- @string/description_direction_right
- @string/description_direction_up
- @string/description_direction_left
- @string/description_direction_down
-
-
-
-
- @drawable/ic_lockscreen_answer_video
- @drawable/ic_lockscreen_decline_video
-
-
-
- @string/description_target_accept_upgrade_to_video_request
- @null
- @string/description_target_decline_upgrade_to_video_request
- @null"
-
-
- @string/description_direction_right
- @null
- @string/description_direction_left
- @null
-
-
diff --git a/InCallUI/res/values/attrs.xml b/InCallUI/res/values/attrs.xml
deleted file mode 100644
index e135fb72d02655b0bd1f5b0a77336f1a232f6395..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/attrs.xml
+++ /dev/null
@@ -1,71 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/InCallUI/res/values/colors.xml b/InCallUI/res/values/colors.xml
deleted file mode 100644
index 238d360335c2d84f259c3dd99451e0808e37a79d..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/colors.xml
+++ /dev/null
@@ -1,133 +0,0 @@
-
-
-
-
-
-
- @color/dialer_theme_color
- #ffffff
-
-
- @color/incall_background_color
- #ffffff
-
- #ffffff
- #f5f5f5
- #333333
-
- @color/incall_background_color
- @color/incall_call_banner_text_color
-
- #545454
-
-
- #cc000000
-
- #f8f8f8
- #4d4d4d
- #999999
-
- #999999
- #ffffff
-
- #dddddd
-
-
- #333
-
- #ffffff
- #ccaaaaaa
-
- @color/incall_background_color
- @color/dialer_theme_color_dark
-
- #b3ffffff
-
- #33ffffff
-
-
- @color/dialer_theme_color
-
- @color/dialer_theme_color
-
- #33999999
-
-
- #b3000000
-
- #26ffffff
- #ffffff
- #ffffff
- #cccccc
- #00c853
- #ff1744
- #a3a3a3
- #ffffff
-
-
- #B2FFFFFF
-
-
- #330288d1
-
-
-
- #00796B
- #3367D6
- #303F9F
- #7B1FA2
- #C2185B
- #C53929
- #A52714
-
-
-
-
- #00695C
- #2A56C6
- #283593
- #6A1B9A
- #AD1457
- #B93221
- #841F10
-
-
-
- #A52714
-
-
- #40000000
-
- @color/incall_call_banner_subtext_color
- @color/dialer_theme_color
- @color/incall_call_banner_subtext_color
- @color/incall_call_banner_subtext_color
- @color/incall_call_banner_subtext_color
-
-
- #ffffff
-
-
- #919191
-
diff --git a/InCallUI/res/values/config.xml b/InCallUI/res/values/config.xml
deleted file mode 100644
index b81ba3ca03c0383947733579fc257d2890536e79..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/config.xml
+++ /dev/null
@@ -1,27 +0,0 @@
-
-
-
- 5
-
-
- true
-
- 5000
-
\ No newline at end of file
diff --git a/InCallUI/res/values/dimens.xml b/InCallUI/res/values/dimens.xml
deleted file mode 100644
index 59da7860a00803a7ffe2a5b6323766122c3406cd..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/dimens.xml
+++ /dev/null
@@ -1,150 +0,0 @@
-
-
-
-
-
- false
-
-
- false
-
-
-
- 0dp
- 20dp
-
- 3dp
-
-
- 2dp
-
-
- 24dp
-
- 16dp
- 24dp
- 32dp
- 16sp
-
-
- 8dp
-
-
- 16sp
- 12sp
- 34dp
- 28sp
- 16sp
-
- 50sp
-
-
- 48dp
-
- 0dp
- 2dp
-
-
- 1dp
-
- 0dp
- 20sp
- 50dp
- 36dp
-
- -10dp
-
- 8dp
- 6dp
-
-
- 10dp
- 5dp
- 10dp
-
-
- 64dp
-
-
- 56dp
-
-
- 250dp
-
- 125dp
-
-
- 70dip
-
-
- 40dip
-
-
- 15dip
-
- -48dip
- 0dip
-
- 2dp
-
- 2dp
-
- 50dp
-
-
- 90dp
-
- 0dp
-
- 72dp
- 56dp
-
- 64dp
- 46dp
-
- 14sp
- 19dp
- 23dp
- 13dp
- 13dp
-
- 30dp
- 16sp
- 7dp
- 12dp
- 15dp
- 2dp
- 7dp
- 14sp
-
- 10dp
- 25dp
- 20dp
- 16sp
- 12sp
-
- 40dp
-
diff --git a/InCallUI/res/values/ids.xml b/InCallUI/res/values/ids.xml
deleted file mode 100644
index accb8fb73c1c431603f42218dadbd8c05cbe50cf..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/ids.xml
+++ /dev/null
@@ -1,20 +0,0 @@
-
-
-
-
-
-
-
diff --git a/InCallUI/res/values/strings.xml b/InCallUI/res/values/strings.xml
deleted file mode 100644
index 92de14042aaf998751e1568928078f4df50c29f3..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/strings.xml
+++ /dev/null
@@ -1,540 +0,0 @@
-
-
-
-
-
-
- Phone
-
-
- InCallUI
-
-
-
-
- On hold
-
-
- Unknown
-
- Private number
-
- Payphone
-
-
- Conference call
-
- Call dropped
-
-
-
-
-
- Speaker
-
- Handset earpiece
-
- Wired headset
-
- Bluetooth
-
-
-
- Send the following tones?\n
-
- Sending tones\n
-
- Send
-
- Yes
-
- No
-
- Replace wild character with
-
-
- Conference call %s
-
-
- (650) 555-1234
-
- Incoming phone number
-
- Fake Incoming Call
-
-
- Voicemail number
-
-
-
- Dialing
-
- Redialing
-
- Conference call
-
- Incoming call
-
- Incoming work call
-
- Call ended
-
- On hold
-
- Hanging up
-
- In call
-
- My number is %s
-
- Connecting video
-
- Video call
-
- Requesting video
-
- Can\'t connect video call
-
- Video request rejected
-
-
- Your callback number\n
- %1$s
-
-
-
- Your emergency callback number\n
- %1$s
-
-
-
-
- Dialing
-
- Missed call
-
- Missed calls
-
- %s missed calls
-
- Missed call from %s
-
- Ongoing call
-
- Ongoing work call
-
- Ongoing Wi-Fi call
-
- Ongoing Wi-Fi work call
-
- On hold
-
- Incoming call
-
- Incoming work call
-
- Incoming Wi-Fi call
-
- Incoming Wi-Fi work call
-
- Incoming video call
-
- Incoming suspected spam call
-
- Incoming video request
-
- New voicemail
-
- New voicemail (%d)
-
- Dial %s
-
- Voicemail number unknown
-
- No service
-
- Selected network (%s) unavailable
-
- Answer
-
- Hang up
-
- Video
-
- Voice
-
- Accept
-
- Dismiss
-
-
- Call back
-
- Message
-
- Ongoing call on another device
-
- Transfer Call
-
-
- To place a call, first turn off Airplane mode.
-
- Not registered on network.
-
- Cellular network not available.
-
- To place a call, enter a valid number.
-
- Can\'t call.
-
- Starting MMI sequence\u2026
-
- Service not supported.
-
- Can\'t switch calls.
-
- Can\'t separate call.
-
- Can\'t transfer.
-
- Can\'t conference.
-
- Can\'t reject call.
-
- Can\'t release call(s).
-
-
- SIP call
-
-
- Emergency call
-
- Turning on radio\u2026
-
- No service. Trying again\u2026
-
-
-
- Can\'t call. %s is not an emergency number.
-
- Can\'t call. Dial an emergency number.
-
-
- Use keyboard to dial
-
-
- Hold Call
-
- Resume Call
-
- End Call
-
- Show Dialpad
-
- Hide Dialpad
-
- Mute
-
- Unmute
-
- Add call
-
- Merge calls
-
- Swap
-
- Manage calls
-
- Manage conference call
-
- Conference call
-
- Manage
-
- Audio
-
- Video call
-
- Change to voice call
-
- Switch camera
-
- Turn on camera
-
- Turn off camera
-
- More options
-
-
- Player Started
-
- Player Stopped
-
- Camera not ready
-
- Camera ready
-
- "Unkown call session event"
-
-
-
- ABSENT NUMBER
- ABSENTNUMBER
-
-
-
- Service
-
-
- Setup
-
-
- <Not set>
-
-
- Other call settings
-
-
- Calling via %s
-
- Incoming via %s
-
-
- contact photo
-
- go private
-
- select contact
-
-
- Write your own...
-
- Cancel
-
- Send
-
-
- Answer
-
- Send SMS
-
- Decline
-
- Answer as video call
-
- Answer as audio call
-
- Accept video request
-
- Decline video request
-
- Accept video transmit request
-
- Decline video transmit request
-
- Accept video receive request
-
- Decline video receive request
-
-
- Slide up for %s.
-
- "Slide left for %s.
-
- Slide right for %s.
-
- Slide down for %s.
-
-
- Vibrate
-
- Vibrate
-
-
- Sound
-
-
- Default sound (%1$s)
-
-
- never
-
-
-
- always
- silent
- never
-
-
-
- Phone ringtone
-
-
- Vibrate when ringing
-
-
- Ringtone & Vibrate
-
-
- Manage conference call
-
-
- Emergency number
-
-
- Profile photo
-
-
- Camera off
-
-
- via %s
-
-
- Note sent
-
-
- Recent messages
-
-
- Business info
-
-
-
-
- %.1f mi away
-
- %.1f km away
-
- %1$s, %2$s
-
- %1$s - %2$s
-
- %1$s, %2$s
-
- Opens tomorrow at %s
-
- Opens today at %s
-
- Closes at %s
-
- Closed today at %s
-
- Open now
-
- Closed now
-
- Suspected spam caller
-
-
- Call ended %1$s
-
- This is the first time this number called you.
-
- We suspected this call to be a spammer.
-
- Block/report spam
-
- Add contact
-
- Not spam
-
diff --git a/InCallUI/res/values/styles.xml b/InCallUI/res/values/styles.xml
deleted file mode 100644
index 11d636261dfe309695603d0c0b2dab3063c0e1ae..0000000000000000000000000000000000000000
--- a/InCallUI/res/values/styles.xml
+++ /dev/null
@@ -1,100 +0,0 @@
-
-
-
-
- #FF333333
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/InCallUI/src/com/android/incallui/AccelerometerListener.java b/InCallUI/src/com/android/incallui/AccelerometerListener.java
deleted file mode 100644
index b5ad29675f4c41afe0d5b487d8f027fe9f9c43d0..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/AccelerometerListener.java
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.hardware.Sensor;
-import android.hardware.SensorEvent;
-import android.hardware.SensorEventListener;
-import android.hardware.SensorManager;
-import android.os.Handler;
-import android.os.Message;
-import android.util.Log;
-
-/**
- * This class is used to listen to the accelerometer to monitor the
- * orientation of the phone. The client of this class is notified when
- * the orientation changes between horizontal and vertical.
- */
-public class AccelerometerListener {
- private static final String TAG = "AccelerometerListener";
- private static final boolean DEBUG = true;
- private static final boolean VDEBUG = false;
-
- private SensorManager mSensorManager;
- private Sensor mSensor;
-
- // mOrientation is the orientation value most recently reported to the client.
- private int mOrientation;
-
- // mPendingOrientation is the latest orientation computed based on the sensor value.
- // This is sent to the client after a rebounce delay, at which point it is copied to
- // mOrientation.
- private int mPendingOrientation;
-
- private OrientationListener mListener;
-
- // Device orientation
- public static final int ORIENTATION_UNKNOWN = 0;
- public static final int ORIENTATION_VERTICAL = 1;
- public static final int ORIENTATION_HORIZONTAL = 2;
-
- private static final int ORIENTATION_CHANGED = 1234;
-
- private static final int VERTICAL_DEBOUNCE = 100;
- private static final int HORIZONTAL_DEBOUNCE = 500;
- private static final double VERTICAL_ANGLE = 50.0;
-
- public interface OrientationListener {
- public void orientationChanged(int orientation);
- }
-
- public AccelerometerListener(Context context) {
- mSensorManager = (SensorManager)context.getSystemService(Context.SENSOR_SERVICE);
- mSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
- }
-
- public void setListener(OrientationListener listener) {
- mListener = listener;
- }
-
- public void enable(boolean enable) {
- if (DEBUG) Log.d(TAG, "enable(" + enable + ")");
- synchronized (this) {
- if (enable) {
- mOrientation = ORIENTATION_UNKNOWN;
- mPendingOrientation = ORIENTATION_UNKNOWN;
- mSensorManager.registerListener(mSensorListener, mSensor,
- SensorManager.SENSOR_DELAY_NORMAL);
- } else {
- mSensorManager.unregisterListener(mSensorListener);
- mHandler.removeMessages(ORIENTATION_CHANGED);
- }
- }
- }
-
- private void setOrientation(int orientation) {
- synchronized (this) {
- if (mPendingOrientation == orientation) {
- // Pending orientation has not changed, so do nothing.
- return;
- }
-
- // Cancel any pending messages.
- // We will either start a new timer or cancel alltogether
- // if the orientation has not changed.
- mHandler.removeMessages(ORIENTATION_CHANGED);
-
- if (mOrientation != orientation) {
- // Set timer to send an event if the orientation has changed since its
- // previously reported value.
- mPendingOrientation = orientation;
- final Message m = mHandler.obtainMessage(ORIENTATION_CHANGED);
- // set delay to our debounce timeout
- int delay = (orientation == ORIENTATION_VERTICAL ? VERTICAL_DEBOUNCE
- : HORIZONTAL_DEBOUNCE);
- mHandler.sendMessageDelayed(m, delay);
- } else {
- // no message is pending
- mPendingOrientation = ORIENTATION_UNKNOWN;
- }
- }
- }
-
- private void onSensorEvent(double x, double y, double z) {
- if (VDEBUG) Log.d(TAG, "onSensorEvent(" + x + ", " + y + ", " + z + ")");
-
- // If some values are exactly zero, then likely the sensor is not powered up yet.
- // ignore these events to avoid false horizontal positives.
- if (x == 0.0 || y == 0.0 || z == 0.0) return;
-
- // magnitude of the acceleration vector projected onto XY plane
- final double xy = Math.hypot(x, y);
- // compute the vertical angle
- double angle = Math.atan2(xy, z);
- // convert to degrees
- angle = angle * 180.0 / Math.PI;
- final int orientation = (angle > VERTICAL_ANGLE ? ORIENTATION_VERTICAL : ORIENTATION_HORIZONTAL);
- if (VDEBUG) Log.d(TAG, "angle: " + angle + " orientation: " + orientation);
- setOrientation(orientation);
- }
-
- SensorEventListener mSensorListener = new SensorEventListener() {
- @Override
- public void onSensorChanged(SensorEvent event) {
- onSensorEvent(event.values[0], event.values[1], event.values[2]);
- }
-
- @Override
- public void onAccuracyChanged(Sensor sensor, int accuracy) {
- // ignore
- }
- };
-
- Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case ORIENTATION_CHANGED:
- synchronized (this) {
- mOrientation = mPendingOrientation;
- if (DEBUG) {
- Log.d(TAG, "orientation: " +
- (mOrientation == ORIENTATION_HORIZONTAL ? "horizontal"
- : (mOrientation == ORIENTATION_VERTICAL ? "vertical"
- : "unknown")));
- }
- if (mListener != null) {
- mListener.orientationChanged(mOrientation);
- }
- }
- break;
- }
- }
- };
-}
diff --git a/InCallUI/src/com/android/incallui/AccessibleAnswerFragment.java b/InCallUI/src/com/android/incallui/AccessibleAnswerFragment.java
deleted file mode 100644
index 89c78ec6115493de113d77a17f3676a1b36f774d..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/AccessibleAnswerFragment.java
+++ /dev/null
@@ -1,157 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.os.Bundle;
-import android.telecom.VideoProfile;
-import android.view.GestureDetector;
-import android.view.GestureDetector.SimpleOnGestureListener;
-import android.view.LayoutInflater;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.android.dialer.R;
-
-/**
- * AnswerFragment to use when touch exploration is enabled in accessibility.
- */
-public class AccessibleAnswerFragment extends AnswerFragment {
-
- private static final String TAG = AccessibleAnswerFragment.class.getSimpleName();
- private static final int SWIPE_THRESHOLD = 100;
-
- private View mAnswer;
- private View mDecline;
- private View mText;
-
- private TouchListener mTouchListener;
- private GestureDetector mGestureDetector;
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- ViewGroup group = (ViewGroup) inflater.inflate(R.layout.accessible_answer_fragment,
- container, false);
-
- mTouchListener = new TouchListener();
- mGestureDetector = new GestureDetector(getContext(), new SimpleOnGestureListener() {
- @Override
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
- float velocityY) {
- return AccessibleAnswerFragment.this.onFling(e1, e2, velocityX, velocityX);
- }
- });
-
- mAnswer = group.findViewById(R.id.accessible_answer_fragment_answer);
- mAnswer.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- Log.d(TAG, "Answer Button Clicked");
- onAnswer(VideoProfile.STATE_AUDIO_ONLY, getContext());
- }
- });
- mDecline = group.findViewById(R.id.accessible_answer_fragment_decline);
- mDecline.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- Log.d(TAG, "Decline Button Clicked");
- onDecline(getContext());
- }
- });
-
- mText = group.findViewById(R.id.accessible_answer_fragment_text);
- mText.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- Log.d(TAG, "Text Button Clicked");
- onText();
- }
- });
- return group;
- }
-
- @Override
- public void onResume() {
- super.onResume();
- // Intercept all touch events for full screen swiping gesture.
- InCallActivity activity = (InCallActivity) getActivity();
- activity.setDispatchTouchEventListener(mTouchListener);
- }
-
- @Override
- public void onPause() {
- super.onPause();
- InCallActivity activity = (InCallActivity) getActivity();
- activity.setDispatchTouchEventListener(null);
- }
-
- private class TouchListener implements View.OnTouchListener {
- @Override
- public boolean onTouch(View v, MotionEvent event) {
- return mGestureDetector.onTouchEvent(event);
- }
- }
-
- private boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
- float velocityY) {
- if (hasPendingDialogs()) {
- return false;
- }
-
- float diffY = e2.getY() - e1.getY();
- float diffX = e2.getX() - e1.getX();
- if (Math.abs(diffX) > Math.abs(diffY)) {
- if (Math.abs(diffX) > SWIPE_THRESHOLD) {
- if (diffX > 0) {
- onSwipeRight();
- } else {
- onSwipeLeft();
- }
- }
- return true;
- } else if (Math.abs(diffY) > SWIPE_THRESHOLD) {
- if (diffY > 0) {
- onSwipeDown();
- } else {
- onSwipeUp();
- }
- return true;
- }
-
- return false;
- }
-
- private void onSwipeUp() {
- Log.d(TAG, "onSwipeUp");
- onText();
- }
-
- private void onSwipeDown() {
- Log.d(TAG, "onSwipeDown");
- }
-
- private void onSwipeLeft() {
- Log.d(TAG, "onSwipeLeft");
- onDecline(getContext());
- }
-
- private void onSwipeRight() {
- Log.d(TAG, "onSwipeRight");
- onAnswer(VideoProfile.STATE_AUDIO_ONLY, getContext());
- }
-}
diff --git a/InCallUI/src/com/android/incallui/AnswerFragment.java b/InCallUI/src/com/android/incallui/AnswerFragment.java
deleted file mode 100644
index 44ddfcd49c1dd1a5a6c95934f6fd7055161feba1..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/AnswerFragment.java
+++ /dev/null
@@ -1,307 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.app.AlertDialog;
-import android.app.Dialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.os.Bundle;
-import android.text.Editable;
-import android.text.TextWatcher;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.WindowManager;
-import android.widget.AdapterView;
-import android.widget.ArrayAdapter;
-import android.widget.Button;
-import android.widget.EditText;
-import android.widget.ListView;
-
-import com.android.dialer.R;
-
-import java.util.ArrayList;
-import java.util.List;
-
-
-/**
- * Provides only common interface and functions. Should be derived to implement the actual UI.
- */
-public abstract class AnswerFragment extends BaseFragment
- implements AnswerPresenter.AnswerUi {
-
- public static final int TARGET_SET_FOR_AUDIO_WITHOUT_SMS = 0;
- public static final int TARGET_SET_FOR_AUDIO_WITH_SMS = 1;
- public static final int TARGET_SET_FOR_VIDEO_WITHOUT_SMS = 2;
- public static final int TARGET_SET_FOR_VIDEO_WITH_SMS = 3;
- public static final int TARGET_SET_FOR_VIDEO_ACCEPT_REJECT_REQUEST = 4;
-
- /**
- * This fragment implement no UI at all. Derived class should do it.
- */
- @Override
- public abstract View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState);
-
- /**
- * The popup showing the list of canned responses.
- *
- * This is an AlertDialog containing a ListView showing the possible choices. This may be null
- * if the InCallScreen hasn't ever called showRespondViaSmsPopup() yet, or if the popup was
- * visible once but then got dismissed.
- */
- private Dialog mCannedResponsePopup = null;
-
- /**
- * The popup showing a text field for users to type in their custom message.
- */
- private AlertDialog mCustomMessagePopup = null;
-
- private ArrayAdapter mSmsResponsesAdapter;
-
- private final List mSmsResponses = new ArrayList<>();
-
- @Override
- public AnswerPresenter createPresenter() {
- return InCallPresenter.getInstance().getAnswerPresenter();
- }
-
- @Override
- public AnswerPresenter.AnswerUi getUi() {
- return this;
- }
-
- @Override
- public void showMessageDialog() {
- final AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
-
- mSmsResponsesAdapter = new ArrayAdapter<>(builder.getContext(),
- android.R.layout.simple_list_item_1, android.R.id.text1, mSmsResponses);
-
- final ListView lv = new ListView(getActivity());
- lv.setAdapter(mSmsResponsesAdapter);
- lv.setOnItemClickListener(new RespondViaSmsItemClickListener());
-
- builder.setCancelable(true).setView(lv).setOnCancelListener(
- new DialogInterface.OnCancelListener() {
- @Override
- public void onCancel(DialogInterface dialogInterface) {
- onMessageDialogCancel();
- dismissCannedResponsePopup();
- getPresenter().onDismissDialog();
- }
- });
- mCannedResponsePopup = builder.create();
- mCannedResponsePopup.getWindow().addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED);
- mCannedResponsePopup.show();
- }
-
- private boolean isCannedResponsePopupShowing() {
- if (mCannedResponsePopup != null) {
- return mCannedResponsePopup.isShowing();
- }
- return false;
- }
-
- private boolean isCustomMessagePopupShowing() {
- if (mCustomMessagePopup != null) {
- return mCustomMessagePopup.isShowing();
- }
- return false;
- }
-
- /**
- * Dismiss the canned response list popup.
- *
- * This is safe to call even if the popup is already dismissed, and even if you never called
- * showRespondViaSmsPopup() in the first place.
- */
- protected void dismissCannedResponsePopup() {
- if (mCannedResponsePopup != null) {
- mCannedResponsePopup.dismiss(); // safe even if already dismissed
- mCannedResponsePopup = null;
- }
- }
-
- /**
- * Dismiss the custom compose message popup.
- */
- private void dismissCustomMessagePopup() {
- if (mCustomMessagePopup != null) {
- mCustomMessagePopup.dismiss();
- mCustomMessagePopup = null;
- }
- }
-
- public void dismissPendingDialogs() {
- if (isCannedResponsePopupShowing()) {
- dismissCannedResponsePopup();
- }
-
- if (isCustomMessagePopupShowing()) {
- dismissCustomMessagePopup();
- }
- }
-
- public boolean hasPendingDialogs() {
- return !(mCannedResponsePopup == null && mCustomMessagePopup == null);
- }
-
- /**
- * Shows the custom message entry dialog.
- */
- public void showCustomMessageDialog() {
- // Create an alert dialog containing an EditText
- final AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
- final EditText et = new EditText(builder.getContext());
- builder.setCancelable(true).setView(et)
- .setPositiveButton(R.string.custom_message_send,
- new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- // The order is arranged in a way that the popup will be destroyed
- // when the InCallActivity is about to finish.
- final String textMessage = et.getText().toString().trim();
- dismissCustomMessagePopup();
- getPresenter().rejectCallWithMessage(textMessage);
- }
- })
- .setNegativeButton(R.string.custom_message_cancel,
- new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- dismissCustomMessagePopup();
- getPresenter().onDismissDialog();
- }
- })
- .setOnCancelListener(new DialogInterface.OnCancelListener() {
- @Override
- public void onCancel(DialogInterface dialogInterface) {
- dismissCustomMessagePopup();
- getPresenter().onDismissDialog();
- }
- })
- .setTitle(R.string.respond_via_sms_custom_message);
- mCustomMessagePopup = builder.create();
-
- // Enable/disable the send button based on whether there is a message in the EditText
- et.addTextChangedListener(new TextWatcher() {
- @Override
- public void beforeTextChanged(CharSequence s, int start, int count, int after) {
- }
-
- @Override
- public void onTextChanged(CharSequence s, int start, int before, int count) {
- }
-
- @Override
- public void afterTextChanged(Editable s) {
- final Button sendButton = mCustomMessagePopup.getButton(
- DialogInterface.BUTTON_POSITIVE);
- sendButton.setEnabled(s != null && s.toString().trim().length() != 0);
- }
- });
-
- // Keyboard up, show the dialog
- mCustomMessagePopup.getWindow().setSoftInputMode(
- WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
- mCustomMessagePopup.getWindow().addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED);
- mCustomMessagePopup.show();
-
- // Send button starts out disabled
- final Button sendButton = mCustomMessagePopup.getButton(DialogInterface.BUTTON_POSITIVE);
- sendButton.setEnabled(false);
- }
-
- @Override
- public void configureMessageDialog(List textResponses) {
- mSmsResponses.clear();
- mSmsResponses.addAll(textResponses);
- mSmsResponses.add(getResources().getString(
- R.string.respond_via_sms_custom_message));
- if (mSmsResponsesAdapter != null) {
- mSmsResponsesAdapter.notifyDataSetChanged();
- }
- }
-
- @Override
- public Context getContext() {
- return getActivity();
- }
-
- public void onAnswer(int videoState, Context context) {
- Log.d(this, "onAnswer videoState=" + videoState + " context=" + context);
- getPresenter().onAnswer(videoState, context);
- }
-
- public void onDecline(Context context) {
- getPresenter().onDecline(context);
- }
-
- public void onDeclineUpgradeRequest(Context context) {
- InCallPresenter.getInstance().declineUpgradeRequest(context);
- }
-
- public void onText() {
- getPresenter().onText();
- }
-
- /**
- * OnItemClickListener for the "Respond via SMS" popup.
- */
- public class RespondViaSmsItemClickListener implements AdapterView.OnItemClickListener {
-
- /**
- * Handles the user selecting an item from the popup.
- */
- @Override
- public void onItemClick(AdapterView> parent, // The ListView
- View view, // The TextView that was clicked
- int position, long id) {
- Log.d(this, "RespondViaSmsItemClickListener.onItemClick(" + position + ")...");
- final String message = (String) parent.getItemAtPosition(position);
- Log.v(this, "- message: '" + message + "'");
- dismissCannedResponsePopup();
-
- // The "Custom" choice is a special case.
- // (For now, it's guaranteed to be the last item.)
- if (position == (parent.getCount() - 1)) {
- // Show the custom message dialog
- showCustomMessageDialog();
- } else {
- getPresenter().rejectCallWithMessage(message);
- }
- }
- }
-
- public void onShowAnswerUi(boolean shown) {
- // Do Nothing
- }
-
- public void showTargets(int targetSet) {
- // Do Nothing
- }
-
- public void showTargets(int targetSet, int videoState) {
- // Do Nothing
- }
-
- protected void onMessageDialogCancel() {
- // Do nothing.
- }
-}
diff --git a/InCallUI/src/com/android/incallui/AnswerPresenter.java b/InCallUI/src/com/android/incallui/AnswerPresenter.java
deleted file mode 100644
index 883b54fed7925fa27ace1040a44482b36e575547..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/AnswerPresenter.java
+++ /dev/null
@@ -1,312 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-
-import com.android.dialer.compat.UserManagerCompat;
-import com.android.dialer.util.TelecomUtil;
-import com.android.incallui.InCallPresenter.InCallState;
-
-import java.util.List;
-
-/**
- * Presenter for the Incoming call widget. The {@link AnswerPresenter} handles the logic during
- * incoming calls. It is also in charge of responding to incoming calls, so there needs to be
- * an instance alive so that it can receive onIncomingCall callbacks.
- *
- * An instance of {@link AnswerPresenter} is created by InCallPresenter at startup, registers
- * for callbacks via InCallPresenter, and shows/hides the {@link AnswerFragment} via IncallActivity.
- *
- */
-public class AnswerPresenter extends Presenter
- implements CallList.CallUpdateListener, InCallPresenter.InCallUiListener,
- InCallPresenter.IncomingCallListener,
- CallList.Listener {
-
- private static final String TAG = AnswerPresenter.class.getSimpleName();
-
- private String mCallId;
- private Call mCall = null;
- private boolean mHasTextMessages = false;
-
- @Override
- public void onUiShowing(boolean showing) {
- if (showing) {
- CallList.getInstance().addListener(this);
- final CallList calls = CallList.getInstance();
- Call call;
- call = calls.getIncomingCall();
- if (call != null) {
- processIncomingCall(call);
- }
- call = calls.getVideoUpgradeRequestCall();
- Log.d(this, "getVideoUpgradeRequestCall call =" + call);
- if (call != null) {
- showAnswerUi(true);
- processVideoUpgradeRequestCall(call);
- }
- } else {
- CallList.getInstance().removeListener(this);
- // This is necessary because the activity can be destroyed while an incoming call exists.
- // This happens when back button is pressed while incoming call is still being shown.
- if (mCallId != null) {
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- }
- }
- }
-
- @Override
- public void onIncomingCall(InCallState oldState, InCallState newState, Call call) {
- Log.d(this, "onIncomingCall: " + this);
- Call modifyCall = CallList.getInstance().getVideoUpgradeRequestCall();
- if (modifyCall != null) {
- showAnswerUi(false);
- Log.d(this, "declining upgrade request id: ");
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- InCallPresenter.getInstance().declineUpgradeRequest();
- }
- if (!call.getId().equals(mCallId)) {
- // A new call is coming in.
- processIncomingCall(call);
- }
- }
-
- @Override
- public void onIncomingCall(Call call) {
- }
-
- @Override
- public void onCallListChange(CallList list) {
- }
-
- @Override
- public void onDisconnect(Call call) {
- // no-op
- }
-
- public void onSessionModificationStateChange(int sessionModificationState) {
- boolean isUpgradePending = sessionModificationState ==
- Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST;
-
- if (!isUpgradePending) {
- // Stop listening for updates.
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- showAnswerUi(false);
- }
- }
-
- @Override
- public void onLastForwardedNumberChange() {
- // no-op
- }
-
- @Override
- public void onChildNumberChange() {
- // no-op
- }
-
- private boolean isVideoUpgradePending(Call call) {
- return call.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST;
- }
-
- @Override
- public void onUpgradeToVideo(Call call) {
- Log.d(this, "onUpgradeToVideo: " + this + " call=" + call);
- showAnswerUi(true);
- boolean isUpgradePending = isVideoUpgradePending(call);
- InCallPresenter inCallPresenter = InCallPresenter.getInstance();
- if (isUpgradePending
- && inCallPresenter.getInCallState() == InCallPresenter.InCallState.INCOMING) {
- Log.d(this, "declining upgrade request");
- //If there is incoming call reject upgrade request
- inCallPresenter.declineUpgradeRequest(getUi().getContext());
- } else if (isUpgradePending) {
- Log.d(this, "process upgrade request as no MT call");
- processVideoUpgradeRequestCall(call);
- }
- }
-
- private void processIncomingCall(Call call) {
- mCallId = call.getId();
- mCall = call;
-
- // Listen for call updates for the current call.
- CallList.getInstance().addCallUpdateListener(mCallId, this);
-
- Log.d(TAG, "Showing incoming for call id: " + mCallId + " " + this);
- if (showAnswerUi(true)) {
- final List textMsgs = CallList.getInstance().getTextResponses(call.getId());
- configureAnswerTargetsForSms(call, textMsgs);
- }
- }
-
- private boolean showAnswerUi(boolean show) {
- final InCallActivity activity = InCallPresenter.getInstance().getActivity();
- if (activity != null) {
- activity.showAnswerFragment(show);
- if (getUi() != null) {
- getUi().onShowAnswerUi(show);
- }
- return true;
- } else {
- return false;
- }
- }
-
- private void processVideoUpgradeRequestCall(Call call) {
- Log.d(this, " processVideoUpgradeRequestCall call=" + call);
- mCallId = call.getId();
- mCall = call;
-
- // Listen for call updates for the current call.
- CallList.getInstance().addCallUpdateListener(mCallId, this);
-
- final int currentVideoState = call.getVideoState();
- final int modifyToVideoState = call.getRequestedVideoState();
-
- if (currentVideoState == modifyToVideoState) {
- Log.w(this, "processVideoUpgradeRequestCall: Video states are same. Return.");
- return;
- }
-
- AnswerUi ui = getUi();
-
- if (ui == null) {
- Log.e(this, "Ui is null. Can't process upgrade request");
- return;
- }
- showAnswerUi(true);
- ui.showTargets(AnswerFragment.TARGET_SET_FOR_VIDEO_ACCEPT_REJECT_REQUEST,
- modifyToVideoState);
- }
-
- private boolean isEnabled(int videoState, int mask) {
- return (videoState & mask) == mask;
- }
-
- @Override
- public void onCallChanged(Call call) {
- Log.d(this, "onCallStateChange() " + call + " " + this);
- if (call.getState() != Call.State.INCOMING) {
- boolean isUpgradePending = isVideoUpgradePending(call);
- if (!isUpgradePending) {
- // Stop listening for updates.
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- }
-
- final Call incall = CallList.getInstance().getIncomingCall();
- if (incall != null || isUpgradePending) {
- showAnswerUi(true);
- } else {
- showAnswerUi(false);
- }
-
- mHasTextMessages = false;
- } else if (!mHasTextMessages) {
- final List textMsgs = CallList.getInstance().getTextResponses(call.getId());
- if (textMsgs != null) {
- configureAnswerTargetsForSms(call, textMsgs);
- }
- }
- }
-
- public void onAnswer(int videoState, Context context) {
- if (mCallId == null) {
- return;
- }
-
- if (mCall.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- Log.d(this, "onAnswer (upgradeCall) mCallId=" + mCallId + " videoState=" + videoState);
- InCallPresenter.getInstance().acceptUpgradeRequest(videoState, context);
- } else {
- Log.d(this, "onAnswer (answerCall) mCallId=" + mCallId + " videoState=" + videoState);
- TelecomAdapter.getInstance().answerCall(mCall.getId(), videoState);
- }
- }
-
- /**
- * TODO: We are using reject and decline interchangeably. We should settle on
- * reject since it seems to be more prevalent.
- */
- public void onDecline(Context context) {
- Log.d(this, "onDecline " + mCallId);
- if (mCall.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- InCallPresenter.getInstance().declineUpgradeRequest(context);
- } else {
- TelecomAdapter.getInstance().rejectCall(mCall.getId(), false, null);
- }
- }
-
- public void onText() {
- if (getUi() != null) {
- TelecomUtil.silenceRinger(getUi().getContext());
- getUi().showMessageDialog();
- }
- }
-
- public void rejectCallWithMessage(String message) {
- Log.d(this, "sendTextToDefaultActivity()...");
- TelecomAdapter.getInstance().rejectCall(mCall.getId(), true, message);
-
- onDismissDialog();
- }
-
- public void onDismissDialog() {
- InCallPresenter.getInstance().onDismissDialog();
- }
-
- private void configureAnswerTargetsForSms(Call call, List textMsgs) {
- if (getUi() == null) {
- return;
- }
- mHasTextMessages = textMsgs != null;
- boolean withSms = UserManagerCompat.isUserUnlocked(getUi().getContext())
- && call.can(android.telecom.Call.Details.CAPABILITY_RESPOND_VIA_TEXT)
- && mHasTextMessages;
-
- // Only present the user with the option to answer as a video call if the incoming call is
- // a bi-directional video call.
- if (VideoUtils.isBidirectionalVideoCall(call)) {
- if (withSms) {
- getUi().showTargets(AnswerFragment.TARGET_SET_FOR_VIDEO_WITH_SMS);
- getUi().configureMessageDialog(textMsgs);
- } else {
- getUi().showTargets(AnswerFragment.TARGET_SET_FOR_VIDEO_WITHOUT_SMS);
- }
- } else {
- if (withSms) {
- getUi().showTargets(AnswerFragment.TARGET_SET_FOR_AUDIO_WITH_SMS);
- getUi().configureMessageDialog(textMsgs);
- } else {
- getUi().showTargets(AnswerFragment.TARGET_SET_FOR_AUDIO_WITHOUT_SMS);
- }
- }
- }
-
- interface AnswerUi extends Ui {
- public void onShowAnswerUi(boolean shown);
- public void showTargets(int targetSet);
- public void showTargets(int targetSet, int videoState);
- public void showMessageDialog();
- public void configureMessageDialog(List textResponses);
- public Context getContext();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/AudioModeProvider.java b/InCallUI/src/com/android/incallui/AudioModeProvider.java
deleted file mode 100644
index ea56dd6249a97285a92d51bd69d3de9aafc9560b..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/AudioModeProvider.java
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.telecom.CallAudioState;
-
-import com.google.common.collect.Lists;
-
-import java.util.List;
-
-/**
- * Proxy class for getting and setting the audio mode.
- */
-public class AudioModeProvider {
-
- static final int AUDIO_MODE_INVALID = 0;
-
- private static AudioModeProvider sAudioModeProvider = new AudioModeProvider();
- private int mAudioMode = CallAudioState.ROUTE_EARPIECE;
- private boolean mMuted = false;
- private int mSupportedModes = CallAudioState.ROUTE_EARPIECE
- | CallAudioState.ROUTE_BLUETOOTH | CallAudioState.ROUTE_WIRED_HEADSET
- | CallAudioState.ROUTE_SPEAKER;
- private final List mListeners = Lists.newArrayList();
-
- public static AudioModeProvider getInstance() {
- return sAudioModeProvider;
- }
-
- public void onAudioStateChanged(boolean isMuted, int route, int supportedRouteMask) {
- onAudioModeChange(route, isMuted);
- onSupportedAudioModeChange(supportedRouteMask);
- }
-
- public void onAudioModeChange(int newMode, boolean muted) {
- if (mAudioMode != newMode) {
- mAudioMode = newMode;
- for (AudioModeListener l : mListeners) {
- l.onAudioMode(mAudioMode);
- }
- }
-
- if (mMuted != muted) {
- mMuted = muted;
- for (AudioModeListener l : mListeners) {
- l.onMute(mMuted);
- }
- }
- }
-
- public void onSupportedAudioModeChange(int newModeMask) {
- mSupportedModes = newModeMask;
-
- for (AudioModeListener l : mListeners) {
- l.onSupportedAudioMode(mSupportedModes);
- }
- }
-
- public void addListener(AudioModeListener listener) {
- if (!mListeners.contains(listener)) {
- mListeners.add(listener);
- listener.onSupportedAudioMode(mSupportedModes);
- listener.onAudioMode(mAudioMode);
- listener.onMute(mMuted);
- }
- }
-
- public void removeListener(AudioModeListener listener) {
- if (mListeners.contains(listener)) {
- mListeners.remove(listener);
- }
- }
-
- public int getSupportedModes() {
- return mSupportedModes;
- }
-
- public int getAudioMode() {
- return mAudioMode;
- }
-
- public boolean getMute() {
- return mMuted;
- }
-
- /* package */ interface AudioModeListener {
- void onAudioMode(int newMode);
- void onMute(boolean muted);
- void onSupportedAudioMode(int modeMask);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/BaseFragment.java b/InCallUI/src/com/android/incallui/BaseFragment.java
deleted file mode 100644
index 58d991acd3dd4979d0bfcb5306c993396d27bd67..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/BaseFragment.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.app.Activity;
-import android.app.Fragment;
-import android.os.Bundle;
-
-/**
- * Parent for all fragments that use Presenters and Ui design.
- */
-public abstract class BaseFragment, U extends Ui> extends Fragment {
-
- private static final String KEY_FRAGMENT_HIDDEN = "key_fragment_hidden";
-
- private T mPresenter;
-
- public abstract T createPresenter();
-
- public abstract U getUi();
-
- protected BaseFragment() {
- mPresenter = createPresenter();
- }
-
- /**
- * Presenter will be available after onActivityCreated().
- *
- * @return The presenter associated with this fragment.
- */
- public T getPresenter() {
- return mPresenter;
- }
-
- @Override
- public void onActivityCreated(Bundle savedInstanceState) {
- super.onActivityCreated(savedInstanceState);
- mPresenter.onUiReady(getUi());
- }
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- if (savedInstanceState != null) {
- mPresenter.onRestoreInstanceState(savedInstanceState);
- if (savedInstanceState.getBoolean(KEY_FRAGMENT_HIDDEN)) {
- getFragmentManager().beginTransaction().hide(this).commit();
- }
- }
- }
-
- @Override
- public void onDestroyView() {
- super.onDestroyView();
- mPresenter.onUiDestroy(getUi());
- }
-
- @Override
- public void onSaveInstanceState(Bundle outState) {
- super.onSaveInstanceState(outState);
- mPresenter.onSaveInstanceState(outState);
- outState.putBoolean(KEY_FRAGMENT_HIDDEN, isHidden());
- }
-
- @Override
- public void onAttach(Activity activity) {
- super.onAttach(activity);
- ((FragmentDisplayManager) activity).onFragmentAttached(this);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/Call.java b/InCallUI/src/com/android/incallui/Call.java
deleted file mode 100644
index 1ad37e01a8c21e5b92f97c9c3a7cd89b9b8bbc3b..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/Call.java
+++ /dev/null
@@ -1,1023 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.hardware.camera2.CameraCharacteristics;
-import android.net.Uri;
-import android.os.Bundle;
-import android.os.Trace;
-import android.support.annotation.IntDef;
-import android.telecom.Call.Details;
-import android.telecom.Connection;
-import android.telecom.DisconnectCause;
-import android.telecom.GatewayInfo;
-import android.telecom.InCallService.VideoCall;
-import android.telecom.PhoneAccount;
-import android.telecom.PhoneAccountHandle;
-import android.telecom.TelecomManager;
-import android.telecom.VideoProfile;
-import android.text.TextUtils;
-
-import com.android.contacts.common.CallUtil;
-import com.android.contacts.common.compat.CallSdkCompat;
-import com.android.contacts.common.compat.CompatUtils;
-import com.android.contacts.common.compat.SdkVersionOverride;
-import com.android.contacts.common.compat.telecom.TelecomManagerCompat;
-import com.android.contacts.common.testing.NeededForTesting;
-import com.android.dialer.util.IntentUtil;
-import com.android.incallui.util.TelecomCallUtil;
-
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Locale;
-import java.util.Objects;
-
-/**
- * Describes a single call and its state.
- */
-@NeededForTesting
-public class Call {
-
- /**
- * Specifies whether a number is in the call history or not.
- * {@link #CALL_HISTORY_STATUS_UNKNOWN} means there is no result.
- */
- @IntDef({CALL_HISTORY_STATUS_UNKNOWN, CALL_HISTORY_STATUS_PRESENT,
- CALL_HISTORY_STATUS_NOT_PRESENT})
- @Retention(RetentionPolicy.SOURCE)
- public @interface CallHistoryStatus {}
- public static final int CALL_HISTORY_STATUS_UNKNOWN = 0;
- public static final int CALL_HISTORY_STATUS_PRESENT = 1;
- public static final int CALL_HISTORY_STATUS_NOT_PRESENT = 2;
-
- /* Defines different states of this call */
- public static class State {
- public static final int INVALID = 0;
- public static final int NEW = 1; /* The call is new. */
- public static final int IDLE = 2; /* The call is idle. Nothing active */
- public static final int ACTIVE = 3; /* There is an active call */
- public static final int INCOMING = 4; /* A normal incoming phone call */
- public static final int CALL_WAITING = 5; /* Incoming call while another is active */
- public static final int DIALING = 6; /* An outgoing call during dial phase */
- public static final int REDIALING = 7; /* Subsequent dialing attempt after a failure */
- public static final int ONHOLD = 8; /* An active phone call placed on hold */
- public static final int DISCONNECTING = 9; /* A call is being ended. */
- public static final int DISCONNECTED = 10; /* State after a call disconnects */
- public static final int CONFERENCED = 11; /* Call part of a conference call */
- public static final int SELECT_PHONE_ACCOUNT = 12; /* Waiting for account selection */
- public static final int CONNECTING = 13; /* Waiting for Telecom broadcast to finish */
- public static final int BLOCKED = 14; /* The number was found on the block list */
-
-
- public static boolean isConnectingOrConnected(int state) {
- switch(state) {
- case ACTIVE:
- case INCOMING:
- case CALL_WAITING:
- case CONNECTING:
- case DIALING:
- case REDIALING:
- case ONHOLD:
- case CONFERENCED:
- return true;
- default:
- }
- return false;
- }
-
- public static boolean isDialing(int state) {
- return state == DIALING || state == REDIALING;
- }
-
- public static String toString(int state) {
- switch (state) {
- case INVALID:
- return "INVALID";
- case NEW:
- return "NEW";
- case IDLE:
- return "IDLE";
- case ACTIVE:
- return "ACTIVE";
- case INCOMING:
- return "INCOMING";
- case CALL_WAITING:
- return "CALL_WAITING";
- case DIALING:
- return "DIALING";
- case REDIALING:
- return "REDIALING";
- case ONHOLD:
- return "ONHOLD";
- case DISCONNECTING:
- return "DISCONNECTING";
- case DISCONNECTED:
- return "DISCONNECTED";
- case CONFERENCED:
- return "CONFERENCED";
- case SELECT_PHONE_ACCOUNT:
- return "SELECT_PHONE_ACCOUNT";
- case CONNECTING:
- return "CONNECTING";
- case BLOCKED:
- return "BLOCKED";
- default:
- return "UNKNOWN";
- }
- }
- }
-
- /**
- * Defines different states of session modify requests, which are used to upgrade to video, or
- * downgrade to audio.
- */
- public static class SessionModificationState {
- public static final int NO_REQUEST = 0;
- public static final int WAITING_FOR_RESPONSE = 1;
- public static final int REQUEST_FAILED = 2;
- public static final int RECEIVED_UPGRADE_TO_VIDEO_REQUEST = 3;
- public static final int UPGRADE_TO_VIDEO_REQUEST_TIMED_OUT = 4;
- public static final int REQUEST_REJECTED = 5;
- }
-
- public static class VideoSettings {
- public static final int CAMERA_DIRECTION_UNKNOWN = -1;
- public static final int CAMERA_DIRECTION_FRONT_FACING =
- CameraCharacteristics.LENS_FACING_FRONT;
- public static final int CAMERA_DIRECTION_BACK_FACING =
- CameraCharacteristics.LENS_FACING_BACK;
-
- private int mCameraDirection = CAMERA_DIRECTION_UNKNOWN;
-
- /**
- * Sets the camera direction. if camera direction is set to CAMERA_DIRECTION_UNKNOWN,
- * the video state of the call should be used to infer the camera direction.
- *
- * @see {@link CameraCharacteristics#LENS_FACING_FRONT}
- * @see {@link CameraCharacteristics#LENS_FACING_BACK}
- */
- public void setCameraDir(int cameraDirection) {
- if (cameraDirection == CAMERA_DIRECTION_FRONT_FACING
- || cameraDirection == CAMERA_DIRECTION_BACK_FACING) {
- mCameraDirection = cameraDirection;
- } else {
- mCameraDirection = CAMERA_DIRECTION_UNKNOWN;
- }
- }
-
- /**
- * Gets the camera direction. if camera direction is set to CAMERA_DIRECTION_UNKNOWN,
- * the video state of the call should be used to infer the camera direction.
- *
- * @see {@link CameraCharacteristics#LENS_FACING_FRONT}
- * @see {@link CameraCharacteristics#LENS_FACING_BACK}
- */
- public int getCameraDir() {
- return mCameraDirection;
- }
-
- @Override
- public String toString() {
- return "(CameraDir:" + getCameraDir() + ")";
- }
- }
-
- /**
- * Tracks any state variables that is useful for logging. There is some amount of overlap with
- * existing call member variables, but this duplication helps to ensure that none of these
- * logging variables will interface with/and affect call logic.
- */
- public static class LogState {
-
- // Contact lookup type constants
- // Unknown lookup result (lookup not completed yet?)
- public static final int LOOKUP_UNKNOWN = 0;
- public static final int LOOKUP_NOT_FOUND = 1;
- public static final int LOOKUP_LOCAL_CONTACT = 2;
- public static final int LOOKUP_LOCAL_CACHE = 3;
- public static final int LOOKUP_REMOTE_CONTACT = 4;
- public static final int LOOKUP_EMERGENCY = 5;
- public static final int LOOKUP_VOICEMAIL = 6;
-
- // Call initiation type constants
- public static final int INITIATION_UNKNOWN = 0;
- public static final int INITIATION_INCOMING = 1;
- public static final int INITIATION_DIALPAD = 2;
- public static final int INITIATION_SPEED_DIAL = 3;
- public static final int INITIATION_REMOTE_DIRECTORY = 4;
- public static final int INITIATION_SMART_DIAL = 5;
- public static final int INITIATION_REGULAR_SEARCH = 6;
- public static final int INITIATION_CALL_LOG = 7;
- public static final int INITIATION_CALL_LOG_FILTER = 8;
- public static final int INITIATION_VOICEMAIL_LOG = 9;
- public static final int INITIATION_CALL_DETAILS = 10;
- public static final int INITIATION_QUICK_CONTACTS = 11;
- public static final int INITIATION_EXTERNAL = 12;
-
- public DisconnectCause disconnectCause;
- public boolean isIncoming = false;
- public int contactLookupResult = LOOKUP_UNKNOWN;
- public int callInitiationMethod = INITIATION_EXTERNAL;
- // If this was a conference call, the total number of calls involved in the conference.
- public int conferencedCalls = 0;
- public long duration = 0;
- public boolean isLogged = false;
-
- @Override
- public String toString() {
- return String.format(Locale.US, "["
- + "%s, " // DisconnectCause toString already describes the object type
- + "isIncoming: %s, "
- + "contactLookup: %s, "
- + "callInitiation: %s, "
- + "duration: %s"
- + "]",
- disconnectCause,
- isIncoming,
- lookupToString(contactLookupResult),
- initiationToString(callInitiationMethod),
- duration);
- }
-
- private static String lookupToString(int lookupType) {
- switch (lookupType) {
- case LOOKUP_LOCAL_CONTACT:
- return "Local";
- case LOOKUP_LOCAL_CACHE:
- return "Cache";
- case LOOKUP_REMOTE_CONTACT:
- return "Remote";
- case LOOKUP_EMERGENCY:
- return "Emergency";
- case LOOKUP_VOICEMAIL:
- return "Voicemail";
- default:
- return "Not found";
- }
- }
-
- private static String initiationToString(int initiationType) {
- switch (initiationType) {
- case INITIATION_INCOMING:
- return "Incoming";
- case INITIATION_DIALPAD:
- return "Dialpad";
- case INITIATION_SPEED_DIAL:
- return "Speed Dial";
- case INITIATION_REMOTE_DIRECTORY:
- return "Remote Directory";
- case INITIATION_SMART_DIAL:
- return "Smart Dial";
- case INITIATION_REGULAR_SEARCH:
- return "Regular Search";
- case INITIATION_CALL_LOG:
- return "Call Log";
- case INITIATION_CALL_LOG_FILTER:
- return "Call Log Filter";
- case INITIATION_VOICEMAIL_LOG:
- return "Voicemail Log";
- case INITIATION_CALL_DETAILS:
- return "Call Details";
- case INITIATION_QUICK_CONTACTS:
- return "Quick Contacts";
- default:
- return "Unknown";
- }
- }
- }
-
-
- private static final String ID_PREFIX = Call.class.getSimpleName() + "_";
- private static int sIdCounter = 0;
-
- private final android.telecom.Call.Callback mTelecomCallCallback =
- new android.telecom.Call.Callback() {
- @Override
- public void onStateChanged(android.telecom.Call call, int newState) {
- Log.d(this, "TelecomCallCallback onStateChanged call=" + call + " newState="
- + newState);
- update();
- }
-
- @Override
- public void onParentChanged(android.telecom.Call call,
- android.telecom.Call newParent) {
- Log.d(this, "TelecomCallCallback onParentChanged call=" + call + " newParent="
- + newParent);
- update();
- }
-
- @Override
- public void onChildrenChanged(android.telecom.Call call,
- List children) {
- update();
- }
-
- @Override
- public void onDetailsChanged(android.telecom.Call call,
- android.telecom.Call.Details details) {
- Log.d(this, "TelecomCallCallback onStateChanged call=" + call + " details="
- + details);
- update();
- }
-
- @Override
- public void onCannedTextResponsesLoaded(android.telecom.Call call,
- List cannedTextResponses) {
- Log.d(this, "TelecomCallCallback onStateChanged call=" + call
- + " cannedTextResponses=" + cannedTextResponses);
- update();
- }
-
- @Override
- public void onPostDialWait(android.telecom.Call call,
- String remainingPostDialSequence) {
- Log.d(this, "TelecomCallCallback onStateChanged call=" + call
- + " remainingPostDialSequence=" + remainingPostDialSequence);
- update();
- }
-
- @Override
- public void onVideoCallChanged(android.telecom.Call call,
- VideoCall videoCall) {
- Log.d(this, "TelecomCallCallback onStateChanged call=" + call + " videoCall="
- + videoCall);
- update();
- }
-
- @Override
- public void onCallDestroyed(android.telecom.Call call) {
- Log.d(this, "TelecomCallCallback onStateChanged call=" + call);
- call.unregisterCallback(this);
- }
-
- @Override
- public void onConferenceableCallsChanged(android.telecom.Call call,
- List conferenceableCalls) {
- update();
- }
- };
-
- private final android.telecom.Call mTelecomCall;
- private final LatencyReport mLatencyReport;
- private boolean mIsEmergencyCall;
- private Uri mHandle;
- private final String mId;
- private int mState = State.INVALID;
- private DisconnectCause mDisconnectCause;
- private int mSessionModificationState;
- private final List mChildCallIds = new ArrayList<>();
- private final VideoSettings mVideoSettings = new VideoSettings();
- private int mVideoState;
-
- /**
- * mRequestedVideoState is used to store requested upgrade / downgrade video state
- */
- private int mRequestedVideoState = VideoProfile.STATE_AUDIO_ONLY;
-
- private InCallVideoCallCallback mVideoCallCallback;
- private boolean mIsVideoCallCallbackRegistered;
- private String mChildNumber;
- private String mLastForwardedNumber;
- private String mCallSubject;
- private PhoneAccountHandle mPhoneAccountHandle;
- @CallHistoryStatus private int mCallHistoryStatus = CALL_HISTORY_STATUS_UNKNOWN;
- private boolean mIsSpam;
-
- /**
- * Indicates whether the phone account associated with this call supports specifying a call
- * subject.
- */
- private boolean mIsCallSubjectSupported;
-
- private long mTimeAddedMs;
-
- private final LogState mLogState = new LogState();
-
- /**
- * Used only to create mock calls for testing
- */
- @NeededForTesting
- Call(int state) {
- mTelecomCall = null;
- mLatencyReport = new LatencyReport();
- mId = ID_PREFIX + Integer.toString(sIdCounter++);
- setState(state);
- }
-
- /**
- * Creates a new instance of a {@link Call}. Registers a callback for
- * {@link android.telecom.Call} events.
- */
- public Call(android.telecom.Call telecomCall, LatencyReport latencyReport) {
- this(telecomCall, latencyReport, true /* registerCallback */);
- }
-
- /**
- * Creates a new instance of a {@link Call}. Optionally registers a callback for
- * {@link android.telecom.Call} events.
- *
- * Intended for use when creating a {@link Call} instance for use with the
- * {@link ContactInfoCache}, where we do not want to register callbacks for the new call.
- */
- public Call(android.telecom.Call telecomCall, LatencyReport latencyReport,
- boolean registerCallback) {
- mTelecomCall = telecomCall;
- mLatencyReport = latencyReport;
- mId = ID_PREFIX + Integer.toString(sIdCounter++);
-
- updateFromTelecomCall(registerCallback);
-
- if (registerCallback) {
- mTelecomCall.registerCallback(mTelecomCallCallback);
- }
-
- mTimeAddedMs = System.currentTimeMillis();
- }
-
- public android.telecom.Call getTelecomCall() {
- return mTelecomCall;
- }
-
- /**
- * @return video settings of the call, null if the call is not a video call.
- * @see VideoProfile
- */
- public VideoSettings getVideoSettings() {
- return mVideoSettings;
- }
-
- private void update() {
- Trace.beginSection("Update");
- int oldState = getState();
- // We want to potentially register a video call callback here.
- updateFromTelecomCall(true /* registerCallback */);
- if (oldState != getState() && getState() == Call.State.DISCONNECTED) {
- CallList.getInstance().onDisconnect(this);
- } else {
- CallList.getInstance().onUpdate(this);
- }
- Trace.endSection();
- }
-
- private void updateFromTelecomCall(boolean registerCallback) {
- Log.d(this, "updateFromTelecomCall: " + mTelecomCall.toString());
- final int translatedState = translateState(mTelecomCall.getState());
- if (mState != State.BLOCKED) {
- setState(translatedState);
- setDisconnectCause(mTelecomCall.getDetails().getDisconnectCause());
- maybeCancelVideoUpgrade(mTelecomCall.getDetails().getVideoState());
- }
-
- if (registerCallback && mTelecomCall.getVideoCall() != null) {
- if (mVideoCallCallback == null) {
- mVideoCallCallback = new InCallVideoCallCallback(this);
- }
- mTelecomCall.getVideoCall().registerCallback(mVideoCallCallback);
- mIsVideoCallCallbackRegistered = true;
- }
-
- mChildCallIds.clear();
- final int numChildCalls = mTelecomCall.getChildren().size();
- for (int i = 0; i < numChildCalls; i++) {
- mChildCallIds.add(
- CallList.getInstance().getCallByTelecomCall(
- mTelecomCall.getChildren().get(i)).getId());
- }
-
- // The number of conferenced calls can change over the course of the call, so use the
- // maximum number of conferenced child calls as the metric for conference call usage.
- mLogState.conferencedCalls = Math.max(numChildCalls, mLogState.conferencedCalls);
-
- updateFromCallExtras(mTelecomCall.getDetails().getExtras());
-
- // If the handle of the call has changed, update state for the call determining if it is an
- // emergency call.
- Uri newHandle = mTelecomCall.getDetails().getHandle();
- if (!Objects.equals(mHandle, newHandle)) {
- mHandle = newHandle;
- updateEmergencyCallState();
- }
-
- // If the phone account handle of the call is set, cache capability bit indicating whether
- // the phone account supports call subjects.
- PhoneAccountHandle newPhoneAccountHandle = mTelecomCall.getDetails().getAccountHandle();
- if (!Objects.equals(mPhoneAccountHandle, newPhoneAccountHandle)) {
- mPhoneAccountHandle = newPhoneAccountHandle;
-
- if (mPhoneAccountHandle != null) {
- TelecomManager mgr = InCallPresenter.getInstance().getTelecomManager();
- PhoneAccount phoneAccount =
- TelecomManagerCompat.getPhoneAccount(mgr, mPhoneAccountHandle);
- if (phoneAccount != null) {
- mIsCallSubjectSupported = phoneAccount.hasCapabilities(
- PhoneAccount.CAPABILITY_CALL_SUBJECT);
- }
- }
- }
- }
-
- /**
- * Tests corruption of the {@code callExtras} bundle by calling {@link
- * Bundle#containsKey(String)}. If the bundle is corrupted a {@link IllegalArgumentException}
- * will be thrown and caught by this function.
- *
- * @param callExtras the bundle to verify
- * @returns {@code true} if the bundle is corrupted, {@code false} otherwise.
- */
- protected boolean areCallExtrasCorrupted(Bundle callExtras) {
- /**
- * There's currently a bug in Telephony service (b/25613098) that could corrupt the
- * extras bundle, resulting in a IllegalArgumentException while validating data under
- * {@link Bundle#containsKey(String)}.
- */
- try {
- callExtras.containsKey(Connection.EXTRA_CHILD_ADDRESS);
- return false;
- } catch (IllegalArgumentException e) {
- Log.e(this, "CallExtras is corrupted, ignoring exception", e);
- return true;
- }
- }
-
- protected void updateFromCallExtras(Bundle callExtras) {
- if (callExtras == null || areCallExtrasCorrupted(callExtras)) {
- /**
- * If the bundle is corrupted, abandon information update as a work around. These are
- * not critical for the dialer to function.
- */
- return;
- }
- // Check for a change in the child address and notify any listeners.
- if (callExtras.containsKey(Connection.EXTRA_CHILD_ADDRESS)) {
- String childNumber = callExtras.getString(Connection.EXTRA_CHILD_ADDRESS);
- if (!Objects.equals(childNumber, mChildNumber)) {
- mChildNumber = childNumber;
- CallList.getInstance().onChildNumberChange(this);
- }
- }
-
- // Last forwarded number comes in as an array of strings. We want to choose the
- // last item in the array. The forwarding numbers arrive independently of when the
- // call is originally set up, so we need to notify the the UI of the change.
- if (callExtras.containsKey(Connection.EXTRA_LAST_FORWARDED_NUMBER)) {
- ArrayList lastForwardedNumbers =
- callExtras.getStringArrayList(Connection.EXTRA_LAST_FORWARDED_NUMBER);
-
- if (lastForwardedNumbers != null) {
- String lastForwardedNumber = null;
- if (!lastForwardedNumbers.isEmpty()) {
- lastForwardedNumber = lastForwardedNumbers.get(
- lastForwardedNumbers.size() - 1);
- }
-
- if (!Objects.equals(lastForwardedNumber, mLastForwardedNumber)) {
- mLastForwardedNumber = lastForwardedNumber;
- CallList.getInstance().onLastForwardedNumberChange(this);
- }
- }
- }
-
- // Call subject is present in the extras at the start of call, so we do not need to
- // notify any other listeners of this.
- if (callExtras.containsKey(Connection.EXTRA_CALL_SUBJECT)) {
- String callSubject = callExtras.getString(Connection.EXTRA_CALL_SUBJECT);
- if (!Objects.equals(mCallSubject, callSubject)) {
- mCallSubject = callSubject;
- }
- }
- }
-
- /**
- * Determines if a received upgrade to video request should be cancelled. This can happen if
- * another InCall UI responds to the upgrade to video request.
- *
- * @param newVideoState The new video state.
- */
- private void maybeCancelVideoUpgrade(int newVideoState) {
- boolean isVideoStateChanged = mVideoState != newVideoState;
-
- if (mSessionModificationState == SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST
- && isVideoStateChanged) {
-
- Log.v(this, "maybeCancelVideoUpgrade : cancelling upgrade notification");
- setSessionModificationState(SessionModificationState.NO_REQUEST);
- }
- mVideoState = newVideoState;
- }
- private static int translateState(int state) {
- switch (state) {
- case android.telecom.Call.STATE_NEW:
- case android.telecom.Call.STATE_CONNECTING:
- return Call.State.CONNECTING;
- case android.telecom.Call.STATE_SELECT_PHONE_ACCOUNT:
- return Call.State.SELECT_PHONE_ACCOUNT;
- case android.telecom.Call.STATE_DIALING:
- return Call.State.DIALING;
- case android.telecom.Call.STATE_RINGING:
- return Call.State.INCOMING;
- case android.telecom.Call.STATE_ACTIVE:
- return Call.State.ACTIVE;
- case android.telecom.Call.STATE_HOLDING:
- return Call.State.ONHOLD;
- case android.telecom.Call.STATE_DISCONNECTED:
- return Call.State.DISCONNECTED;
- case android.telecom.Call.STATE_DISCONNECTING:
- return Call.State.DISCONNECTING;
- default:
- return Call.State.INVALID;
- }
- }
-
- public String getId() {
- return mId;
- }
-
- public long getTimeAddedMs() {
- return mTimeAddedMs;
- }
-
- public String getNumber() {
- return TelecomCallUtil.getNumber(mTelecomCall);
- }
-
- public void blockCall() {
- mTelecomCall.reject(false, null);
- setState(State.BLOCKED);
- }
-
- public Uri getHandle() {
- return mTelecomCall == null ? null : mTelecomCall.getDetails().getHandle();
- }
-
- public boolean isEmergencyCall() {
- return mIsEmergencyCall;
- }
-
- public int getState() {
- if (mTelecomCall != null && mTelecomCall.getParent() != null) {
- return State.CONFERENCED;
- } else {
- return mState;
- }
- }
-
- public void setState(int state) {
- mState = state;
- if (mState == State.INCOMING) {
- mLogState.isIncoming = true;
- } else if (mState == State.DISCONNECTED) {
- mLogState.duration = getConnectTimeMillis() == 0 ?
- 0: System.currentTimeMillis() - getConnectTimeMillis();
- }
- }
-
- public int getNumberPresentation() {
- return mTelecomCall == null ? null : mTelecomCall.getDetails().getHandlePresentation();
- }
-
- public int getCnapNamePresentation() {
- return mTelecomCall == null ? null
- : mTelecomCall.getDetails().getCallerDisplayNamePresentation();
- }
-
- public String getCnapName() {
- return mTelecomCall == null ? null
- : getTelecomCall().getDetails().getCallerDisplayName();
- }
-
- public Bundle getIntentExtras() {
- return mTelecomCall.getDetails().getIntentExtras();
- }
-
- public Bundle getExtras() {
- return mTelecomCall == null ? null : mTelecomCall.getDetails().getExtras();
- }
-
- /**
- * @return The child number for the call, or {@code null} if none specified.
- */
- public String getChildNumber() {
- return mChildNumber;
- }
-
- /**
- * @return The last forwarded number for the call, or {@code null} if none specified.
- */
- public String getLastForwardedNumber() {
- return mLastForwardedNumber;
- }
-
- /**
- * @return The call subject, or {@code null} if none specified.
- */
- public String getCallSubject() {
- return mCallSubject;
- }
-
- /**
- * @return {@code true} if the call's phone account supports call subjects, {@code false}
- * otherwise.
- */
- public boolean isCallSubjectSupported() {
- return mIsCallSubjectSupported;
- }
-
- /** Returns call disconnect cause, defined by {@link DisconnectCause}. */
- public DisconnectCause getDisconnectCause() {
- if (mState == State.DISCONNECTED || mState == State.IDLE) {
- return mDisconnectCause;
- }
-
- return new DisconnectCause(DisconnectCause.UNKNOWN);
- }
-
- public void setDisconnectCause(DisconnectCause disconnectCause) {
- mDisconnectCause = disconnectCause;
- mLogState.disconnectCause = mDisconnectCause;
- }
-
- /** Returns the possible text message responses. */
- public List getCannedSmsResponses() {
- return mTelecomCall.getCannedTextResponses();
- }
-
- /** Checks if the call supports the given set of capabilities supplied as a bit mask. */
- public boolean can(int capabilities) {
- int supportedCapabilities = mTelecomCall.getDetails().getCallCapabilities();
-
- if ((capabilities & android.telecom.Call.Details.CAPABILITY_MERGE_CONFERENCE) != 0) {
- // We allow you to merge if the capabilities allow it or if it is a call with
- // conferenceable calls.
- if (mTelecomCall.getConferenceableCalls().isEmpty() &&
- ((android.telecom.Call.Details.CAPABILITY_MERGE_CONFERENCE
- & supportedCapabilities) == 0)) {
- // Cannot merge calls if there are no calls to merge with.
- return false;
- }
- capabilities &= ~android.telecom.Call.Details.CAPABILITY_MERGE_CONFERENCE;
- }
- return (capabilities == (capabilities & mTelecomCall.getDetails().getCallCapabilities()));
- }
-
- public boolean hasProperty(int property) {
- return mTelecomCall.getDetails().hasProperty(property);
- }
-
- /** Gets the time when the call first became active. */
- public long getConnectTimeMillis() {
- return mTelecomCall.getDetails().getConnectTimeMillis();
- }
-
- public boolean isConferenceCall() {
- return hasProperty(android.telecom.Call.Details.PROPERTY_CONFERENCE);
- }
-
- public GatewayInfo getGatewayInfo() {
- return mTelecomCall == null ? null : mTelecomCall.getDetails().getGatewayInfo();
- }
-
- public PhoneAccountHandle getAccountHandle() {
- return mTelecomCall == null ? null : mTelecomCall.getDetails().getAccountHandle();
- }
-
- /**
- * @return The {@link VideoCall} instance associated with the {@link android.telecom.Call}.
- * Will return {@code null} until {@link #updateFromTelecomCall()} has registered a valid
- * callback on the {@link VideoCall}.
- */
- public VideoCall getVideoCall() {
- return mTelecomCall == null || !mIsVideoCallCallbackRegistered ? null
- : mTelecomCall.getVideoCall();
- }
-
- public List getChildCallIds() {
- return mChildCallIds;
- }
-
- public String getParentId() {
- android.telecom.Call parentCall = mTelecomCall.getParent();
- if (parentCall != null) {
- return CallList.getInstance().getCallByTelecomCall(parentCall).getId();
- }
- return null;
- }
-
- public int getVideoState() {
- return mTelecomCall.getDetails().getVideoState();
- }
-
- public boolean isVideoCall(Context context) {
- return CallUtil.isVideoEnabled(context) &&
- VideoUtils.isVideoCall(getVideoState());
- }
-
- /**
- * Handles incoming session modification requests. Stores the pending video request and sets
- * the session modification state to
- * {@link SessionModificationState#RECEIVED_UPGRADE_TO_VIDEO_REQUEST} so that we can keep track
- * of the fact the request was received. Only upgrade requests require user confirmation and
- * will be handled by this method. The remote user can turn off their own camera without
- * confirmation.
- *
- * @param videoState The requested video state.
- */
- public void setRequestedVideoState(int videoState) {
- Log.d(this, "setRequestedVideoState - video state= " + videoState);
- if (videoState == getVideoState()) {
- mSessionModificationState = Call.SessionModificationState.NO_REQUEST;
- Log.w(this,"setRequestedVideoState - Clearing session modification state");
- return;
- }
-
- mSessionModificationState = Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST;
- mRequestedVideoState = videoState;
- CallList.getInstance().onUpgradeToVideo(this);
-
- Log.d(this, "setRequestedVideoState - mSessionModificationState="
- + mSessionModificationState + " video state= " + videoState);
- update();
- }
-
- /**
- * Set the session modification state. Used to keep track of pending video session modification
- * operations and to inform listeners of these changes.
- *
- * @param state the new session modification state.
- */
- public void setSessionModificationState(int state) {
- boolean hasChanged = mSessionModificationState != state;
- mSessionModificationState = state;
- Log.d(this, "setSessionModificationState " + state + " mSessionModificationState="
- + mSessionModificationState);
- if (hasChanged) {
- CallList.getInstance().onSessionModificationStateChange(this, state);
- }
- }
-
- /**
- * Determines if the call handle is an emergency number or not and caches the result to avoid
- * repeated calls to isEmergencyNumber.
- */
- private void updateEmergencyCallState() {
- mIsEmergencyCall = TelecomCallUtil.isEmergencyCall(mTelecomCall);
- }
-
- /**
- * Gets the video state which was requested via a session modification request.
- *
- * @return The video state.
- */
- public int getRequestedVideoState() {
- return mRequestedVideoState;
- }
-
- public static boolean areSame(Call call1, Call call2) {
- if (call1 == null && call2 == null) {
- return true;
- } else if (call1 == null || call2 == null) {
- return false;
- }
-
- // otherwise compare call Ids
- return call1.getId().equals(call2.getId());
- }
-
- public static boolean areSameNumber(Call call1, Call call2) {
- if (call1 == null && call2 == null) {
- return true;
- } else if (call1 == null || call2 == null) {
- return false;
- }
-
- // otherwise compare call Numbers
- return TextUtils.equals(call1.getNumber(), call2.getNumber());
- }
-
- /**
- * Gets the current video session modification state.
- *
- * @return The session modification state.
- */
- public int getSessionModificationState() {
- return mSessionModificationState;
- }
-
- public LogState getLogState() {
- return mLogState;
- }
-
- /**
- * Determines if the call is an external call.
- *
- * An external call is one which does not exist locally for the
- * {@link android.telecom.ConnectionService} it is associated with.
- *
- * External calls are only supported in N and higher.
- *
- * @return {@code true} if the call is an external call, {@code false} otherwise.
- */
- public boolean isExternalCall() {
- return CompatUtils.isNCompatible() &&
- hasProperty(CallSdkCompat.Details.PROPERTY_IS_EXTERNAL_CALL);
- }
-
- /**
- * Determines if the external call is pullable.
- *
- * An external call is one which does not exist locally for the
- * {@link android.telecom.ConnectionService} it is associated with. An external call may be
- * "pullable", which means that the user can request it be transferred to the current device.
- *
- * External calls are only supported in N and higher.
- *
- * @return {@code true} if the call is an external call, {@code false} otherwise.
- */
- public boolean isPullableExternalCall() {
- return CompatUtils.isNCompatible() &&
- (mTelecomCall.getDetails().getCallCapabilities()
- & CallSdkCompat.Details.CAPABILITY_CAN_PULL_CALL)
- == CallSdkCompat.Details.CAPABILITY_CAN_PULL_CALL;
- }
-
- /**
- * Logging utility methods
- */
- public void logCallInitiationType() {
- if (isExternalCall()) {
- return;
- }
-
- if (getState() == State.INCOMING) {
- getLogState().callInitiationMethod = LogState.INITIATION_INCOMING;
- } else if (getIntentExtras() != null) {
- getLogState().callInitiationMethod =
- getIntentExtras().getInt(IntentUtil.EXTRA_CALL_INITIATION_TYPE,
- LogState.INITIATION_EXTERNAL);
- }
- }
-
- @Override
- public String toString() {
- if (mTelecomCall == null) {
- // This should happen only in testing since otherwise we would never have a null
- // Telecom call.
- return String.valueOf(mId);
- }
-
- return String.format(Locale.US, "[%s, %s, %s, %s, children:%s, parent:%s, " +
- "conferenceable:%s, videoState:%s, mSessionModificationState:%d, VideoSettings:%s]",
- mId,
- State.toString(getState()),
- Details.capabilitiesToString(mTelecomCall.getDetails().getCallCapabilities()),
- Details.propertiesToString(mTelecomCall.getDetails().getCallProperties()),
- mChildCallIds,
- getParentId(),
- this.mTelecomCall.getConferenceableCalls(),
- VideoProfile.videoStateToString(mTelecomCall.getDetails().getVideoState()),
- mSessionModificationState,
- getVideoSettings());
- }
-
- public String toSimpleString() {
- return super.toString();
- }
-
- public void setCallHistoryStatus(@CallHistoryStatus int callHistoryStatus) {
- mCallHistoryStatus = callHistoryStatus;
- }
-
- @CallHistoryStatus
- public int getCallHistoryStatus() {
- return mCallHistoryStatus;
- }
-
- public void setSpam(boolean isSpam) {
- mIsSpam = isSpam;
- }
-
- public boolean isSpam() {
- return mIsSpam;
- }
-
- public LatencyReport getLatencyReport() {
- return mLatencyReport;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallButtonFragment.java b/InCallUI/src/com/android/incallui/CallButtonFragment.java
deleted file mode 100644
index 6b633eaf3892b4ab25a557354bf0628b5db7ee7b..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallButtonFragment.java
+++ /dev/null
@@ -1,819 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_ADD_CALL;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_AUDIO;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_COUNT;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_DIALPAD;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_DOWNGRADE_TO_AUDIO;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_HOLD;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_MANAGE_VIDEO_CONFERENCE;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_MERGE;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_MUTE;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_PAUSE_VIDEO;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_SWAP;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_SWITCH_CAMERA;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_UPGRADE_TO_VIDEO;
-
-import android.content.Context;
-import android.content.res.ColorStateList;
-import android.content.res.Resources;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.GradientDrawable;
-import android.graphics.drawable.LayerDrawable;
-import android.graphics.drawable.RippleDrawable;
-import android.graphics.drawable.StateListDrawable;
-import android.os.Bundle;
-import android.telecom.CallAudioState;
-import android.util.SparseIntArray;
-import android.view.ContextThemeWrapper;
-import android.view.HapticFeedbackConstants;
-import android.view.LayoutInflater;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.CompoundButton;
-import android.widget.ImageButton;
-import android.widget.PopupMenu;
-import android.widget.PopupMenu.OnDismissListener;
-import android.widget.PopupMenu.OnMenuItemClickListener;
-
-import com.android.contacts.common.util.MaterialColorMapUtils.MaterialPalette;
-import com.android.dialer.R;
-
-/**
- * Fragment for call control buttons
- */
-public class CallButtonFragment
- extends BaseFragment
- implements CallButtonPresenter.CallButtonUi, OnMenuItemClickListener, OnDismissListener,
- View.OnClickListener {
-
- private int mButtonMaxVisible;
- // The button is currently visible in the UI
- private static final int BUTTON_VISIBLE = 1;
- // The button is hidden in the UI
- private static final int BUTTON_HIDDEN = 2;
- // The button has been collapsed into the overflow menu
- private static final int BUTTON_MENU = 3;
-
- public interface Buttons {
-
- public static final int BUTTON_AUDIO = 0;
- public static final int BUTTON_MUTE = 1;
- public static final int BUTTON_DIALPAD = 2;
- public static final int BUTTON_HOLD = 3;
- public static final int BUTTON_SWAP = 4;
- public static final int BUTTON_UPGRADE_TO_VIDEO = 5;
- public static final int BUTTON_SWITCH_CAMERA = 6;
- public static final int BUTTON_DOWNGRADE_TO_AUDIO = 7;
- public static final int BUTTON_ADD_CALL = 8;
- public static final int BUTTON_MERGE = 9;
- public static final int BUTTON_PAUSE_VIDEO = 10;
- public static final int BUTTON_MANAGE_VIDEO_CONFERENCE = 11;
- public static final int BUTTON_COUNT = 12;
- }
-
- private SparseIntArray mButtonVisibilityMap = new SparseIntArray(BUTTON_COUNT);
-
- private CompoundButton mAudioButton;
- private CompoundButton mMuteButton;
- private CompoundButton mShowDialpadButton;
- private CompoundButton mHoldButton;
- private ImageButton mSwapButton;
- private ImageButton mChangeToVideoButton;
- private ImageButton mChangeToVoiceButton;
- private CompoundButton mSwitchCameraButton;
- private ImageButton mAddCallButton;
- private ImageButton mMergeButton;
- private CompoundButton mPauseVideoButton;
- private ImageButton mOverflowButton;
- private ImageButton mManageVideoCallConferenceButton;
-
- private PopupMenu mAudioModePopup;
- private boolean mAudioModePopupVisible;
- private PopupMenu mOverflowPopup;
-
- private int mPrevAudioMode = 0;
-
- // Constants for Drawable.setAlpha()
- private static final int HIDDEN = 0;
- private static final int VISIBLE = 255;
-
- private boolean mIsEnabled;
- private MaterialPalette mCurrentThemeColors;
-
- @Override
- public CallButtonPresenter createPresenter() {
- // TODO: find a cleaner way to include audio mode provider than having a singleton instance.
- return new CallButtonPresenter();
- }
-
- @Override
- public CallButtonPresenter.CallButtonUi getUi() {
- return this;
- }
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- for (int i = 0; i < BUTTON_COUNT; i++) {
- mButtonVisibilityMap.put(i, BUTTON_HIDDEN);
- }
-
- mButtonMaxVisible = getResources().getInteger(R.integer.call_card_max_buttons);
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- final View parent = inflater.inflate(R.layout.call_button_fragment, container, false);
-
- mAudioButton = (CompoundButton) parent.findViewById(R.id.audioButton);
- mAudioButton.setOnClickListener(this);
- mMuteButton = (CompoundButton) parent.findViewById(R.id.muteButton);
- mMuteButton.setOnClickListener(this);
- mShowDialpadButton = (CompoundButton) parent.findViewById(R.id.dialpadButton);
- mShowDialpadButton.setOnClickListener(this);
- mHoldButton = (CompoundButton) parent.findViewById(R.id.holdButton);
- mHoldButton.setOnClickListener(this);
- mSwapButton = (ImageButton) parent.findViewById(R.id.swapButton);
- mSwapButton.setOnClickListener(this);
- mChangeToVideoButton = (ImageButton) parent.findViewById(R.id.changeToVideoButton);
- mChangeToVideoButton.setOnClickListener(this);
- mChangeToVoiceButton = (ImageButton) parent.findViewById(R.id.changeToVoiceButton);
- mChangeToVoiceButton.setOnClickListener(this);
- mSwitchCameraButton = (CompoundButton) parent.findViewById(R.id.switchCameraButton);
- mSwitchCameraButton.setOnClickListener(this);
- mAddCallButton = (ImageButton) parent.findViewById(R.id.addButton);
- mAddCallButton.setOnClickListener(this);
- mMergeButton = (ImageButton) parent.findViewById(R.id.mergeButton);
- mMergeButton.setOnClickListener(this);
- mPauseVideoButton = (CompoundButton) parent.findViewById(R.id.pauseVideoButton);
- mPauseVideoButton.setOnClickListener(this);
- mOverflowButton = (ImageButton) parent.findViewById(R.id.overflowButton);
- mOverflowButton.setOnClickListener(this);
- mManageVideoCallConferenceButton = (ImageButton) parent.findViewById(
- R.id.manageVideoCallConferenceButton);
- mManageVideoCallConferenceButton.setOnClickListener(this);
- return parent;
- }
-
- @Override
- public void onActivityCreated(Bundle savedInstanceState) {
- super.onActivityCreated(savedInstanceState);
-
- // set the buttons
- updateAudioButtons();
- }
-
- @Override
- public void onResume() {
- if (getPresenter() != null) {
- getPresenter().refreshMuteState();
- }
- super.onResume();
-
- updateColors();
- }
-
- @Override
- public void onClick(View view) {
- int id = view.getId();
- Log.d(this, "onClick(View " + view + ", id " + id + ")...");
-
- if (id == R.id.audioButton) {
- onAudioButtonClicked();
- } else if (id == R.id.addButton) {
- getPresenter().addCallClicked();
- } else if (id == R.id.muteButton) {
- getPresenter().muteClicked(!mMuteButton.isSelected());
- } else if (id == R.id.mergeButton) {
- getPresenter().mergeClicked();
- mMergeButton.setEnabled(false);
- } else if (id == R.id.holdButton) {
- getPresenter().holdClicked(!mHoldButton.isSelected());
- } else if (id == R.id.swapButton) {
- getPresenter().swapClicked();
- } else if (id == R.id.dialpadButton) {
- getPresenter().showDialpadClicked(!mShowDialpadButton.isSelected());
- } else if (id == R.id.changeToVideoButton) {
- getPresenter().changeToVideoClicked();
- } else if (id == R.id.changeToVoiceButton) {
- getPresenter().changeToVoiceClicked();
- } else if (id == R.id.switchCameraButton) {
- getPresenter().switchCameraClicked(
- mSwitchCameraButton.isSelected() /* useFrontFacingCamera */);
- } else if (id == R.id.pauseVideoButton) {
- getPresenter().pauseVideoClicked(
- !mPauseVideoButton.isSelected() /* pause */);
- } else if (id == R.id.overflowButton) {
- if (mOverflowPopup != null) {
- mOverflowPopup.show();
- }
- } else if (id == R.id.manageVideoCallConferenceButton) {
- onManageVideoCallConferenceClicked();
- } else {
- Log.wtf(this, "onClick: unexpected");
- return;
- }
-
- view.performHapticFeedback(
- HapticFeedbackConstants.VIRTUAL_KEY,
- HapticFeedbackConstants.FLAG_IGNORE_GLOBAL_SETTING);
- }
-
- public void updateColors() {
- MaterialPalette themeColors = InCallPresenter.getInstance().getThemeColors();
-
- if (mCurrentThemeColors != null && mCurrentThemeColors.equals(themeColors)) {
- return;
- }
-
- View[] compoundButtons = {
- mAudioButton,
- mMuteButton,
- mShowDialpadButton,
- mHoldButton,
- mSwitchCameraButton,
- mPauseVideoButton
- };
-
- for (View button : compoundButtons) {
- final LayerDrawable layers = (LayerDrawable) button.getBackground();
- final RippleDrawable btnCompoundDrawable = compoundBackgroundDrawable(themeColors);
- layers.setDrawableByLayerId(R.id.compoundBackgroundItem, btnCompoundDrawable);
- }
-
- ImageButton[] normalButtons = {
- mSwapButton,
- mChangeToVideoButton,
- mChangeToVoiceButton,
- mAddCallButton,
- mMergeButton,
- mOverflowButton
- };
-
- for (ImageButton button : normalButtons) {
- final LayerDrawable layers = (LayerDrawable) button.getBackground();
- final RippleDrawable btnDrawable = backgroundDrawable(themeColors);
- layers.setDrawableByLayerId(R.id.backgroundItem, btnDrawable);
- }
-
- mCurrentThemeColors = themeColors;
- }
-
- /**
- * Generate a RippleDrawable which will be the background for a compound button, i.e.
- * a button with pressed and unpressed states. The unpressed state will be the same color
- * as the rest of the call card, the pressed state will be the dark version of that color.
- */
- private RippleDrawable compoundBackgroundDrawable(MaterialPalette palette) {
- Resources res = getResources();
- ColorStateList rippleColor =
- ColorStateList.valueOf(res.getColor(R.color.incall_accent_color));
-
- StateListDrawable stateListDrawable = new StateListDrawable();
- addSelectedAndFocused(res, stateListDrawable);
- addFocused(res, stateListDrawable);
- addSelected(res, stateListDrawable, palette);
- addUnselected(res, stateListDrawable, palette);
-
- return new RippleDrawable(rippleColor, stateListDrawable, null);
- }
-
- /**
- * Generate a RippleDrawable which will be the background of a button to ensure it
- * is the same color as the rest of the call card.
- */
- private RippleDrawable backgroundDrawable(MaterialPalette palette) {
- Resources res = getResources();
- ColorStateList rippleColor =
- ColorStateList.valueOf(res.getColor(R.color.incall_accent_color));
-
- StateListDrawable stateListDrawable = new StateListDrawable();
- addFocused(res, stateListDrawable);
- addUnselected(res, stateListDrawable, palette);
-
- return new RippleDrawable(rippleColor, stateListDrawable, null);
- }
-
- // state_selected and state_focused
- private void addSelectedAndFocused(Resources res, StateListDrawable drawable) {
- int[] selectedAndFocused = {android.R.attr.state_selected, android.R.attr.state_focused};
- Drawable selectedAndFocusedDrawable = res.getDrawable(R.drawable.btn_selected_focused);
- drawable.addState(selectedAndFocused, selectedAndFocusedDrawable);
- }
-
- // state_focused
- private void addFocused(Resources res, StateListDrawable drawable) {
- int[] focused = {android.R.attr.state_focused};
- Drawable focusedDrawable = res.getDrawable(R.drawable.btn_unselected_focused);
- drawable.addState(focused, focusedDrawable);
- }
-
- // state_selected
- private void addSelected(Resources res, StateListDrawable drawable, MaterialPalette palette) {
- int[] selected = {android.R.attr.state_selected};
- LayerDrawable selectedDrawable = (LayerDrawable) res.getDrawable(R.drawable.btn_selected);
- ((GradientDrawable) selectedDrawable.getDrawable(0)).setColor(palette.mSecondaryColor);
- drawable.addState(selected, selectedDrawable);
- }
-
- // default
- private void addUnselected(Resources res, StateListDrawable drawable, MaterialPalette palette) {
- LayerDrawable unselectedDrawable =
- (LayerDrawable) res.getDrawable(R.drawable.btn_unselected);
- ((GradientDrawable) unselectedDrawable.getDrawable(0)).setColor(palette.mPrimaryColor);
- drawable.addState(new int[0], unselectedDrawable);
- }
-
- @Override
- public void setEnabled(boolean isEnabled) {
- mIsEnabled = isEnabled;
-
- mAudioButton.setEnabled(isEnabled);
- mMuteButton.setEnabled(isEnabled);
- mShowDialpadButton.setEnabled(isEnabled);
- mHoldButton.setEnabled(isEnabled);
- mSwapButton.setEnabled(isEnabled);
- mChangeToVideoButton.setEnabled(isEnabled);
- mChangeToVoiceButton.setEnabled(isEnabled);
- mSwitchCameraButton.setEnabled(isEnabled);
- mAddCallButton.setEnabled(isEnabled);
- mMergeButton.setEnabled(isEnabled);
- mPauseVideoButton.setEnabled(isEnabled);
- mOverflowButton.setEnabled(isEnabled);
- mManageVideoCallConferenceButton.setEnabled(isEnabled);
- }
-
- @Override
- public void showButton(int buttonId, boolean show) {
- mButtonVisibilityMap.put(buttonId, show ? BUTTON_VISIBLE : BUTTON_HIDDEN);
- }
-
- @Override
- public void enableButton(int buttonId, boolean enable) {
- final View button = getButtonById(buttonId);
- if (button != null) {
- button.setEnabled(enable);
- }
- }
-
- private View getButtonById(int id) {
- if (id == BUTTON_AUDIO) {
- return mAudioButton;
- } else if (id == BUTTON_MUTE) {
- return mMuteButton;
- } else if (id == BUTTON_DIALPAD) {
- return mShowDialpadButton;
- } else if (id == BUTTON_HOLD) {
- return mHoldButton;
- } else if (id == BUTTON_SWAP) {
- return mSwapButton;
- } else if (id == BUTTON_UPGRADE_TO_VIDEO) {
- return mChangeToVideoButton;
- } else if (id == BUTTON_DOWNGRADE_TO_AUDIO) {
- return mChangeToVoiceButton;
- } else if (id == BUTTON_SWITCH_CAMERA) {
- return mSwitchCameraButton;
- } else if (id == BUTTON_ADD_CALL) {
- return mAddCallButton;
- } else if (id == BUTTON_MERGE) {
- return mMergeButton;
- } else if (id == BUTTON_PAUSE_VIDEO) {
- return mPauseVideoButton;
- } else if (id == BUTTON_MANAGE_VIDEO_CONFERENCE) {
- return mManageVideoCallConferenceButton;
- } else {
- Log.w(this, "Invalid button id");
- return null;
- }
- }
-
- @Override
- public void setHold(boolean value) {
- if (mHoldButton.isSelected() != value) {
- mHoldButton.setSelected(value);
- mHoldButton.setContentDescription(getContext().getString(
- value ? R.string.onscreenHoldText_selected
- : R.string.onscreenHoldText_unselected));
- }
- }
-
- @Override
- public void setCameraSwitched(boolean isBackFacingCamera) {
- mSwitchCameraButton.setSelected(isBackFacingCamera);
- }
-
- @Override
- public void setVideoPaused(boolean isVideoPaused) {
- mPauseVideoButton.setSelected(isVideoPaused);
-
- if (isVideoPaused) {
- mPauseVideoButton.setContentDescription(getText(R.string.onscreenTurnOnCameraText));
- } else {
- mPauseVideoButton.setContentDescription(getText(R.string.onscreenTurnOffCameraText));
- }
- }
-
- @Override
- public void setMute(boolean value) {
- if (mMuteButton.isSelected() != value) {
- mMuteButton.setSelected(value);
- mMuteButton.setContentDescription(getContext().getString(
- value ? R.string.onscreenMuteText_selected
- : R.string.onscreenMuteText_unselected));
- }
- }
-
- private void addToOverflowMenu(int id, View button, PopupMenu menu) {
- button.setVisibility(View.GONE);
- menu.getMenu().add(Menu.NONE, id, Menu.NONE, button.getContentDescription());
- mButtonVisibilityMap.put(id, BUTTON_MENU);
- }
-
- private PopupMenu getPopupMenu() {
- return new PopupMenu(new ContextThemeWrapper(getActivity(), R.style.InCallPopupMenuStyle),
- mOverflowButton);
- }
-
- /**
- * Iterates through the list of buttons and toggles their visibility depending on the
- * setting configured by the CallButtonPresenter. If there are more visible buttons than
- * the allowed maximum, the excess buttons are collapsed into a single overflow menu.
- */
- @Override
- public void updateButtonStates() {
- View prevVisibleButton = null;
- int prevVisibleId = -1;
- PopupMenu menu = null;
- int visibleCount = 0;
- for (int i = 0; i < BUTTON_COUNT; i++) {
- final int visibility = mButtonVisibilityMap.get(i);
- final View button = getButtonById(i);
- if (visibility == BUTTON_VISIBLE) {
- visibleCount++;
- if (visibleCount <= mButtonMaxVisible) {
- button.setVisibility(View.VISIBLE);
- prevVisibleButton = button;
- prevVisibleId = i;
- } else {
- if (menu == null) {
- menu = getPopupMenu();
- }
- // Collapse the current button into the overflow menu. If is the first visible
- // button that exceeds the threshold, also collapse the previous visible button
- // so that the total number of visible buttons will never exceed the threshold.
- if (prevVisibleButton != null) {
- addToOverflowMenu(prevVisibleId, prevVisibleButton, menu);
- prevVisibleButton = null;
- prevVisibleId = -1;
- }
- addToOverflowMenu(i, button, menu);
- }
- } else if (visibility == BUTTON_HIDDEN) {
- button.setVisibility(View.GONE);
- }
- }
-
- mOverflowButton.setVisibility(menu != null ? View.VISIBLE : View.GONE);
- if (menu != null) {
- mOverflowPopup = menu;
- mOverflowPopup.setOnMenuItemClickListener(new OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- final int id = item.getItemId();
- getButtonById(id).performClick();
- return true;
- }
- });
- }
- }
-
- @Override
- public void setAudio(int mode) {
- updateAudioButtons();
- refreshAudioModePopup();
-
- if (mPrevAudioMode != mode) {
- updateAudioButtonContentDescription(mode);
- mPrevAudioMode = mode;
- }
- }
-
- @Override
- public void setSupportedAudio(int modeMask) {
- updateAudioButtons();
- refreshAudioModePopup();
- }
-
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- Log.d(this, "- onMenuItemClick: " + item);
- Log.d(this, " id: " + item.getItemId());
- Log.d(this, " title: '" + item.getTitle() + "'");
-
- int mode = CallAudioState.ROUTE_WIRED_OR_EARPIECE;
- int resId = item.getItemId();
-
- if (resId == R.id.audio_mode_speaker) {
- mode = CallAudioState.ROUTE_SPEAKER;
- } else if (resId == R.id.audio_mode_earpiece || resId == R.id.audio_mode_wired_headset) {
- // InCallCallAudioState.ROUTE_EARPIECE means either the handset earpiece,
- // or the wired headset (if connected.)
- mode = CallAudioState.ROUTE_WIRED_OR_EARPIECE;
- } else if (resId == R.id.audio_mode_bluetooth) {
- mode = CallAudioState.ROUTE_BLUETOOTH;
- } else {
- Log.e(this, "onMenuItemClick: unexpected View ID " + item.getItemId()
- + " (MenuItem = '" + item + "')");
- }
-
- getPresenter().setAudioMode(mode);
-
- return true;
- }
-
- // PopupMenu.OnDismissListener implementation; see showAudioModePopup().
- // This gets called when the PopupMenu gets dismissed for *any* reason, like
- // the user tapping outside its bounds, or pressing Back, or selecting one
- // of the menu items.
- @Override
- public void onDismiss(PopupMenu menu) {
- Log.d(this, "- onDismiss: " + menu);
- mAudioModePopupVisible = false;
- updateAudioButtons();
- }
-
- /**
- * Checks for supporting modes. If bluetooth is supported, it uses the audio
- * pop up menu. Otherwise, it toggles the speakerphone.
- */
- private void onAudioButtonClicked() {
- Log.d(this, "onAudioButtonClicked: " +
- CallAudioState.audioRouteToString(getPresenter().getSupportedAudio()));
-
- if (isSupported(CallAudioState.ROUTE_BLUETOOTH)) {
- showAudioModePopup();
- } else {
- getPresenter().toggleSpeakerphone();
- }
- }
-
- private void onManageVideoCallConferenceClicked() {
- Log.d(this, "onManageVideoCallConferenceClicked");
- InCallPresenter.getInstance().showConferenceCallManager(true);
- }
-
- /**
- * Refreshes the "Audio mode" popup if it's visible. This is useful
- * (for example) when a wired headset is plugged or unplugged,
- * since we need to switch back and forth between the "earpiece"
- * and "wired headset" items.
- *
- * This is safe to call even if the popup is already dismissed, or even if
- * you never called showAudioModePopup() in the first place.
- */
- public void refreshAudioModePopup() {
- if (mAudioModePopup != null && mAudioModePopupVisible) {
- // Dismiss the previous one
- mAudioModePopup.dismiss(); // safe even if already dismissed
- // And bring up a fresh PopupMenu
- showAudioModePopup();
- }
- }
-
- /**
- * Updates the audio button so that the appriopriate visual layers
- * are visible based on the supported audio formats.
- */
- private void updateAudioButtons() {
- final boolean bluetoothSupported = isSupported(CallAudioState.ROUTE_BLUETOOTH);
- final boolean speakerSupported = isSupported(CallAudioState.ROUTE_SPEAKER);
-
- boolean audioButtonEnabled = false;
- boolean audioButtonChecked = false;
- boolean showMoreIndicator = false;
-
- boolean showBluetoothIcon = false;
- boolean showSpeakerphoneIcon = false;
- boolean showHandsetIcon = false;
-
- boolean showToggleIndicator = false;
-
- if (bluetoothSupported) {
- Log.d(this, "updateAudioButtons - popup menu mode");
-
- audioButtonEnabled = true;
- audioButtonChecked = true;
- showMoreIndicator = true;
-
- // Update desired layers:
- if (isAudio(CallAudioState.ROUTE_BLUETOOTH)) {
- showBluetoothIcon = true;
- } else if (isAudio(CallAudioState.ROUTE_SPEAKER)) {
- showSpeakerphoneIcon = true;
- } else {
- showHandsetIcon = true;
- // TODO: if a wired headset is plugged in, that takes precedence
- // over the handset earpiece. If so, maybe we should show some
- // sort of "wired headset" icon here instead of the "handset
- // earpiece" icon. (Still need an asset for that, though.)
- }
-
- // The audio button is NOT a toggle in this state, so set selected to false.
- mAudioButton.setSelected(false);
- } else if (speakerSupported) {
- Log.d(this, "updateAudioButtons - speaker toggle mode");
-
- audioButtonEnabled = true;
-
- // The audio button *is* a toggle in this state, and indicated the
- // current state of the speakerphone.
- audioButtonChecked = isAudio(CallAudioState.ROUTE_SPEAKER);
- mAudioButton.setSelected(audioButtonChecked);
-
- // update desired layers:
- showToggleIndicator = true;
- showSpeakerphoneIcon = true;
- } else {
- Log.d(this, "updateAudioButtons - disabled...");
-
- // The audio button is a toggle in this state, but that's mostly
- // irrelevant since it's always disabled and unchecked.
- audioButtonEnabled = false;
- audioButtonChecked = false;
- mAudioButton.setSelected(false);
-
- // update desired layers:
- showToggleIndicator = true;
- showSpeakerphoneIcon = true;
- }
-
- // Finally, update it all!
-
- Log.v(this, "audioButtonEnabled: " + audioButtonEnabled);
- Log.v(this, "audioButtonChecked: " + audioButtonChecked);
- Log.v(this, "showMoreIndicator: " + showMoreIndicator);
- Log.v(this, "showBluetoothIcon: " + showBluetoothIcon);
- Log.v(this, "showSpeakerphoneIcon: " + showSpeakerphoneIcon);
- Log.v(this, "showHandsetIcon: " + showHandsetIcon);
-
- // Only enable the audio button if the fragment is enabled.
- mAudioButton.setEnabled(audioButtonEnabled && mIsEnabled);
- mAudioButton.setChecked(audioButtonChecked);
-
- final LayerDrawable layers = (LayerDrawable) mAudioButton.getBackground();
- Log.d(this, "'layers' drawable: " + layers);
-
- layers.findDrawableByLayerId(R.id.compoundBackgroundItem)
- .setAlpha(showToggleIndicator ? VISIBLE : HIDDEN);
-
- layers.findDrawableByLayerId(R.id.moreIndicatorItem)
- .setAlpha(showMoreIndicator ? VISIBLE : HIDDEN);
-
- layers.findDrawableByLayerId(R.id.bluetoothItem)
- .setAlpha(showBluetoothIcon ? VISIBLE : HIDDEN);
-
- layers.findDrawableByLayerId(R.id.handsetItem)
- .setAlpha(showHandsetIcon ? VISIBLE : HIDDEN);
-
- layers.findDrawableByLayerId(R.id.speakerphoneItem)
- .setAlpha(showSpeakerphoneIcon ? VISIBLE : HIDDEN);
-
- }
-
- /**
- * Update the content description of the audio button.
- */
- private void updateAudioButtonContentDescription(int mode) {
- int stringId = 0;
-
- // If bluetooth is not supported, the audio buttion will toggle, so use the label "speaker".
- // Otherwise, use the label of the currently selected audio mode.
- if (!isSupported(CallAudioState.ROUTE_BLUETOOTH)) {
- stringId = R.string.audio_mode_speaker;
- } else {
- switch (mode) {
- case CallAudioState.ROUTE_EARPIECE:
- stringId = R.string.audio_mode_earpiece;
- break;
- case CallAudioState.ROUTE_BLUETOOTH:
- stringId = R.string.audio_mode_bluetooth;
- break;
- case CallAudioState.ROUTE_WIRED_HEADSET:
- stringId = R.string.audio_mode_wired_headset;
- break;
- case CallAudioState.ROUTE_SPEAKER:
- stringId = R.string.audio_mode_speaker;
- break;
- }
- }
-
- if (stringId != 0) {
- mAudioButton.setContentDescription(getResources().getString(stringId));
- }
- }
-
- private void showAudioModePopup() {
- Log.d(this, "showAudioPopup()...");
-
- final ContextThemeWrapper contextWrapper = new ContextThemeWrapper(getActivity(),
- R.style.InCallPopupMenuStyle);
- mAudioModePopup = new PopupMenu(contextWrapper, mAudioButton /* anchorView */);
- mAudioModePopup.getMenuInflater().inflate(R.menu.incall_audio_mode_menu,
- mAudioModePopup.getMenu());
- mAudioModePopup.setOnMenuItemClickListener(this);
- mAudioModePopup.setOnDismissListener(this);
-
- final Menu menu = mAudioModePopup.getMenu();
-
- // TODO: Still need to have the "currently active" audio mode come
- // up pre-selected (or focused?) with a blue highlight. Still
- // need exact visual design, and possibly framework support for this.
- // See comments below for the exact logic.
-
- final MenuItem speakerItem = menu.findItem(R.id.audio_mode_speaker);
- speakerItem.setEnabled(isSupported(CallAudioState.ROUTE_SPEAKER));
- // TODO: Show speakerItem as initially "selected" if
- // speaker is on.
-
- // We display *either* "earpiece" or "wired headset", never both,
- // depending on whether a wired headset is physically plugged in.
- final MenuItem earpieceItem = menu.findItem(R.id.audio_mode_earpiece);
- final MenuItem wiredHeadsetItem = menu.findItem(R.id.audio_mode_wired_headset);
-
- final boolean usingHeadset = isSupported(CallAudioState.ROUTE_WIRED_HEADSET);
- earpieceItem.setVisible(!usingHeadset);
- earpieceItem.setEnabled(!usingHeadset);
- wiredHeadsetItem.setVisible(usingHeadset);
- wiredHeadsetItem.setEnabled(usingHeadset);
- // TODO: Show the above item (either earpieceItem or wiredHeadsetItem)
- // as initially "selected" if speakerOn and
- // bluetoothIndicatorOn are both false.
-
- final MenuItem bluetoothItem = menu.findItem(R.id.audio_mode_bluetooth);
- bluetoothItem.setEnabled(isSupported(CallAudioState.ROUTE_BLUETOOTH));
- // TODO: Show bluetoothItem as initially "selected" if
- // bluetoothIndicatorOn is true.
-
- mAudioModePopup.show();
-
- // Unfortunately we need to manually keep track of the popup menu's
- // visiblity, since PopupMenu doesn't have an isShowing() method like
- // Dialogs do.
- mAudioModePopupVisible = true;
- }
-
- private boolean isSupported(int mode) {
- return (mode == (getPresenter().getSupportedAudio() & mode));
- }
-
- private boolean isAudio(int mode) {
- return (mode == getPresenter().getAudioMode());
- }
-
- @Override
- public void displayDialpad(boolean value, boolean animate) {
- if (getActivity() != null && getActivity() instanceof InCallActivity) {
- boolean changed = ((InCallActivity) getActivity()).showDialpadFragment(value, animate);
- if (changed) {
- mShowDialpadButton.setSelected(value);
- mShowDialpadButton.setContentDescription(getContext().getString(
- value /* show */ ? R.string.onscreenShowDialpadText_unselected
- : R.string.onscreenShowDialpadText_selected));
- }
- }
- }
-
- @Override
- public boolean isDialpadVisible() {
- if (getActivity() != null && getActivity() instanceof InCallActivity) {
- return ((InCallActivity) getActivity()).isDialpadVisible();
- }
- return false;
- }
-
- @Override
- public Context getContext() {
- return getActivity();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallButtonPresenter.java b/InCallUI/src/com/android/incallui/CallButtonPresenter.java
deleted file mode 100644
index defafda99a2ad1c1fc876ec4c1e69bc97792d705..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallButtonPresenter.java
+++ /dev/null
@@ -1,486 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_ADD_CALL;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_AUDIO;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_DIALPAD;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_DOWNGRADE_TO_AUDIO;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_HOLD;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_MERGE;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_MUTE;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_PAUSE_VIDEO;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_SWAP;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_SWITCH_CAMERA;
-import static com.android.incallui.CallButtonFragment.Buttons.BUTTON_UPGRADE_TO_VIDEO;
-
-import android.content.Context;
-import android.os.Build;
-import android.os.Bundle;
-import android.telecom.CallAudioState;
-import android.telecom.InCallService.VideoCall;
-import android.telecom.VideoProfile;
-
-import com.android.contacts.common.compat.CallSdkCompat;
-import com.android.contacts.common.compat.SdkVersionOverride;
-import com.android.dialer.compat.UserManagerCompat;
-import com.android.incallui.AudioModeProvider.AudioModeListener;
-import com.android.incallui.InCallCameraManager.Listener;
-import com.android.incallui.InCallPresenter.CanAddCallListener;
-import com.android.incallui.InCallPresenter.InCallDetailsListener;
-import com.android.incallui.InCallPresenter.InCallState;
-import com.android.incallui.InCallPresenter.InCallStateListener;
-import com.android.incallui.InCallPresenter.IncomingCallListener;
-
-/**
- * Logic for call buttons.
- */
-public class CallButtonPresenter extends Presenter
- implements InCallStateListener, AudioModeListener, IncomingCallListener,
- InCallDetailsListener, CanAddCallListener, Listener {
-
- private static final String KEY_AUTOMATICALLY_MUTED = "incall_key_automatically_muted";
- private static final String KEY_PREVIOUS_MUTE_STATE = "incall_key_previous_mute_state";
-
- private Call mCall;
- private boolean mAutomaticallyMuted = false;
- private boolean mPreviousMuteState = false;
-
- public CallButtonPresenter() {
- }
-
- @Override
- public void onUiReady(CallButtonUi ui) {
- super.onUiReady(ui);
-
- AudioModeProvider.getInstance().addListener(this);
-
- // register for call state changes last
- final InCallPresenter inCallPresenter = InCallPresenter.getInstance();
- inCallPresenter.addListener(this);
- inCallPresenter.addIncomingCallListener(this);
- inCallPresenter.addDetailsListener(this);
- inCallPresenter.addCanAddCallListener(this);
- inCallPresenter.getInCallCameraManager().addCameraSelectionListener(this);
-
- // Update the buttons state immediately for the current call
- onStateChange(InCallState.NO_CALLS, inCallPresenter.getInCallState(),
- CallList.getInstance());
- }
-
- @Override
- public void onUiUnready(CallButtonUi ui) {
- super.onUiUnready(ui);
-
- InCallPresenter.getInstance().removeListener(this);
- AudioModeProvider.getInstance().removeListener(this);
- InCallPresenter.getInstance().removeIncomingCallListener(this);
- InCallPresenter.getInstance().removeDetailsListener(this);
- InCallPresenter.getInstance().getInCallCameraManager().removeCameraSelectionListener(this);
- InCallPresenter.getInstance().removeCanAddCallListener(this);
- }
-
- @Override
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList) {
- CallButtonUi ui = getUi();
-
- if (newState == InCallState.OUTGOING) {
- mCall = callList.getOutgoingCall();
- } else if (newState == InCallState.INCALL) {
- mCall = callList.getActiveOrBackgroundCall();
-
- // When connected to voice mail, automatically shows the dialpad.
- // (On previous releases we showed it when in-call shows up, before waiting for
- // OUTGOING. We may want to do that once we start showing "Voice mail" label on
- // the dialpad too.)
- if (ui != null) {
- if (oldState == InCallState.OUTGOING && mCall != null) {
- if (CallerInfoUtils.isVoiceMailNumber(ui.getContext(), mCall)) {
- ui.displayDialpad(true /* show */, true /* animate */);
- }
- }
- }
- } else if (newState == InCallState.INCOMING) {
- if (ui != null) {
- ui.displayDialpad(false /* show */, true /* animate */);
- }
- mCall = callList.getIncomingCall();
- } else {
- mCall = null;
- }
- updateUi(newState, mCall);
- }
-
- /**
- * Updates the user interface in response to a change in the details of a call.
- * Currently handles changes to the call buttons in response to a change in the details for a
- * call. This is important to ensure changes to the active call are reflected in the available
- * buttons.
- *
- * @param call The active call.
- * @param details The call details.
- */
- @Override
- public void onDetailsChanged(Call call, android.telecom.Call.Details details) {
- // Only update if the changes are for the currently active call
- if (getUi() != null && call != null && call.equals(mCall)) {
- updateButtonsState(call);
- }
- }
-
- @Override
- public void onIncomingCall(InCallState oldState, InCallState newState, Call call) {
- onStateChange(oldState, newState, CallList.getInstance());
- }
-
- @Override
- public void onCanAddCallChanged(boolean canAddCall) {
- if (getUi() != null && mCall != null) {
- updateButtonsState(mCall);
- }
- }
-
- @Override
- public void onAudioMode(int mode) {
- if (getUi() != null) {
- getUi().setAudio(mode);
- }
- }
-
- @Override
- public void onSupportedAudioMode(int mask) {
- if (getUi() != null) {
- getUi().setSupportedAudio(mask);
- }
- }
-
- @Override
- public void onMute(boolean muted) {
- if (getUi() != null && !mAutomaticallyMuted) {
- getUi().setMute(muted);
- }
- }
-
- public int getAudioMode() {
- return AudioModeProvider.getInstance().getAudioMode();
- }
-
- public int getSupportedAudio() {
- return AudioModeProvider.getInstance().getSupportedModes();
- }
-
- public void setAudioMode(int mode) {
-
- // TODO: Set a intermediate state in this presenter until we get
- // an update for onAudioMode(). This will make UI response immediate
- // if it turns out to be slow
-
- Log.d(this, "Sending new Audio Mode: " + CallAudioState.audioRouteToString(mode));
- TelecomAdapter.getInstance().setAudioRoute(mode);
- }
-
- /**
- * Function assumes that bluetooth is not supported.
- */
- public void toggleSpeakerphone() {
- // this function should not be called if bluetooth is available
- if (0 != (CallAudioState.ROUTE_BLUETOOTH & getSupportedAudio())) {
-
- // It's clear the UI is wrong, so update the supported mode once again.
- Log.e(this, "toggling speakerphone not allowed when bluetooth supported.");
- getUi().setSupportedAudio(getSupportedAudio());
- return;
- }
-
- int newMode = CallAudioState.ROUTE_SPEAKER;
-
- // if speakerphone is already on, change to wired/earpiece
- if (getAudioMode() == CallAudioState.ROUTE_SPEAKER) {
- newMode = CallAudioState.ROUTE_WIRED_OR_EARPIECE;
- }
-
- setAudioMode(newMode);
- }
-
- public void muteClicked(boolean checked) {
- Log.d(this, "turning on mute: " + checked);
- TelecomAdapter.getInstance().mute(checked);
- }
-
- public void holdClicked(boolean checked) {
- if (mCall == null) {
- return;
- }
- if (checked) {
- Log.i(this, "Putting the call on hold: " + mCall);
- TelecomAdapter.getInstance().holdCall(mCall.getId());
- } else {
- Log.i(this, "Removing the call from hold: " + mCall);
- TelecomAdapter.getInstance().unholdCall(mCall.getId());
- }
- }
-
- public void swapClicked() {
- if (mCall == null) {
- return;
- }
-
- Log.i(this, "Swapping the call: " + mCall);
- TelecomAdapter.getInstance().swap(mCall.getId());
- }
-
- public void mergeClicked() {
- TelecomAdapter.getInstance().merge(mCall.getId());
- }
-
- public void addCallClicked() {
- // Automatically mute the current call
- mAutomaticallyMuted = true;
- mPreviousMuteState = AudioModeProvider.getInstance().getMute();
- // Simulate a click on the mute button
- muteClicked(true);
- TelecomAdapter.getInstance().addCall();
- }
-
- public void changeToVoiceClicked() {
- VideoCall videoCall = mCall.getVideoCall();
- if (videoCall == null) {
- return;
- }
-
- VideoProfile videoProfile = new VideoProfile(VideoProfile.STATE_AUDIO_ONLY);
- videoCall.sendSessionModifyRequest(videoProfile);
- }
-
- public void showDialpadClicked(boolean checked) {
- Log.v(this, "Show dialpad " + String.valueOf(checked));
- getUi().displayDialpad(checked /* show */, true /* animate */);
- }
-
- public void changeToVideoClicked() {
- VideoCall videoCall = mCall.getVideoCall();
- if (videoCall == null) {
- return;
- }
- int currVideoState = mCall.getVideoState();
- int currUnpausedVideoState = VideoUtils.getUnPausedVideoState(currVideoState);
- currUnpausedVideoState |= VideoProfile.STATE_BIDIRECTIONAL;
-
- VideoProfile videoProfile = new VideoProfile(currUnpausedVideoState);
- videoCall.sendSessionModifyRequest(videoProfile);
- mCall.setSessionModificationState(Call.SessionModificationState.WAITING_FOR_RESPONSE);
- }
-
- /**
- * Switches the camera between the front-facing and back-facing camera.
- * @param useFrontFacingCamera True if we should switch to using the front-facing camera, or
- * false if we should switch to using the back-facing camera.
- */
- public void switchCameraClicked(boolean useFrontFacingCamera) {
- InCallCameraManager cameraManager = InCallPresenter.getInstance().getInCallCameraManager();
- cameraManager.setUseFrontFacingCamera(useFrontFacingCamera);
-
- VideoCall videoCall = mCall.getVideoCall();
- if (videoCall == null) {
- return;
- }
-
- String cameraId = cameraManager.getActiveCameraId();
- if (cameraId != null) {
- final int cameraDir = cameraManager.isUsingFrontFacingCamera()
- ? Call.VideoSettings.CAMERA_DIRECTION_FRONT_FACING
- : Call.VideoSettings.CAMERA_DIRECTION_BACK_FACING;
- mCall.getVideoSettings().setCameraDir(cameraDir);
- videoCall.setCamera(cameraId);
- videoCall.requestCameraCapabilities();
- }
- }
-
-
- /**
- * Stop or start client's video transmission.
- * @param pause True if pausing the local user's video, or false if starting the local user's
- * video.
- */
- public void pauseVideoClicked(boolean pause) {
- VideoCall videoCall = mCall.getVideoCall();
- if (videoCall == null) {
- return;
- }
-
- final int currUnpausedVideoState = VideoUtils.getUnPausedVideoState(mCall.getVideoState());
- if (pause) {
- videoCall.setCamera(null);
- VideoProfile videoProfile = new VideoProfile(currUnpausedVideoState
- & ~VideoProfile.STATE_TX_ENABLED);
- videoCall.sendSessionModifyRequest(videoProfile);
- } else {
- InCallCameraManager cameraManager = InCallPresenter.getInstance().
- getInCallCameraManager();
- videoCall.setCamera(cameraManager.getActiveCameraId());
- VideoProfile videoProfile = new VideoProfile(currUnpausedVideoState
- | VideoProfile.STATE_TX_ENABLED);
- videoCall.sendSessionModifyRequest(videoProfile);
- mCall.setSessionModificationState(Call.SessionModificationState.WAITING_FOR_RESPONSE);
- }
- getUi().setVideoPaused(pause);
- }
-
- private void updateUi(InCallState state, Call call) {
- Log.d(this, "Updating call UI for call: ", call);
-
- final CallButtonUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- final boolean isEnabled =
- state.isConnectingOrConnected() &&!state.isIncoming() && call != null;
- ui.setEnabled(isEnabled);
-
- if (call == null) {
- return;
- }
-
- updateButtonsState(call);
- }
-
- /**
- * Updates the buttons applicable for the UI.
- *
- * @param call The active call.
- */
- private void updateButtonsState(Call call) {
- Log.v(this, "updateButtonsState");
- final CallButtonUi ui = getUi();
- final boolean isVideo = VideoUtils.isVideoCall(call);
-
- // Common functionality (audio, hold, etc).
- // Show either HOLD or SWAP, but not both. If neither HOLD or SWAP is available:
- // (1) If the device normally can hold, show HOLD in a disabled state.
- // (2) If the device doesn't have the concept of hold/swap, remove the button.
- final boolean showSwap = call.can(
- android.telecom.Call.Details.CAPABILITY_SWAP_CONFERENCE);
- final boolean showHold = !showSwap
- && call.can(android.telecom.Call.Details.CAPABILITY_SUPPORT_HOLD)
- && call.can(android.telecom.Call.Details.CAPABILITY_HOLD);
- final boolean isCallOnHold = call.getState() == Call.State.ONHOLD;
-
- final boolean showAddCall = TelecomAdapter.getInstance().canAddCall()
- && UserManagerCompat.isUserUnlocked(ui.getContext());
- final boolean showMerge = call.can(
- android.telecom.Call.Details.CAPABILITY_MERGE_CONFERENCE);
- final boolean showUpgradeToVideo = !isVideo && hasVideoCallCapabilities(call);
- final boolean showDowngradeToAudio = isVideo && isDowngradeToAudioSupported(call);
- final boolean showMute = call.can(android.telecom.Call.Details.CAPABILITY_MUTE);
-
- ui.showButton(BUTTON_AUDIO, true);
- ui.showButton(BUTTON_SWAP, showSwap);
- ui.showButton(BUTTON_HOLD, showHold);
- ui.setHold(isCallOnHold);
- ui.showButton(BUTTON_MUTE, showMute);
- ui.showButton(BUTTON_ADD_CALL, showAddCall);
- ui.showButton(BUTTON_UPGRADE_TO_VIDEO, showUpgradeToVideo);
- ui.showButton(BUTTON_DOWNGRADE_TO_AUDIO, showDowngradeToAudio);
- ui.showButton(BUTTON_SWITCH_CAMERA, isVideo);
- ui.showButton(BUTTON_PAUSE_VIDEO, isVideo);
- if (isVideo) {
- getUi().setVideoPaused(!VideoUtils.isTransmissionEnabled(call));
- }
- ui.showButton(BUTTON_DIALPAD, true);
- ui.showButton(BUTTON_MERGE, showMerge);
-
- ui.updateButtonStates();
- }
-
- private boolean hasVideoCallCapabilities(Call call) {
- if (SdkVersionOverride.getSdkVersion(Build.VERSION_CODES.M) >= Build.VERSION_CODES.M) {
- return call.can(android.telecom.Call.Details.CAPABILITY_SUPPORTS_VT_LOCAL_TX)
- && call.can(android.telecom.Call.Details.CAPABILITY_SUPPORTS_VT_REMOTE_RX);
- }
- // In L, this single flag represents both video transmitting and receiving capabilities
- return call.can(android.telecom.Call.Details.CAPABILITY_SUPPORTS_VT_LOCAL_TX);
- }
-
- /**
- * Determines if downgrading from a video call to an audio-only call is supported. In order to
- * support downgrade to audio, the SDK version must be >= N and the call should NOT have the
- * {@link android.telecom.Call.Details#CAPABILITY_CANNOT_DOWNGRADE_VIDEO_TO_AUDIO}.
- * @param call The call.
- * @return {@code true} if downgrading to an audio-only call from a video call is supported.
- */
- private boolean isDowngradeToAudioSupported(Call call) {
- return !call.can(CallSdkCompat.Details.CAPABILITY_CANNOT_DOWNGRADE_VIDEO_TO_AUDIO);
- }
-
- public void refreshMuteState() {
- // Restore the previous mute state
- if (mAutomaticallyMuted &&
- AudioModeProvider.getInstance().getMute() != mPreviousMuteState) {
- if (getUi() == null) {
- return;
- }
- muteClicked(mPreviousMuteState);
- }
- mAutomaticallyMuted = false;
- }
-
- @Override
- public void onSaveInstanceState(Bundle outState) {
- super.onSaveInstanceState(outState);
- outState.putBoolean(KEY_AUTOMATICALLY_MUTED, mAutomaticallyMuted);
- outState.putBoolean(KEY_PREVIOUS_MUTE_STATE, mPreviousMuteState);
- }
-
- @Override
- public void onRestoreInstanceState(Bundle savedInstanceState) {
- mAutomaticallyMuted =
- savedInstanceState.getBoolean(KEY_AUTOMATICALLY_MUTED, mAutomaticallyMuted);
- mPreviousMuteState =
- savedInstanceState.getBoolean(KEY_PREVIOUS_MUTE_STATE, mPreviousMuteState);
- super.onRestoreInstanceState(savedInstanceState);
- }
-
- public interface CallButtonUi extends Ui {
- void showButton(int buttonId, boolean show);
- void enableButton(int buttonId, boolean enable);
- void setEnabled(boolean on);
- void setMute(boolean on);
- void setHold(boolean on);
- void setCameraSwitched(boolean isBackFacingCamera);
- void setVideoPaused(boolean isPaused);
- void setAudio(int mode);
- void setSupportedAudio(int mask);
- void displayDialpad(boolean on, boolean animate);
- boolean isDialpadVisible();
-
- /**
- * Once showButton() has been called on each of the individual buttons in the UI, call
- * this to configure the overflow menu appropriately.
- */
- void updateButtonStates();
- Context getContext();
- }
-
- @Override
- public void onActiveCameraSelectionChanged(boolean isUsingFrontFacingCamera) {
- if (getUi() == null) {
- return;
- }
- getUi().setCameraSwitched(!isUsingFrontFacingCamera);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallCardFragment.java b/InCallUI/src/com/android/incallui/CallCardFragment.java
deleted file mode 100644
index c2022d18c3751451b28f2c1e64cd4d7c613b19d7..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallCardFragment.java
+++ /dev/null
@@ -1,1510 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.animation.Animator;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.AnimatorSet;
-import android.animation.ObjectAnimator;
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.drawable.AnimationDrawable;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.GradientDrawable;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Looper;
-import android.os.Trace;
-import android.support.v4.graphics.drawable.RoundedBitmapDrawable;
-import android.support.v4.graphics.drawable.RoundedBitmapDrawableFactory;
-import android.telecom.DisconnectCause;
-import android.telephony.PhoneNumberUtils;
-import android.text.TextUtils;
-import android.text.format.DateUtils;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.View.OnLayoutChangeListener;
-import android.view.ViewGroup;
-import android.view.ViewPropertyAnimator;
-import android.view.ViewTreeObserver;
-import android.view.ViewTreeObserver.OnGlobalLayoutListener;
-import android.view.accessibility.AccessibilityEvent;
-import android.view.accessibility.AccessibilityManager;
-import android.view.animation.Animation;
-import android.view.animation.AnimationUtils;
-import android.widget.ImageButton;
-import android.widget.ImageView;
-import android.widget.LinearLayout;
-import android.widget.ListAdapter;
-import android.widget.ListView;
-import android.widget.TextView;
-import android.widget.Toast;
-
-import com.android.contacts.common.compat.PhoneNumberUtilsCompat;
-import com.android.contacts.common.util.MaterialColorMapUtils.MaterialPalette;
-import com.android.contacts.common.widget.FloatingActionButtonController;
-import com.android.dialer.R;
-import com.android.phone.common.animation.AnimUtils;
-
-import java.util.List;
-
-/**
- * Fragment for call card.
- */
-public class CallCardFragment extends BaseFragment
- implements CallCardPresenter.CallCardUi {
- private static final String TAG = "CallCardFragment";
-
- /**
- * Internal class which represents the call state label which is to be applied.
- */
- private class CallStateLabel {
- private CharSequence mCallStateLabel;
- private boolean mIsAutoDismissing;
-
- public CallStateLabel(CharSequence callStateLabel, boolean isAutoDismissing) {
- mCallStateLabel = callStateLabel;
- mIsAutoDismissing = isAutoDismissing;
- }
-
- public CharSequence getCallStateLabel() {
- return mCallStateLabel;
- }
-
- /**
- * Determines if the call state label should auto-dismiss.
- *
- * @return {@code true} if the call state label should auto-dismiss.
- */
- public boolean isAutoDismissing() {
- return mIsAutoDismissing;
- }
- };
-
- private static final String IS_DIALPAD_SHOWING_KEY = "is_dialpad_showing";
-
- /**
- * The duration of time (in milliseconds) a call state label should remain visible before
- * resetting to its previous value.
- */
- private static final long CALL_STATE_LABEL_RESET_DELAY_MS = 3000;
- /**
- * Amount of time to wait before sending an announcement via the accessibility manager.
- * When the call state changes to an outgoing or incoming state for the first time, the
- * UI can often be changing due to call updates or contact lookup. This allows the UI
- * to settle to a stable state to ensure that the correct information is announced.
- */
- private static final long ACCESSIBILITY_ANNOUNCEMENT_DELAY_MS = 500;
-
- private AnimatorSet mAnimatorSet;
- private int mShrinkAnimationDuration;
- private int mFabNormalDiameter;
- private int mFabSmallDiameter;
- private boolean mIsLandscape;
- private boolean mHasLargePhoto;
- private boolean mIsDialpadShowing;
-
- // Primary caller info
- private TextView mPhoneNumber;
- private TextView mNumberLabel;
- private TextView mPrimaryName;
- private View mCallStateButton;
- private ImageView mCallStateIcon;
- private ImageView mCallStateVideoCallIcon;
- private TextView mCallStateLabel;
- private TextView mCallTypeLabel;
- private ImageView mHdAudioIcon;
- private ImageView mForwardIcon;
- private ImageView mSpamIcon;
- private View mCallNumberAndLabel;
- private TextView mElapsedTime;
- private Drawable mPrimaryPhotoDrawable;
- private TextView mCallSubject;
- private ImageView mWorkProfileIcon;
-
- // Container view that houses the entire primary call card, including the call buttons
- private View mPrimaryCallCardContainer;
- // Container view that houses the primary call information
- private ViewGroup mPrimaryCallInfo;
- private View mCallButtonsContainer;
- private ImageView mPhotoSmall;
-
- // Secondary caller info
- private View mSecondaryCallInfo;
- private TextView mSecondaryCallName;
- private View mSecondaryCallProviderInfo;
- private TextView mSecondaryCallProviderLabel;
- private View mSecondaryCallConferenceCallIcon;
- private View mSecondaryCallVideoCallIcon;
- private View mProgressSpinner;
-
- // Call card content
- private View mCallCardContent;
- private ImageView mPhotoLarge;
- private View mContactContext;
- private TextView mContactContextTitle;
- private ListView mContactContextListView;
- private LinearLayout mContactContextListHeaders;
-
- private View mManageConferenceCallButton;
-
- // Dark number info bar
- private TextView mInCallMessageLabel;
-
- private FloatingActionButtonController mFloatingActionButtonController;
- private View mFloatingActionButtonContainer;
- private ImageButton mFloatingActionButton;
- private int mFloatingActionButtonVerticalOffset;
-
- private float mTranslationOffset;
- private Animation mPulseAnimation;
-
- private int mVideoAnimationDuration;
- // Whether or not the call card is currently in the process of an animation
- private boolean mIsAnimating;
-
- private MaterialPalette mCurrentThemeColors;
-
- /**
- * Call state label to set when an auto-dismissing call state label is dismissed.
- */
- private CharSequence mPostResetCallStateLabel;
- private boolean mCallStateLabelResetPending = false;
- private Handler mHandler;
-
- /**
- * Determines if secondary call info is populated in the secondary call info UI.
- */
- private boolean mHasSecondaryCallInfo = false;
-
- @Override
- public CallCardPresenter.CallCardUi getUi() {
- return this;
- }
-
- @Override
- public CallCardPresenter createPresenter() {
- return new CallCardPresenter();
- }
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- mHandler = new Handler(Looper.getMainLooper());
- mShrinkAnimationDuration = getResources().getInteger(R.integer.shrink_animation_duration);
- mVideoAnimationDuration = getResources().getInteger(R.integer.video_animation_duration);
- mFloatingActionButtonVerticalOffset = getResources().getDimensionPixelOffset(
- R.dimen.floating_action_button_vertical_offset);
- mFabNormalDiameter = getResources().getDimensionPixelOffset(
- R.dimen.end_call_floating_action_button_diameter);
- mFabSmallDiameter = getResources().getDimensionPixelOffset(
- R.dimen.end_call_floating_action_button_small_diameter);
-
- if (savedInstanceState != null) {
- mIsDialpadShowing = savedInstanceState.getBoolean(IS_DIALPAD_SHOWING_KEY, false);
- }
- }
-
- @Override
- public void onActivityCreated(Bundle savedInstanceState) {
- super.onActivityCreated(savedInstanceState);
-
- final CallList calls = CallList.getInstance();
- final Call call = calls.getFirstCall();
- getPresenter().init(getActivity(), call);
- }
-
- @Override
- public void onSaveInstanceState(Bundle outState) {
- outState.putBoolean(IS_DIALPAD_SHOWING_KEY, mIsDialpadShowing);
- super.onSaveInstanceState(outState);
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- Trace.beginSection(TAG + " onCreate");
- mTranslationOffset =
- getResources().getDimensionPixelSize(R.dimen.call_card_anim_translate_y_offset);
- final View view = inflater.inflate(R.layout.call_card_fragment, container, false);
- Trace.endSection();
- return view;
- }
-
- @Override
- public void onViewCreated(View view, Bundle savedInstanceState) {
- super.onViewCreated(view, savedInstanceState);
-
- mPulseAnimation =
- AnimationUtils.loadAnimation(view.getContext(), R.anim.call_status_pulse);
-
- mPhoneNumber = (TextView) view.findViewById(R.id.phoneNumber);
- mPrimaryName = (TextView) view.findViewById(R.id.name);
- mNumberLabel = (TextView) view.findViewById(R.id.label);
- mSecondaryCallInfo = view.findViewById(R.id.secondary_call_info);
- mSecondaryCallProviderInfo = view.findViewById(R.id.secondary_call_provider_info);
- mCallCardContent = view.findViewById(R.id.call_card_content);
- mPhotoLarge = (ImageView) view.findViewById(R.id.photoLarge);
- mPhotoLarge.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- getPresenter().onContactPhotoClick();
- }
- });
-
- mContactContext = view.findViewById(R.id.contact_context);
- mContactContextTitle = (TextView) view.findViewById(R.id.contactContextTitle);
- mContactContextListView = (ListView) view.findViewById(R.id.contactContextInfo);
- // This layout stores all the list header layouts so they can be easily removed.
- mContactContextListHeaders = new LinearLayout(getView().getContext());
- mContactContextListView.addHeaderView(mContactContextListHeaders);
-
- mCallStateIcon = (ImageView) view.findViewById(R.id.callStateIcon);
- mCallStateVideoCallIcon = (ImageView) view.findViewById(R.id.videoCallIcon);
- mWorkProfileIcon = (ImageView) view.findViewById(R.id.workProfileIcon);
- mCallStateLabel = (TextView) view.findViewById(R.id.callStateLabel);
- mHdAudioIcon = (ImageView) view.findViewById(R.id.hdAudioIcon);
- mForwardIcon = (ImageView) view.findViewById(R.id.forwardIcon);
- mSpamIcon = (ImageView) view.findViewById(R.id.spamIcon);
- mCallNumberAndLabel = view.findViewById(R.id.labelAndNumber);
- mCallTypeLabel = (TextView) view.findViewById(R.id.callTypeLabel);
- mElapsedTime = (TextView) view.findViewById(R.id.elapsedTime);
- mPrimaryCallCardContainer = view.findViewById(R.id.primary_call_info_container);
- mPrimaryCallInfo = (ViewGroup) view.findViewById(R.id.primary_call_banner);
- mCallButtonsContainer = view.findViewById(R.id.callButtonFragment);
- mPhotoSmall = (ImageView) view.findViewById(R.id.photoSmall);
- mPhotoSmall.setVisibility(View.GONE);
- mInCallMessageLabel = (TextView) view.findViewById(R.id.connectionServiceMessage);
- mProgressSpinner = view.findViewById(R.id.progressSpinner);
-
- mFloatingActionButtonContainer = view.findViewById(
- R.id.floating_end_call_action_button_container);
- mFloatingActionButton = (ImageButton) view.findViewById(
- R.id.floating_end_call_action_button);
- mFloatingActionButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- getPresenter().endCallClicked();
- }
- });
- mFloatingActionButtonController = new FloatingActionButtonController(getActivity(),
- mFloatingActionButtonContainer, mFloatingActionButton);
-
- mSecondaryCallInfo.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- getPresenter().secondaryInfoClicked();
- updateFabPositionForSecondaryCallInfo();
- }
- });
-
- mCallStateButton = view.findViewById(R.id.callStateButton);
- mCallStateButton.setOnLongClickListener(new View.OnLongClickListener() {
- @Override
- public boolean onLongClick(View v) {
- getPresenter().onCallStateButtonTouched();
- return false;
- }
- });
-
- mManageConferenceCallButton = view.findViewById(R.id.manage_conference_call_button);
- mManageConferenceCallButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- InCallActivity activity = (InCallActivity) getActivity();
- activity.showConferenceFragment(true);
- }
- });
-
- mPrimaryName.setElegantTextHeight(false);
- mCallStateLabel.setElegantTextHeight(false);
- mCallSubject = (TextView) view.findViewById(R.id.callSubject);
- }
-
- @Override
- public void setVisible(boolean on) {
- if (on) {
- getView().setVisibility(View.VISIBLE);
- } else {
- getView().setVisibility(View.INVISIBLE);
- }
- }
-
- /**
- * Hides or shows the progress spinner.
- *
- * @param visible {@code True} if the progress spinner should be visible.
- */
- @Override
- public void setProgressSpinnerVisible(boolean visible) {
- mProgressSpinner.setVisibility(visible ? View.VISIBLE : View.GONE);
- }
-
- @Override
- public void setContactContextTitle(View headerView) {
- mContactContextListHeaders.removeAllViews();
- mContactContextListHeaders.addView(headerView);
- }
-
- @Override
- public void setContactContextContent(ListAdapter listAdapter) {
- mContactContextListView.setAdapter(listAdapter);
- }
-
- @Override
- public void showContactContext(boolean show) {
- showImageView(mPhotoLarge, !show);
- showImageView(mPhotoSmall, show);
- mPrimaryCallCardContainer.setElevation(
- show ? 0 : getResources().getDimension(R.dimen.primary_call_elevation));
- mContactContext.setVisibility(show ? View.VISIBLE : View.GONE);
- }
-
- /**
- * Sets the visibility of the primary call card.
- * Ensures that when the primary call card is hidden, the video surface slides over to fill the
- * entire screen.
- *
- * @param visible {@code True} if the primary call card should be visible.
- */
- @Override
- public void setCallCardVisible(final boolean visible) {
- Log.v(this, "setCallCardVisible : isVisible = " + visible);
- // When animating the hide/show of the views in a landscape layout, we need to take into
- // account whether we are in a left-to-right locale or a right-to-left locale and adjust
- // the animations accordingly.
- final boolean isLayoutRtl = InCallPresenter.isRtl();
-
- // Retrieve here since at fragment creation time the incoming video view is not inflated.
- final View videoView = getView().findViewById(R.id.incomingVideo);
- if (videoView == null) {
- return;
- }
-
- // Determine how much space there is below or to the side of the call card.
- final float spaceBesideCallCard = getSpaceBesideCallCard();
-
- // We need to translate the video surface, but we need to know its position after the layout
- // has occurred so use a {@code ViewTreeObserver}.
- final ViewTreeObserver observer = getView().getViewTreeObserver();
- observer.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
- @Override
- public boolean onPreDraw() {
- // We don't want to continue getting called.
- getView().getViewTreeObserver().removeOnPreDrawListener(this);
-
- float videoViewTranslation = 0f;
-
- // Translate the call card to its pre-animation state.
- if (!mIsLandscape) {
- mPrimaryCallCardContainer.setTranslationY(visible ?
- -mPrimaryCallCardContainer.getHeight() : 0);
-
- ViewGroup.LayoutParams p = videoView.getLayoutParams();
- videoViewTranslation = p.height / 2 - spaceBesideCallCard / 2;
- }
-
- // Perform animation of video view.
- ViewPropertyAnimator videoViewAnimator = videoView.animate()
- .setInterpolator(AnimUtils.EASE_OUT_EASE_IN)
- .setDuration(mVideoAnimationDuration);
- if (mIsLandscape) {
- videoViewAnimator
- .translationX(visible ? videoViewTranslation : 0);
- } else {
- videoViewAnimator
- .translationY(visible ? videoViewTranslation : 0);
- }
- videoViewAnimator.start();
-
- // Animate the call card sliding.
- ViewPropertyAnimator callCardAnimator = mPrimaryCallCardContainer.animate()
- .setInterpolator(AnimUtils.EASE_OUT_EASE_IN)
- .setDuration(mVideoAnimationDuration)
- .setListener(new AnimatorListenerAdapter() {
- @Override
- public void onAnimationEnd(Animator animation) {
- super.onAnimationEnd(animation);
- if (!visible) {
- mPrimaryCallCardContainer.setVisibility(View.GONE);
- }
- }
-
- @Override
- public void onAnimationStart(Animator animation) {
- super.onAnimationStart(animation);
- if (visible) {
- mPrimaryCallCardContainer.setVisibility(View.VISIBLE);
- }
- }
- });
-
- if (mIsLandscape) {
- float translationX = mPrimaryCallCardContainer.getWidth();
- translationX *= isLayoutRtl ? 1 : -1;
- callCardAnimator
- .translationX(visible ? 0 : translationX)
- .start();
- } else {
- callCardAnimator
- .translationY(visible ? 0 : -mPrimaryCallCardContainer.getHeight())
- .start();
- }
-
- return true;
- }
- });
- }
-
- /**
- * Determines the amount of space below the call card for portrait layouts), or beside the
- * call card for landscape layouts.
- *
- * @return The amount of space below or beside the call card.
- */
- public float getSpaceBesideCallCard() {
- if (mIsLandscape) {
- return getView().getWidth() - mPrimaryCallCardContainer.getWidth();
- } else {
- final int callCardHeight;
- // Retrieve the actual height of the call card, independent of whether or not the
- // outgoing call animation is in progress. The animation does not run in landscape mode
- // so this only needs to be done for portrait.
- if (mPrimaryCallCardContainer.getTag(R.id.view_tag_callcard_actual_height) != null) {
- callCardHeight = (int) mPrimaryCallCardContainer.getTag(
- R.id.view_tag_callcard_actual_height);
- } else {
- callCardHeight = mPrimaryCallCardContainer.getHeight();
- }
- return getView().getHeight() - callCardHeight;
- }
- }
-
- @Override
- public void setPrimaryName(String name, boolean nameIsNumber) {
- if (TextUtils.isEmpty(name)) {
- mPrimaryName.setText(null);
- } else {
- mPrimaryName.setText(nameIsNumber
- ? PhoneNumberUtilsCompat.createTtsSpannable(name)
- : name);
-
- // Set direction of the name field
- int nameDirection = View.TEXT_DIRECTION_INHERIT;
- if (nameIsNumber) {
- nameDirection = View.TEXT_DIRECTION_LTR;
- }
- mPrimaryName.setTextDirection(nameDirection);
- }
- }
-
- /**
- * Sets the primary image for the contact photo.
- *
- * @param image The drawable to set.
- * @param isVisible Whether the contact photo should be visible after being set.
- */
- @Override
- public void setPrimaryImage(Drawable image, boolean isVisible) {
- if (image != null) {
- setDrawableToImageViews(image);
- showImageView(mPhotoLarge, isVisible);
- }
- }
-
- @Override
- public void setPrimaryPhoneNumber(String number) {
- // Set the number
- if (TextUtils.isEmpty(number)) {
- mPhoneNumber.setText(null);
- mPhoneNumber.setVisibility(View.GONE);
- } else {
- mPhoneNumber.setText(PhoneNumberUtilsCompat.createTtsSpannable(number));
- mPhoneNumber.setVisibility(View.VISIBLE);
- mPhoneNumber.setTextDirection(View.TEXT_DIRECTION_LTR);
- }
- }
-
- @Override
- public void setPrimaryLabel(String label) {
- if (!TextUtils.isEmpty(label)) {
- mNumberLabel.setText(label);
- mNumberLabel.setVisibility(View.VISIBLE);
- } else {
- mNumberLabel.setVisibility(View.GONE);
- }
-
- }
-
- /**
- * Sets the primary caller information.
- *
- * @param number The caller phone number.
- * @param name The caller name.
- * @param nameIsNumber {@code true} if the name should be shown in place of the phone number.
- * @param label The label.
- * @param photo The contact photo drawable.
- * @param isSipCall {@code true} if this is a SIP call.
- * @param isContactPhotoShown {@code true} if the contact photo should be shown (it will be
- * updated even if it is not shown).
- * @param isWorkCall Whether the call is placed through a work phone account or caller is a work
- contact.
- */
- @Override
- public void setPrimary(String number, String name, boolean nameIsNumber, String label,
- Drawable photo, boolean isSipCall, boolean isContactPhotoShown, boolean isWorkCall) {
- Log.d(this, "Setting primary call");
- // set the name field.
- setPrimaryName(name, nameIsNumber);
-
- if (TextUtils.isEmpty(number) && TextUtils.isEmpty(label)) {
- mCallNumberAndLabel.setVisibility(View.GONE);
- mElapsedTime.setTextAlignment(View.TEXT_ALIGNMENT_VIEW_START);
- } else {
- mCallNumberAndLabel.setVisibility(View.VISIBLE);
- mElapsedTime.setTextAlignment(View.TEXT_ALIGNMENT_VIEW_END);
- }
-
- setPrimaryPhoneNumber(number);
-
- // Set the label (Mobile, Work, etc)
- setPrimaryLabel(label);
-
- showInternetCallLabel(isSipCall);
-
- setDrawableToImageViews(photo);
- showImageView(mPhotoLarge, isContactPhotoShown);
- showImageView(mWorkProfileIcon, isWorkCall);
- }
-
- @Override
- public void setSecondary(boolean show, String name, boolean nameIsNumber, String label,
- String providerLabel, boolean isConference, boolean isVideoCall, boolean isFullscreen) {
-
- if (show) {
- mHasSecondaryCallInfo = true;
- boolean hasProvider = !TextUtils.isEmpty(providerLabel);
- initializeSecondaryCallInfo(hasProvider);
-
- // Do not show the secondary caller info in fullscreen mode, but ensure it is populated
- // in case fullscreen mode is exited in the future.
- setSecondaryInfoVisible(!isFullscreen);
-
- mSecondaryCallConferenceCallIcon.setVisibility(isConference ? View.VISIBLE : View.GONE);
- mSecondaryCallVideoCallIcon.setVisibility(isVideoCall ? View.VISIBLE : View.GONE);
-
- mSecondaryCallName.setText(nameIsNumber
- ? PhoneNumberUtilsCompat.createTtsSpannable(name)
- : name);
- if (hasProvider) {
- mSecondaryCallProviderLabel.setText(providerLabel);
- }
-
- int nameDirection = View.TEXT_DIRECTION_INHERIT;
- if (nameIsNumber) {
- nameDirection = View.TEXT_DIRECTION_LTR;
- }
- mSecondaryCallName.setTextDirection(nameDirection);
- } else {
- mHasSecondaryCallInfo = false;
- setSecondaryInfoVisible(false);
- }
- }
-
- /**
- * Sets the visibility of the secondary caller info box. Note, if the {@code visible} parameter
- * is passed in {@code true}, and there is no secondary caller info populated (as determined by
- * {@code mHasSecondaryCallInfo}, the secondary caller info box will not be shown.
- *
- * @param visible {@code true} if the secondary caller info should be shown, {@code false}
- * otherwise.
- */
- @Override
- public void setSecondaryInfoVisible(final boolean visible) {
- boolean wasVisible = mSecondaryCallInfo.isShown();
- final boolean isVisible = visible && mHasSecondaryCallInfo;
- Log.v(this, "setSecondaryInfoVisible: wasVisible = " + wasVisible + " isVisible = "
- + isVisible);
-
- // If visibility didn't change, nothing to do.
- if (wasVisible == isVisible) {
- return;
- }
-
- // If we are showing the secondary info, we need to show it before animating so that its
- // height will be determined on layout.
- if (isVisible) {
- mSecondaryCallInfo.setVisibility(View.VISIBLE);
- } else {
- mSecondaryCallInfo.setVisibility(View.GONE);
- }
-
- updateFabPositionForSecondaryCallInfo();
- // We need to translate the secondary caller info, but we need to know its position after
- // the layout has occurred so use a {@code ViewTreeObserver}.
- final ViewTreeObserver observer = getView().getViewTreeObserver();
-
- observer.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
- @Override
- public boolean onPreDraw() {
- // We don't want to continue getting called.
- getView().getViewTreeObserver().removeOnPreDrawListener(this);
-
- // Get the height of the secondary call info now, and then re-hide the view prior
- // to doing the actual animation.
- int secondaryHeight = mSecondaryCallInfo.getHeight();
- if (isVisible) {
- mSecondaryCallInfo.setVisibility(View.GONE);
- } else {
- mSecondaryCallInfo.setVisibility(View.VISIBLE);
- }
- Log.v(this, "setSecondaryInfoVisible: secondaryHeight = " + secondaryHeight);
-
- // Set the position of the secondary call info card to its starting location.
- mSecondaryCallInfo.setTranslationY(visible ? secondaryHeight : 0);
-
- // Animate the secondary card info slide up/down as it appears and disappears.
- ViewPropertyAnimator secondaryInfoAnimator = mSecondaryCallInfo.animate()
- .setInterpolator(AnimUtils.EASE_OUT_EASE_IN)
- .setDuration(mVideoAnimationDuration)
- .translationY(isVisible ? 0 : secondaryHeight)
- .setListener(new AnimatorListenerAdapter() {
- @Override
- public void onAnimationEnd(Animator animation) {
- if (!isVisible) {
- mSecondaryCallInfo.setVisibility(View.GONE);
- }
- }
-
- @Override
- public void onAnimationStart(Animator animation) {
- if (isVisible) {
- mSecondaryCallInfo.setVisibility(View.VISIBLE);
- }
- }
- });
- secondaryInfoAnimator.start();
-
- // Notify listeners of a change in the visibility of the secondary info. This is
- // important when in a video call so that the video call presenter can shift the
- // video preview up or down to accommodate the secondary caller info.
- InCallPresenter.getInstance().notifySecondaryCallerInfoVisibilityChanged(visible,
- secondaryHeight);
-
- return true;
- }
- });
- }
-
- @Override
- public void setCallState(
- int state,
- int videoState,
- int sessionModificationState,
- DisconnectCause disconnectCause,
- String connectionLabel,
- Drawable callStateIcon,
- String gatewayNumber,
- boolean isWifi,
- boolean isConference,
- boolean isWorkCall) {
- boolean isGatewayCall = !TextUtils.isEmpty(gatewayNumber);
- CallStateLabel callStateLabel = getCallStateLabelFromState(state, videoState,
- sessionModificationState, disconnectCause, connectionLabel, isGatewayCall, isWifi,
- isConference, isWorkCall);
-
- Log.v(this, "setCallState " + callStateLabel.getCallStateLabel());
- Log.v(this, "AutoDismiss " + callStateLabel.isAutoDismissing());
- Log.v(this, "DisconnectCause " + disconnectCause.toString());
- Log.v(this, "gateway " + connectionLabel + gatewayNumber);
-
- // Check for video state change and update the visibility of the contact photo. The contact
- // photo is hidden when the incoming video surface is shown.
- // The contact photo visibility can also change in setPrimary().
- boolean showContactPhoto = !VideoCallPresenter.showIncomingVideo(videoState, state);
- mPhotoLarge.setVisibility(showContactPhoto ? View.VISIBLE : View.GONE);
-
- // Check if the call subject is showing -- if it is, we want to bypass showing the call
- // state.
- boolean isSubjectShowing = mCallSubject.getVisibility() == View.VISIBLE;
-
- if (TextUtils.equals(callStateLabel.getCallStateLabel(), mCallStateLabel.getText()) &&
- !isSubjectShowing) {
- // Nothing to do if the labels are the same
- if (state == Call.State.ACTIVE || state == Call.State.CONFERENCED) {
- mCallStateLabel.clearAnimation();
- mCallStateIcon.clearAnimation();
- }
- return;
- }
-
- if (isSubjectShowing) {
- changeCallStateLabel(null);
- callStateIcon = null;
- } else {
- // Update the call state label and icon.
- setCallStateLabel(callStateLabel);
- }
-
- if (!TextUtils.isEmpty(callStateLabel.getCallStateLabel())) {
- if (state == Call.State.ACTIVE || state == Call.State.CONFERENCED) {
- mCallStateLabel.clearAnimation();
- } else {
- mCallStateLabel.startAnimation(mPulseAnimation);
- }
- } else {
- mCallStateLabel.clearAnimation();
- }
-
- if (callStateIcon != null) {
- mCallStateIcon.setVisibility(View.VISIBLE);
- // Invoke setAlpha(float) instead of setAlpha(int) to set the view's alpha. This is
- // needed because the pulse animation operates on the view alpha.
- mCallStateIcon.setAlpha(1.0f);
- mCallStateIcon.setImageDrawable(callStateIcon);
-
- if (state == Call.State.ACTIVE || state == Call.State.CONFERENCED
- || TextUtils.isEmpty(callStateLabel.getCallStateLabel())) {
- mCallStateIcon.clearAnimation();
- } else {
- mCallStateIcon.startAnimation(mPulseAnimation);
- }
-
- if (callStateIcon instanceof AnimationDrawable) {
- ((AnimationDrawable) callStateIcon).start();
- }
- } else {
- mCallStateIcon.clearAnimation();
-
- // Invoke setAlpha(float) instead of setAlpha(int) to set the view's alpha. This is
- // needed because the pulse animation operates on the view alpha.
- mCallStateIcon.setAlpha(0.0f);
- mCallStateIcon.setVisibility(View.GONE);
- }
-
- if (VideoUtils.isVideoCall(videoState)
- || (state == Call.State.ACTIVE && sessionModificationState
- == Call.SessionModificationState.WAITING_FOR_RESPONSE)) {
- mCallStateVideoCallIcon.setVisibility(View.VISIBLE);
- } else {
- mCallStateVideoCallIcon.setVisibility(View.GONE);
- }
- }
-
- private void setCallStateLabel(CallStateLabel callStateLabel) {
- Log.v(this, "setCallStateLabel : label = " + callStateLabel.getCallStateLabel());
-
- if (callStateLabel.isAutoDismissing()) {
- mCallStateLabelResetPending = true;
- mHandler.postDelayed(new Runnable() {
- @Override
- public void run() {
- Log.v(this, "restoringCallStateLabel : label = " +
- mPostResetCallStateLabel);
- changeCallStateLabel(mPostResetCallStateLabel);
- mCallStateLabelResetPending = false;
- }
- }, CALL_STATE_LABEL_RESET_DELAY_MS);
-
- changeCallStateLabel(callStateLabel.getCallStateLabel());
- } else {
- // Keep track of the current call state label; used when resetting auto dismissing
- // call state labels.
- mPostResetCallStateLabel = callStateLabel.getCallStateLabel();
-
- if (!mCallStateLabelResetPending) {
- changeCallStateLabel(callStateLabel.getCallStateLabel());
- }
- }
- }
-
- private void changeCallStateLabel(CharSequence callStateLabel) {
- Log.v(this, "changeCallStateLabel : label = " + callStateLabel);
- if (!TextUtils.isEmpty(callStateLabel)) {
- mCallStateLabel.setText(callStateLabel);
- mCallStateLabel.setAlpha(1);
- mCallStateLabel.setVisibility(View.VISIBLE);
- } else {
- Animation callStateLabelAnimation = mCallStateLabel.getAnimation();
- if (callStateLabelAnimation != null) {
- callStateLabelAnimation.cancel();
- }
- mCallStateLabel.setText(null);
- mCallStateLabel.setAlpha(0);
- mCallStateLabel.setVisibility(View.GONE);
- }
- }
-
- @Override
- public void setCallbackNumber(String callbackNumber, boolean isEmergencyCall) {
- if (mInCallMessageLabel == null) {
- return;
- }
-
- if (TextUtils.isEmpty(callbackNumber)) {
- mInCallMessageLabel.setVisibility(View.GONE);
- return;
- }
-
- // TODO: The new Locale-specific methods don't seem to be working. Revisit this.
- callbackNumber = PhoneNumberUtils.formatNumber(callbackNumber);
-
- int stringResourceId = isEmergencyCall ? R.string.card_title_callback_number_emergency
- : R.string.card_title_callback_number;
-
- String text = getString(stringResourceId, callbackNumber);
- mInCallMessageLabel.setText(text);
-
- mInCallMessageLabel.setVisibility(View.VISIBLE);
- }
-
- /**
- * Sets and shows the call subject if it is not empty. Hides the call subject otherwise.
- *
- * @param callSubject The call subject.
- */
- @Override
- public void setCallSubject(String callSubject) {
- boolean showSubject = !TextUtils.isEmpty(callSubject);
-
- mCallSubject.setVisibility(showSubject ? View.VISIBLE : View.GONE);
- if (showSubject) {
- mCallSubject.setText(callSubject);
- } else {
- mCallSubject.setText(null);
- }
- }
-
- public boolean isAnimating() {
- return mIsAnimating;
- }
-
- private void showInternetCallLabel(boolean show) {
- if (show) {
- final String label = getView().getContext().getString(
- R.string.incall_call_type_label_sip);
- mCallTypeLabel.setVisibility(View.VISIBLE);
- mCallTypeLabel.setText(label);
- } else {
- mCallTypeLabel.setVisibility(View.GONE);
- }
- }
-
- @Override
- public void setPrimaryCallElapsedTime(boolean show, long duration) {
- if (show) {
- if (mElapsedTime.getVisibility() != View.VISIBLE) {
- AnimUtils.fadeIn(mElapsedTime, AnimUtils.DEFAULT_DURATION);
- }
- String callTimeElapsed = DateUtils.formatElapsedTime(duration / 1000);
- mElapsedTime.setText(callTimeElapsed);
-
- String durationDescription =
- InCallDateUtils.formatDuration(duration);
- mElapsedTime.setContentDescription(
- !TextUtils.isEmpty(durationDescription) ? durationDescription : null);
- } else {
- // hide() animation has no effect if it is already hidden.
- AnimUtils.fadeOut(mElapsedTime, AnimUtils.DEFAULT_DURATION);
- }
- }
-
- /**
- * Set all the ImageViews to the same photo. Currently there are 2 photo views: the large one
- * (which fills about the bottom half of the screen) and the small one, which displays as a
- * circle next to the primary contact info. This method does not handle whether the ImageView
- * is shown or not.
- *
- * @param photo The photo to set for the image views.
- */
- private void setDrawableToImageViews(Drawable photo) {
- if (photo == null) {
- photo = ContactInfoCache.getInstance(getView().getContext())
- .getDefaultContactPhotoDrawable();
- }
-
- if (mPrimaryPhotoDrawable == photo){
- return;
- }
- mPrimaryPhotoDrawable = photo;
-
- mPhotoLarge.setImageDrawable(photo);
-
- // Modify the drawable to be round for the smaller ImageView.
- Bitmap bitmap = drawableToBitmap(photo);
- if (bitmap != null) {
- final RoundedBitmapDrawable drawable =
- RoundedBitmapDrawableFactory.create(getResources(), bitmap);
- drawable.setAntiAlias(true);
- drawable.setCornerRadius(bitmap.getHeight() / 2);
- photo = drawable;
- }
- mPhotoSmall.setImageDrawable(photo);
- }
-
- /**
- * Helper method for image view to handle animations.
- *
- * @param view The image view to show or hide.
- * @param isVisible {@code true} if we want to show the image, {@code false} to hide it.
- */
- private void showImageView(ImageView view, boolean isVisible) {
- if (view.getDrawable() == null) {
- if (isVisible) {
- AnimUtils.fadeIn(mElapsedTime, AnimUtils.DEFAULT_DURATION);
- }
- } else {
- // Cross fading is buggy and not noticeable due to the multiple calls to this method
- // that switch drawables in the middle of the cross-fade animations. Just show the
- // photo directly instead.
- view.setVisibility(isVisible ? View.VISIBLE : View.GONE);
- }
- }
-
- /**
- * Converts a drawable into a bitmap.
- *
- * @param drawable the drawable to be converted.
- */
- public static Bitmap drawableToBitmap(Drawable drawable) {
- Bitmap bitmap;
- if (drawable instanceof BitmapDrawable) {
- bitmap = ((BitmapDrawable) drawable).getBitmap();
- } else {
- if (drawable.getIntrinsicWidth() <= 0 || drawable.getIntrinsicHeight() <= 0) {
- // Needed for drawables that are just a colour.
- bitmap = Bitmap.createBitmap(1, 1, Bitmap.Config.ARGB_8888);
- } else {
- bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(),
- drawable.getIntrinsicHeight(), Bitmap.Config.ARGB_8888);
- }
-
- Log.i(TAG, "Created bitmap with width " + bitmap.getWidth() + ", height "
- + bitmap.getHeight());
-
- Canvas canvas = new Canvas(bitmap);
- drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
- drawable.draw(canvas);
- }
- return bitmap;
- }
-
- /**
- * Gets the call state label based on the state of the call or cause of disconnect.
- *
- * Additional labels are applied as follows:
- * 1. All outgoing calls with display "Calling via [Provider]".
- * 2. Ongoing calls will display the name of the provider.
- * 3. Incoming calls will only display "Incoming via..." for accounts.
- * 4. Video calls, and session modification states (eg. requesting video).
- * 5. Incoming and active Wi-Fi calls will show label provided by hint.
- *
- * TODO: Move this to the CallCardPresenter.
- */
- private CallStateLabel getCallStateLabelFromState(int state, int videoState,
- int sessionModificationState, DisconnectCause disconnectCause, String label,
- boolean isGatewayCall, boolean isWifi, boolean isConference, boolean isWorkCall) {
- final Context context = getView().getContext();
- CharSequence callStateLabel = null; // Label to display as part of the call banner
-
- boolean hasSuggestedLabel = label != null;
- boolean isAccount = hasSuggestedLabel && !isGatewayCall;
- boolean isAutoDismissing = false;
-
- switch (state) {
- case Call.State.IDLE:
- // "Call state" is meaningless in this state.
- break;
- case Call.State.ACTIVE:
- // We normally don't show a "call state label" at all in this state
- // (but we can use the call state label to display the provider name).
- if ((isAccount || isWifi || isConference) && hasSuggestedLabel) {
- callStateLabel = label;
- } else if (sessionModificationState
- == Call.SessionModificationState.REQUEST_REJECTED) {
- callStateLabel = context.getString(R.string.card_title_video_call_rejected);
- isAutoDismissing = true;
- } else if (sessionModificationState
- == Call.SessionModificationState.REQUEST_FAILED) {
- callStateLabel = context.getString(R.string.card_title_video_call_error);
- isAutoDismissing = true;
- } else if (sessionModificationState
- == Call.SessionModificationState.WAITING_FOR_RESPONSE) {
- callStateLabel = context.getString(R.string.card_title_video_call_requesting);
- } else if (sessionModificationState
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- callStateLabel = context.getString(R.string.card_title_video_call_requesting);
- } else if (VideoUtils.isVideoCall(videoState)) {
- callStateLabel = context.getString(R.string.card_title_video_call);
- }
- break;
- case Call.State.ONHOLD:
- callStateLabel = context.getString(R.string.card_title_on_hold);
- break;
- case Call.State.CONNECTING:
- case Call.State.DIALING:
- if (hasSuggestedLabel && !isWifi) {
- callStateLabel = context.getString(R.string.calling_via_template, label);
- } else {
- callStateLabel = context.getString(R.string.card_title_dialing);
- }
- break;
- case Call.State.REDIALING:
- callStateLabel = context.getString(R.string.card_title_redialing);
- break;
- case Call.State.INCOMING:
- case Call.State.CALL_WAITING:
- if (isWifi && hasSuggestedLabel) {
- callStateLabel = label;
- } else if (isAccount) {
- callStateLabel = context.getString(R.string.incoming_via_template, label);
- } else if (VideoUtils.isVideoCall(videoState)) {
- callStateLabel = context.getString(R.string.notification_incoming_video_call);
- } else {
- callStateLabel =
- context.getString(isWorkCall ? R.string.card_title_incoming_work_call
- : R.string.card_title_incoming_call);
- }
- break;
- case Call.State.DISCONNECTING:
- // While in the DISCONNECTING state we display a "Hanging up"
- // message in order to make the UI feel more responsive. (In
- // GSM it's normal to see a delay of a couple of seconds while
- // negotiating the disconnect with the network, so the "Hanging
- // up" state at least lets the user know that we're doing
- // something. This state is currently not used with CDMA.)
- callStateLabel = context.getString(R.string.card_title_hanging_up);
- break;
- case Call.State.DISCONNECTED:
- callStateLabel = disconnectCause.getLabel();
- if (TextUtils.isEmpty(callStateLabel)) {
- callStateLabel = context.getString(R.string.card_title_call_ended);
- }
- break;
- case Call.State.CONFERENCED:
- callStateLabel = context.getString(R.string.card_title_conf_call);
- break;
- default:
- Log.wtf(this, "updateCallStateWidgets: unexpected call: " + state);
- }
- return new CallStateLabel(callStateLabel, isAutoDismissing);
- }
-
- private void initializeSecondaryCallInfo(boolean hasProvider) {
- // mSecondaryCallName is initialized here (vs. onViewCreated) because it is inaccessible
- // until mSecondaryCallInfo is inflated in the call above.
- if (mSecondaryCallName == null) {
- mSecondaryCallName = (TextView) getView().findViewById(R.id.secondaryCallName);
- mSecondaryCallConferenceCallIcon =
- getView().findViewById(R.id.secondaryCallConferenceCallIcon);
- mSecondaryCallVideoCallIcon =
- getView().findViewById(R.id.secondaryCallVideoCallIcon);
- }
-
- if (mSecondaryCallProviderLabel == null && hasProvider) {
- mSecondaryCallProviderInfo.setVisibility(View.VISIBLE);
- mSecondaryCallProviderLabel = (TextView) getView()
- .findViewById(R.id.secondaryCallProviderLabel);
- }
- }
-
- public void dispatchPopulateAccessibilityEvent(AccessibilityEvent event) {
- if (event.getEventType() == AccessibilityEvent.TYPE_ANNOUNCEMENT) {
- // Indicate this call is in active if no label is provided. The label is empty when
- // the call is in active, not in other status such as onhold or dialing etc.
- if (!mCallStateLabel.isShown() || TextUtils.isEmpty(mCallStateLabel.getText())) {
- event.getText().add(
- TextUtils.expandTemplate(
- getResources().getText(R.string.accessibility_call_is_active),
- mPrimaryName.getText()));
- } else {
- dispatchPopulateAccessibilityEvent(event, mCallStateLabel);
- dispatchPopulateAccessibilityEvent(event, mPrimaryName);
- dispatchPopulateAccessibilityEvent(event, mCallTypeLabel);
- dispatchPopulateAccessibilityEvent(event, mPhoneNumber);
- }
- return;
- }
- dispatchPopulateAccessibilityEvent(event, mCallStateLabel);
- dispatchPopulateAccessibilityEvent(event, mPrimaryName);
- dispatchPopulateAccessibilityEvent(event, mPhoneNumber);
- dispatchPopulateAccessibilityEvent(event, mCallTypeLabel);
- dispatchPopulateAccessibilityEvent(event, mSecondaryCallName);
- dispatchPopulateAccessibilityEvent(event, mSecondaryCallProviderLabel);
-
- return;
- }
-
- @Override
- public void sendAccessibilityAnnouncement() {
- mHandler.postDelayed(new Runnable() {
- @Override
- public void run() {
- if (getView() != null && getView().getParent() != null &&
- isAccessibilityEnabled(getContext())) {
- AccessibilityEvent event = AccessibilityEvent.obtain(
- AccessibilityEvent.TYPE_ANNOUNCEMENT);
- dispatchPopulateAccessibilityEvent(event);
- getView().getParent().requestSendAccessibilityEvent(getView(), event);
- }
- }
-
- private boolean isAccessibilityEnabled(Context context) {
- AccessibilityManager accessibilityManager =
- (AccessibilityManager) context.getSystemService(Context.ACCESSIBILITY_SERVICE);
- return accessibilityManager != null && accessibilityManager.isEnabled();
-
- }
- }, ACCESSIBILITY_ANNOUNCEMENT_DELAY_MS);
- }
-
- @Override
- public void setEndCallButtonEnabled(boolean enabled, boolean animate) {
- if (enabled != mFloatingActionButton.isEnabled()) {
- if (animate) {
- if (enabled) {
- mFloatingActionButtonController.scaleIn(AnimUtils.NO_DELAY);
- } else {
- mFloatingActionButtonController.scaleOut();
- }
- } else {
- if (enabled) {
- mFloatingActionButtonContainer.setScaleX(1);
- mFloatingActionButtonContainer.setScaleY(1);
- mFloatingActionButtonContainer.setVisibility(View.VISIBLE);
- } else {
- mFloatingActionButtonContainer.setVisibility(View.GONE);
- }
- }
- mFloatingActionButton.setEnabled(enabled);
- updateFabPosition();
- }
- }
-
- /**
- * Changes the visibility of the HD audio icon.
- *
- * @param visible {@code true} if the UI should show the HD audio icon.
- */
- @Override
- public void showHdAudioIndicator(boolean visible) {
- mHdAudioIcon.setVisibility(visible ? View.VISIBLE : View.GONE);
- }
-
- /**
- * Changes the visibility of the forward icon.
- *
- * @param visible {@code true} if the UI should show the forward icon.
- */
- @Override
- public void showForwardIndicator(boolean visible) {
- mForwardIcon.setVisibility(visible ? View.VISIBLE : View.GONE);
- }
-
- /**
- * Changes the visibility of the spam icon.
- *
- * @param visible {@code true} if the UI should show the spam icon.
- */
- @Override
- public void showSpamIndicator(boolean visible) {
- if (visible) {
- mSpamIcon.setVisibility(View.VISIBLE);
- mNumberLabel.setText(R.string.label_spam_caller);
- mPhoneNumber.setVisibility(View.GONE);
- }
- }
-
- /**
- * Changes the visibility of the "manage conference call" button.
- *
- * @param visible Whether to set the button to be visible or not.
- */
- @Override
- public void showManageConferenceCallButton(boolean visible) {
- mManageConferenceCallButton.setVisibility(visible ? View.VISIBLE : View.GONE);
- }
-
- /**
- * Determines the current visibility of the manage conference button.
- *
- * @return {@code true} if the button is visible.
- */
- @Override
- public boolean isManageConferenceVisible() {
- return mManageConferenceCallButton.getVisibility() == View.VISIBLE;
- }
-
- /**
- * Determines the current visibility of the call subject.
- *
- * @return {@code true} if the subject is visible.
- */
- @Override
- public boolean isCallSubjectVisible() {
- return mCallSubject.getVisibility() == View.VISIBLE;
- }
-
- /**
- * Get the overall InCallUI background colors and apply to call card.
- */
- public void updateColors() {
- MaterialPalette themeColors = InCallPresenter.getInstance().getThemeColors();
-
- if (mCurrentThemeColors != null && mCurrentThemeColors.equals(themeColors)) {
- return;
- }
-
- if (getResources().getBoolean(R.bool.is_layout_landscape)) {
- final GradientDrawable drawable =
- (GradientDrawable) mPrimaryCallCardContainer.getBackground();
- drawable.setColor(themeColors.mPrimaryColor);
- } else {
- mPrimaryCallCardContainer.setBackgroundColor(themeColors.mPrimaryColor);
- }
- mCallButtonsContainer.setBackgroundColor(themeColors.mPrimaryColor);
- mCallSubject.setTextColor(themeColors.mPrimaryColor);
- mContactContext.setBackgroundColor(themeColors.mPrimaryColor);
- //TODO: set color of message text in call context "recent messages" to be the theme color.
-
- mCurrentThemeColors = themeColors;
- }
-
- private void dispatchPopulateAccessibilityEvent(AccessibilityEvent event, View view) {
- if (view == null) return;
- final List eventText = event.getText();
- int size = eventText.size();
- view.dispatchPopulateAccessibilityEvent(event);
- // if no text added write null to keep relative position
- if (size == eventText.size()) {
- eventText.add(null);
- }
- }
-
- @Override
- public void animateForNewOutgoingCall() {
- final ViewGroup parent = (ViewGroup) mPrimaryCallCardContainer.getParent();
-
- final ViewTreeObserver observer = getView().getViewTreeObserver();
-
- mIsAnimating = true;
-
- observer.addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
- @Override
- public void onGlobalLayout() {
- final ViewTreeObserver observer = getView().getViewTreeObserver();
- if (!observer.isAlive()) {
- return;
- }
- observer.removeOnGlobalLayoutListener(this);
-
- final LayoutIgnoringListener listener = new LayoutIgnoringListener();
- mPrimaryCallCardContainer.addOnLayoutChangeListener(listener);
-
- // Prepare the state of views before the slide animation
- final int originalHeight = mPrimaryCallCardContainer.getHeight();
- mPrimaryCallCardContainer.setTag(R.id.view_tag_callcard_actual_height,
- originalHeight);
- mPrimaryCallCardContainer.setBottom(parent.getHeight());
-
- // Set up FAB.
- mFloatingActionButtonContainer.setVisibility(View.GONE);
- mFloatingActionButtonController.setScreenWidth(parent.getWidth());
-
- mCallButtonsContainer.setAlpha(0);
- mCallStateLabel.setAlpha(0);
- mPrimaryName.setAlpha(0);
- mCallTypeLabel.setAlpha(0);
- mCallNumberAndLabel.setAlpha(0);
-
- assignTranslateAnimation(mCallStateLabel, 1);
- assignTranslateAnimation(mCallStateIcon, 1);
- assignTranslateAnimation(mPrimaryName, 2);
- assignTranslateAnimation(mCallNumberAndLabel, 3);
- assignTranslateAnimation(mCallTypeLabel, 4);
- assignTranslateAnimation(mCallButtonsContainer, 5);
-
- final Animator animator = getShrinkAnimator(parent.getHeight(), originalHeight);
-
- animator.addListener(new AnimatorListenerAdapter() {
- @Override
- public void onAnimationEnd(Animator animation) {
- mPrimaryCallCardContainer.setTag(R.id.view_tag_callcard_actual_height,
- null);
- setViewStatePostAnimation(listener);
- mIsAnimating = false;
- InCallPresenter.getInstance().onShrinkAnimationComplete();
- if (animator != null) {
- animator.removeListener(this);
- }
- }
- });
- animator.start();
- }
- });
- }
-
- @Override
- public void showNoteSentToast() {
- Toast.makeText(getContext(), R.string.note_sent, Toast.LENGTH_LONG).show();
- }
-
- public void onDialpadVisibilityChange(boolean isShown) {
- mIsDialpadShowing = isShown;
- updateFabPosition();
- }
-
- private void updateFabPosition() {
- int offsetY = 0;
- if (!mIsDialpadShowing) {
- offsetY = mFloatingActionButtonVerticalOffset;
- if (mSecondaryCallInfo.isShown() && mHasLargePhoto) {
- offsetY -= mSecondaryCallInfo.getHeight();
- }
- }
-
- mFloatingActionButtonController.align(
- FloatingActionButtonController.ALIGN_MIDDLE,
- 0 /* offsetX */,
- offsetY,
- true);
-
- mFloatingActionButtonController.resize(
- mIsDialpadShowing ? mFabSmallDiameter : mFabNormalDiameter, true);
- }
-
- @Override
- public Context getContext() {
- return getActivity();
- }
-
- @Override
- public void onResume() {
- super.onResume();
- // If the previous launch animation is still running, cancel it so that we don't get
- // stuck in an intermediate animation state.
- if (mAnimatorSet != null && mAnimatorSet.isRunning()) {
- mAnimatorSet.cancel();
- }
-
- mIsLandscape = getResources().getBoolean(R.bool.is_layout_landscape);
- mHasLargePhoto = getResources().getBoolean(R.bool.has_large_photo);
-
- final ViewGroup parent = ((ViewGroup) mPrimaryCallCardContainer.getParent());
- final ViewTreeObserver observer = parent.getViewTreeObserver();
- parent.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
- @Override
- public void onGlobalLayout() {
- ViewTreeObserver viewTreeObserver = observer;
- if (!viewTreeObserver.isAlive()) {
- viewTreeObserver = parent.getViewTreeObserver();
- }
- viewTreeObserver.removeOnGlobalLayoutListener(this);
- mFloatingActionButtonController.setScreenWidth(parent.getWidth());
- updateFabPosition();
- }
- });
-
- updateColors();
- }
-
- /**
- * Adds a global layout listener to update the FAB's positioning on the next layout. This allows
- * us to position the FAB after the secondary call info's height has been calculated.
- */
- private void updateFabPositionForSecondaryCallInfo() {
- mSecondaryCallInfo.getViewTreeObserver().addOnGlobalLayoutListener(
- new ViewTreeObserver.OnGlobalLayoutListener() {
- @Override
- public void onGlobalLayout() {
- final ViewTreeObserver observer = mSecondaryCallInfo.getViewTreeObserver();
- if (!observer.isAlive()) {
- return;
- }
- observer.removeOnGlobalLayoutListener(this);
-
- onDialpadVisibilityChange(mIsDialpadShowing);
- }
- });
- }
-
- /**
- * Animator that performs the upwards shrinking animation of the blue call card scrim.
- * At the start of the animation, each child view is moved downwards by a pre-specified amount
- * and then translated upwards together with the scrim.
- */
- private Animator getShrinkAnimator(int startHeight, int endHeight) {
- final ObjectAnimator shrinkAnimator =
- ObjectAnimator.ofInt(mPrimaryCallCardContainer, "bottom", startHeight, endHeight);
- shrinkAnimator.setDuration(mShrinkAnimationDuration);
- shrinkAnimator.addListener(new AnimatorListenerAdapter() {
- @Override
- public void onAnimationStart(Animator animation) {
- mFloatingActionButton.setEnabled(true);
- }
- });
- shrinkAnimator.setInterpolator(AnimUtils.EASE_IN);
- return shrinkAnimator;
- }
-
- private void assignTranslateAnimation(View view, int offset) {
- view.setLayerType(View.LAYER_TYPE_HARDWARE, null);
- view.buildLayer();
- view.setTranslationY(mTranslationOffset * offset);
- view.animate().translationY(0).alpha(1).withLayer()
- .setDuration(mShrinkAnimationDuration).setInterpolator(AnimUtils.EASE_IN);
- }
-
- private void setViewStatePostAnimation(View view) {
- view.setTranslationY(0);
- view.setAlpha(1);
- }
-
- private void setViewStatePostAnimation(OnLayoutChangeListener layoutChangeListener) {
- setViewStatePostAnimation(mCallButtonsContainer);
- setViewStatePostAnimation(mCallStateLabel);
- setViewStatePostAnimation(mPrimaryName);
- setViewStatePostAnimation(mCallTypeLabel);
- setViewStatePostAnimation(mCallNumberAndLabel);
- setViewStatePostAnimation(mCallStateIcon);
-
- mPrimaryCallCardContainer.removeOnLayoutChangeListener(layoutChangeListener);
-
- mFloatingActionButtonController.scaleIn(AnimUtils.NO_DELAY);
- }
-
- private final class LayoutIgnoringListener implements View.OnLayoutChangeListener {
- @Override
- public void onLayoutChange(View v,
- int left,
- int top,
- int right,
- int bottom,
- int oldLeft,
- int oldTop,
- int oldRight,
- int oldBottom) {
- v.setLeft(oldLeft);
- v.setRight(oldRight);
- v.setTop(oldTop);
- v.setBottom(oldBottom);
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallCardPresenter.java b/InCallUI/src/com/android/incallui/CallCardPresenter.java
deleted file mode 100644
index 1ad0c11f17714723924a636c221af793ca5deea8..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallCardPresenter.java
+++ /dev/null
@@ -1,1181 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import android.Manifest;
-import android.content.Context;
-import android.content.Intent;
-import android.content.pm.ApplicationInfo;
-import android.content.pm.PackageManager;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.os.Bundle;
-import android.support.annotation.Nullable;
-import android.telecom.Call.Details;
-import android.telecom.DisconnectCause;
-import android.telecom.PhoneAccount;
-import android.telecom.PhoneAccountHandle;
-import android.telecom.StatusHints;
-import android.telecom.TelecomManager;
-import android.telecom.VideoProfile;
-import android.telephony.PhoneNumberUtils;
-import android.text.TextUtils;
-import android.view.View;
-import android.view.accessibility.AccessibilityManager;
-import android.widget.ListAdapter;
-
-import com.android.contacts.common.ContactsUtils;
-import com.android.contacts.common.compat.telecom.TelecomManagerCompat;
-import com.android.contacts.common.preference.ContactsPreferences;
-import com.android.contacts.common.testing.NeededForTesting;
-import com.android.contacts.common.util.ContactDisplayUtils;
-import com.android.dialer.R;
-import com.android.incallui.Call.State;
-import com.android.incallui.ContactInfoCache.ContactCacheEntry;
-import com.android.incallui.ContactInfoCache.ContactInfoCacheCallback;
-import com.android.incallui.InCallPresenter.InCallDetailsListener;
-import com.android.incallui.InCallPresenter.InCallEventListener;
-import com.android.incallui.InCallPresenter.InCallState;
-import com.android.incallui.InCallPresenter.InCallStateListener;
-import com.android.incallui.InCallPresenter.IncomingCallListener;
-import com.android.incalluibind.ObjectFactory;
-
-import java.lang.ref.WeakReference;
-
-import static com.android.contacts.common.compat.CallSdkCompat.Details.PROPERTY_ENTERPRISE_CALL;
-/**
- * Presenter for the Call Card Fragment.
- *
- * This class listens for changes to InCallState and passes it along to the fragment.
- */
-public class CallCardPresenter extends Presenter
- implements InCallStateListener, IncomingCallListener, InCallDetailsListener,
- InCallEventListener, CallList.CallUpdateListener, DistanceHelper.Listener {
-
- public interface EmergencyCallListener {
- public void onCallUpdated(BaseFragment fragment, boolean isEmergency);
- }
-
- private static final String TAG = CallCardPresenter.class.getSimpleName();
- private static final long CALL_TIME_UPDATE_INTERVAL_MS = 1000;
-
- private final EmergencyCallListener mEmergencyCallListener =
- ObjectFactory.newEmergencyCallListener();
- private DistanceHelper mDistanceHelper;
-
- private Call mPrimary;
- private Call mSecondary;
- private ContactCacheEntry mPrimaryContactInfo;
- private ContactCacheEntry mSecondaryContactInfo;
- private CallTimer mCallTimer;
- private Context mContext;
- @Nullable private ContactsPreferences mContactsPreferences;
- private boolean mSpinnerShowing = false;
- private boolean mHasShownToast = false;
- private InCallContactInteractions mInCallContactInteractions;
- private boolean mIsFullscreen = false;
-
- public static class ContactLookupCallback implements ContactInfoCacheCallback {
- private final WeakReference mCallCardPresenter;
- private final boolean mIsPrimary;
-
- public ContactLookupCallback(CallCardPresenter callCardPresenter, boolean isPrimary) {
- mCallCardPresenter = new WeakReference(callCardPresenter);
- mIsPrimary = isPrimary;
- }
-
- @Override
- public void onContactInfoComplete(String callId, ContactCacheEntry entry) {
- CallCardPresenter presenter = mCallCardPresenter.get();
- if (presenter != null) {
- presenter.onContactInfoComplete(callId, entry, mIsPrimary);
- }
- }
-
- @Override
- public void onImageLoadComplete(String callId, ContactCacheEntry entry) {
- CallCardPresenter presenter = mCallCardPresenter.get();
- if (presenter != null) {
- presenter.onImageLoadComplete(callId, entry);
- }
- }
-
- @Override
- public void onContactInteractionsInfoComplete(String callId, ContactCacheEntry entry) {
- CallCardPresenter presenter = mCallCardPresenter.get();
- if (presenter != null) {
- presenter.onContactInteractionsInfoComplete(callId, entry);
- }
- }
- }
-
- public CallCardPresenter() {
- // create the call timer
- mCallTimer = new CallTimer(new Runnable() {
- @Override
- public void run() {
- updateCallTime();
- }
- });
- }
-
- public void init(Context context, Call call) {
- mContext = Preconditions.checkNotNull(context);
- mDistanceHelper = ObjectFactory.newDistanceHelper(mContext, this);
- mContactsPreferences = ContactsPreferencesFactory.newContactsPreferences(mContext);
-
- // Call may be null if disconnect happened already.
- if (call != null) {
- mPrimary = call;
- if (shouldShowNoteSentToast(mPrimary)) {
- final CallCardUi ui = getUi();
- if (ui != null) {
- ui.showNoteSentToast();
- }
- }
- CallList.getInstance().addCallUpdateListener(call.getId(), this);
-
- // start processing lookups right away.
- if (!call.isConferenceCall()) {
- startContactInfoSearch(call, true, call.getState() == Call.State.INCOMING);
- } else {
- updateContactEntry(null, true);
- }
- }
-
- onStateChange(null, InCallPresenter.getInstance().getInCallState(), CallList.getInstance());
- }
-
- @Override
- public void onUiReady(CallCardUi ui) {
- super.onUiReady(ui);
-
- if (mContactsPreferences != null) {
- mContactsPreferences.refreshValue(ContactsPreferences.DISPLAY_ORDER_KEY);
- }
-
- // Contact search may have completed before ui is ready.
- if (mPrimaryContactInfo != null) {
- updatePrimaryDisplayInfo();
- }
-
- // Register for call state changes last
- InCallPresenter.getInstance().addListener(this);
- InCallPresenter.getInstance().addIncomingCallListener(this);
- InCallPresenter.getInstance().addDetailsListener(this);
- InCallPresenter.getInstance().addInCallEventListener(this);
- }
-
- @Override
- public void onUiUnready(CallCardUi ui) {
- super.onUiUnready(ui);
-
- // stop getting call state changes
- InCallPresenter.getInstance().removeListener(this);
- InCallPresenter.getInstance().removeIncomingCallListener(this);
- InCallPresenter.getInstance().removeDetailsListener(this);
- InCallPresenter.getInstance().removeInCallEventListener(this);
- if (mPrimary != null) {
- CallList.getInstance().removeCallUpdateListener(mPrimary.getId(), this);
- }
-
- if (mDistanceHelper != null) {
- mDistanceHelper.cleanUp();
- }
-
- mPrimary = null;
- mPrimaryContactInfo = null;
- mSecondaryContactInfo = null;
- }
-
- @Override
- public void onIncomingCall(InCallState oldState, InCallState newState, Call call) {
- // same logic should happen as with onStateChange()
- onStateChange(oldState, newState, CallList.getInstance());
- }
-
- @Override
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList) {
- Log.d(this, "onStateChange() " + newState);
- final CallCardUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- Call primary = null;
- Call secondary = null;
-
- if (newState == InCallState.INCOMING) {
- primary = callList.getIncomingCall();
- } else if (newState == InCallState.PENDING_OUTGOING || newState == InCallState.OUTGOING) {
- primary = callList.getOutgoingCall();
- if (primary == null) {
- primary = callList.getPendingOutgoingCall();
- }
-
- // getCallToDisplay doesn't go through outgoing or incoming calls. It will return the
- // highest priority call to display as the secondary call.
- secondary = getCallToDisplay(callList, null, true);
- } else if (newState == InCallState.INCALL) {
- primary = getCallToDisplay(callList, null, false);
- secondary = getCallToDisplay(callList, primary, true);
- }
-
- if (mInCallContactInteractions != null &&
- (oldState == InCallState.INCOMING || newState == InCallState.INCOMING)) {
- ui.showContactContext(newState != InCallState.INCOMING);
- }
-
- Log.d(this, "Primary call: " + primary);
- Log.d(this, "Secondary call: " + secondary);
-
- final boolean primaryChanged = !(Call.areSame(mPrimary, primary) &&
- Call.areSameNumber(mPrimary, primary));
- final boolean secondaryChanged = !(Call.areSame(mSecondary, secondary) &&
- Call.areSameNumber(mSecondary, secondary));
-
- mSecondary = secondary;
- Call previousPrimary = mPrimary;
- mPrimary = primary;
-
- if (primaryChanged && shouldShowNoteSentToast(primary)) {
- ui.showNoteSentToast();
- }
-
- // Refresh primary call information if either:
- // 1. Primary call changed.
- // 2. The call's ability to manage conference has changed.
- // 3. The call subject should be shown or hidden.
- if (shouldRefreshPrimaryInfo(primaryChanged, ui, shouldShowCallSubject(mPrimary))) {
- // primary call has changed
- if (previousPrimary != null) {
- //clear progess spinner (if any) related to previous primary call
- maybeShowProgressSpinner(previousPrimary.getState(),
- Call.SessionModificationState.NO_REQUEST);
- CallList.getInstance().removeCallUpdateListener(previousPrimary.getId(), this);
- }
- CallList.getInstance().addCallUpdateListener(mPrimary.getId(), this);
-
- mPrimaryContactInfo = ContactInfoCache.buildCacheEntryFromCall(mContext, mPrimary,
- mPrimary.getState() == Call.State.INCOMING);
- updatePrimaryDisplayInfo();
- maybeStartSearch(mPrimary, true);
- maybeClearSessionModificationState(mPrimary);
- }
-
- if (previousPrimary != null && mPrimary == null) {
- //clear progess spinner (if any) related to previous primary call
- maybeShowProgressSpinner(previousPrimary.getState(),
- Call.SessionModificationState.NO_REQUEST);
- CallList.getInstance().removeCallUpdateListener(previousPrimary.getId(), this);
- }
-
- if (mSecondary == null) {
- // Secondary call may have ended. Update the ui.
- mSecondaryContactInfo = null;
- updateSecondaryDisplayInfo();
- } else if (secondaryChanged) {
- // secondary call has changed
- mSecondaryContactInfo = ContactInfoCache.buildCacheEntryFromCall(mContext, mSecondary,
- mSecondary.getState() == Call.State.INCOMING);
- updateSecondaryDisplayInfo();
- maybeStartSearch(mSecondary, false);
- maybeClearSessionModificationState(mSecondary);
- }
-
- // Start/stop timers.
- if (isPrimaryCallActive()) {
- Log.d(this, "Starting the calltime timer");
- mCallTimer.start(CALL_TIME_UPDATE_INTERVAL_MS);
- } else {
- Log.d(this, "Canceling the calltime timer");
- mCallTimer.cancel();
- ui.setPrimaryCallElapsedTime(false, 0);
- }
-
- // Set the call state
- int callState = Call.State.IDLE;
- if (mPrimary != null) {
- callState = mPrimary.getState();
- updatePrimaryCallState();
- } else {
- getUi().setCallState(
- callState,
- VideoProfile.STATE_AUDIO_ONLY,
- Call.SessionModificationState.NO_REQUEST,
- new DisconnectCause(DisconnectCause.UNKNOWN),
- null,
- null,
- null,
- false /* isWifi */,
- false /* isConference */,
- false /* isWorkCall */);
- getUi().showHdAudioIndicator(false);
- }
-
- maybeShowManageConferenceCallButton();
-
- // Hide the end call button instantly if we're receiving an incoming call.
- getUi().setEndCallButtonEnabled(shouldShowEndCallButton(mPrimary, callState),
- callState != Call.State.INCOMING /* animate */);
-
- maybeSendAccessibilityEvent(oldState, newState, primaryChanged);
- }
-
- @Override
- public void onDetailsChanged(Call call, Details details) {
- updatePrimaryCallState();
-
- if (call.can(Details.CAPABILITY_MANAGE_CONFERENCE) !=
- details.can(Details.CAPABILITY_MANAGE_CONFERENCE)) {
- maybeShowManageConferenceCallButton();
- }
- }
-
- @Override
- public void onCallChanged(Call call) {
- // No-op; specific call updates handled elsewhere.
- }
-
- /**
- * Handles a change to the session modification state for a call. Triggers showing the progress
- * spinner, as well as updating the call state label.
- *
- * @param sessionModificationState The new session modification state.
- */
- @Override
- public void onSessionModificationStateChange(int sessionModificationState) {
- Log.d(this, "onSessionModificationStateChange : sessionModificationState = " +
- sessionModificationState);
-
- if (mPrimary == null) {
- return;
- }
- maybeShowProgressSpinner(mPrimary.getState(), sessionModificationState);
- getUi().setEndCallButtonEnabled(sessionModificationState !=
- Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST,
- true /* shouldAnimate */);
- updatePrimaryCallState();
- }
-
- /**
- * Handles a change to the last forwarding number by refreshing the primary call info.
- */
- @Override
- public void onLastForwardedNumberChange() {
- Log.v(this, "onLastForwardedNumberChange");
-
- if (mPrimary == null) {
- return;
- }
- updatePrimaryDisplayInfo();
- }
-
- /**
- * Handles a change to the child number by refreshing the primary call info.
- */
- @Override
- public void onChildNumberChange() {
- Log.v(this, "onChildNumberChange");
-
- if (mPrimary == null) {
- return;
- }
- updatePrimaryDisplayInfo();
- }
-
- private boolean shouldRefreshPrimaryInfo(boolean primaryChanged, CallCardUi ui,
- boolean shouldShowCallSubject) {
- if (mPrimary == null) {
- return false;
- }
- return primaryChanged ||
- ui.isManageConferenceVisible() != shouldShowManageConference() ||
- ui.isCallSubjectVisible() != shouldShowCallSubject;
- }
-
- private String getSubscriptionNumber() {
- // If it's an emergency call, and they're not populating the callback number,
- // then try to fall back to the phone sub info (to hopefully get the SIM's
- // number directly from the telephony layer).
- PhoneAccountHandle accountHandle = mPrimary.getAccountHandle();
- if (accountHandle != null) {
- TelecomManager mgr = InCallPresenter.getInstance().getTelecomManager();
- PhoneAccount account = TelecomManagerCompat.getPhoneAccount(mgr, accountHandle);
- if (account != null) {
- return getNumberFromHandle(account.getSubscriptionAddress());
- }
- }
- return null;
- }
-
- private void updatePrimaryCallState() {
- if (getUi() != null && mPrimary != null) {
- boolean isWorkCall = mPrimary.hasProperty(PROPERTY_ENTERPRISE_CALL)
- || (mPrimaryContactInfo == null ? false
- : mPrimaryContactInfo.userType == ContactsUtils.USER_TYPE_WORK);
- getUi().setCallState(
- mPrimary.getState(),
- mPrimary.getVideoState(),
- mPrimary.getSessionModificationState(),
- mPrimary.getDisconnectCause(),
- getConnectionLabel(),
- getCallStateIcon(),
- getGatewayNumber(),
- mPrimary.hasProperty(Details.PROPERTY_WIFI),
- mPrimary.isConferenceCall(),
- isWorkCall);
-
- maybeShowHdAudioIcon();
- setCallbackNumber();
- }
- }
-
- /**
- * Show the HD icon if the call is active and has {@link Details#PROPERTY_HIGH_DEF_AUDIO},
- * except if the call has a last forwarded number (we will show that icon instead).
- */
- private void maybeShowHdAudioIcon() {
- boolean showHdAudioIndicator =
- isPrimaryCallActive() && mPrimary.hasProperty(Details.PROPERTY_HIGH_DEF_AUDIO) &&
- TextUtils.isEmpty(mPrimary.getLastForwardedNumber());
- getUi().showHdAudioIndicator(showHdAudioIndicator);
- }
-
- private void maybeShowSpamIconAndLabel() {
- getUi().showSpamIndicator(mPrimary.isSpam());
- }
-
- /**
- * Only show the conference call button if we can manage the conference.
- */
- private void maybeShowManageConferenceCallButton() {
- getUi().showManageConferenceCallButton(shouldShowManageConference());
- }
-
- /**
- * Determines if a pending session modification exists for the current call. If so, the
- * progress spinner is shown, and the call state is updated.
- *
- * @param callState The call state.
- * @param sessionModificationState The session modification state.
- */
- private void maybeShowProgressSpinner(int callState, int sessionModificationState) {
- final boolean show = sessionModificationState ==
- Call.SessionModificationState.WAITING_FOR_RESPONSE
- && callState == Call.State.ACTIVE;
- if (show != mSpinnerShowing) {
- getUi().setProgressSpinnerVisible(show);
- mSpinnerShowing = show;
- }
- }
-
- /**
- * Determines if the manage conference button should be visible, based on the current primary
- * call.
- *
- * @return {@code True} if the manage conference button should be visible.
- */
- private boolean shouldShowManageConference() {
- if (mPrimary == null) {
- return false;
- }
-
- return mPrimary.can(android.telecom.Call.Details.CAPABILITY_MANAGE_CONFERENCE)
- && !mIsFullscreen;
- }
-
- private void setCallbackNumber() {
- String callbackNumber = null;
-
- // Show the emergency callback number if either:
- // 1. This is an emergency call.
- // 2. The phone is in Emergency Callback Mode, which means we should show the callback
- // number.
- boolean showCallbackNumber = mPrimary.hasProperty(Details.PROPERTY_EMERGENCY_CALLBACK_MODE);
-
- if (mPrimary.isEmergencyCall() || showCallbackNumber) {
- callbackNumber = getSubscriptionNumber();
- } else {
- StatusHints statusHints = mPrimary.getTelecomCall().getDetails().getStatusHints();
- if (statusHints != null) {
- Bundle extras = statusHints.getExtras();
- if (extras != null) {
- callbackNumber = extras.getString(TelecomManager.EXTRA_CALL_BACK_NUMBER);
- }
- }
- }
-
- final String simNumber = TelecomManagerCompat.getLine1Number(
- InCallPresenter.getInstance().getTelecomManager(),
- InCallPresenter.getInstance().getTelephonyManager(),
- mPrimary.getAccountHandle());
- if (!showCallbackNumber && PhoneNumberUtils.compare(callbackNumber, simNumber)) {
- Log.d(this, "Numbers are the same (and callback number is not being forced to show);" +
- " not showing the callback number");
- callbackNumber = null;
- }
-
- getUi().setCallbackNumber(callbackNumber, mPrimary.isEmergencyCall() || showCallbackNumber);
- }
-
- public void updateCallTime() {
- final CallCardUi ui = getUi();
-
- if (ui == null) {
- mCallTimer.cancel();
- } else if (!isPrimaryCallActive()) {
- ui.setPrimaryCallElapsedTime(false, 0);
- mCallTimer.cancel();
- } else {
- final long callStart = mPrimary.getConnectTimeMillis();
- if (callStart > 0) {
- final long duration = System.currentTimeMillis() - callStart;
- ui.setPrimaryCallElapsedTime(true, duration);
- }
- }
- }
-
- public void onCallStateButtonTouched() {
- Intent broadcastIntent = ObjectFactory.getCallStateButtonBroadcastIntent(mContext);
- if (broadcastIntent != null) {
- Log.d(this, "Sending call state button broadcast: ", broadcastIntent);
- mContext.sendBroadcast(broadcastIntent, Manifest.permission.READ_PHONE_STATE);
- }
- }
-
- /**
- * Handles click on the contact photo by toggling fullscreen mode if the current call is a video
- * call.
- */
- public void onContactPhotoClick() {
- if (mPrimary != null && mPrimary.isVideoCall(mContext)) {
- InCallPresenter.getInstance().toggleFullscreenMode();
- }
- }
-
- private void maybeStartSearch(Call call, boolean isPrimary) {
- // no need to start search for conference calls which show generic info.
- if (call != null && !call.isConferenceCall()) {
- startContactInfoSearch(call, isPrimary, call.getState() == Call.State.INCOMING);
- }
- }
-
- private void maybeClearSessionModificationState(Call call) {
- if (call.getSessionModificationState() !=
- Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- call.setSessionModificationState(Call.SessionModificationState.NO_REQUEST);
- }
- }
-
- /**
- * Starts a query for more contact data for the save primary and secondary calls.
- */
- private void startContactInfoSearch(final Call call, final boolean isPrimary,
- boolean isIncoming) {
- final ContactInfoCache cache = ContactInfoCache.getInstance(mContext);
-
- cache.findInfo(call, isIncoming, new ContactLookupCallback(this, isPrimary));
- }
-
- private void onContactInfoComplete(String callId, ContactCacheEntry entry, boolean isPrimary) {
- final boolean entryMatchesExistingCall =
- (isPrimary && mPrimary != null && TextUtils.equals(callId, mPrimary.getId())) ||
- (!isPrimary && mSecondary != null && TextUtils.equals(callId, mSecondary.getId()));
- if (entryMatchesExistingCall) {
- updateContactEntry(entry, isPrimary);
- } else {
- Log.w(this, "Dropping stale contact lookup info for " + callId);
- }
-
- final Call call = CallList.getInstance().getCallById(callId);
- if (call != null) {
- call.getLogState().contactLookupResult = entry.contactLookupResult;
- }
- if (entry.contactUri != null) {
- CallerInfoUtils.sendViewNotification(mContext, entry.contactUri);
- }
- }
-
- private void onImageLoadComplete(String callId, ContactCacheEntry entry) {
- if (getUi() == null) {
- return;
- }
-
- if (entry.photo != null) {
- if (mPrimary != null && callId.equals(mPrimary.getId())) {
- boolean showContactPhoto = !VideoCallPresenter.showIncomingVideo(
- mPrimary.getVideoState(), mPrimary.getState());
- getUi().setPrimaryImage(entry.photo, showContactPhoto);
- }
- }
- }
-
- private void onContactInteractionsInfoComplete(String callId, ContactCacheEntry entry) {
- if (getUi() == null) {
- return;
- }
-
- if (mPrimary != null && callId.equals(mPrimary.getId())) {
- mPrimaryContactInfo.locationAddress = entry.locationAddress;
- updateContactInteractions();
- }
- }
-
- @Override
- public void onLocationReady() {
- // This will only update the contacts interactions data if the location returns after
- // the contact information is found.
- updateContactInteractions();
- }
-
- private void updateContactInteractions() {
- if (mPrimary != null && mPrimaryContactInfo != null
- && (mPrimaryContactInfo.locationAddress != null
- || mPrimaryContactInfo.openingHours != null)) {
- // TODO: This is hardcoded to "isBusiness" because functionality to differentiate
- // between business and personal has not yet been added.
- if (setInCallContactInteractionsType(true /* isBusiness */)) {
- getUi().setContactContextTitle(
- mInCallContactInteractions.getBusinessListHeaderView());
- }
-
- mInCallContactInteractions.setBusinessInfo(
- mPrimaryContactInfo.locationAddress,
- mDistanceHelper.calculateDistance(mPrimaryContactInfo.locationAddress),
- mPrimaryContactInfo.openingHours);
- getUi().setContactContextContent(mInCallContactInteractions.getListAdapter());
- getUi().showContactContext(mPrimary.getState() != State.INCOMING);
- } else {
- getUi().showContactContext(false);
- }
- }
-
- /**
- * Update the contact interactions type so that the correct UI is shown.
- *
- * @param isBusiness {@code true} if the interaction is a business interaction, {@code false} if
- * it is a personal contact.
- *
- * @return {@code true} if this is a new type of contact interaction (business or personal).
- * {@code false} if it hasn't changed.
- */
- private boolean setInCallContactInteractionsType(boolean isBusiness) {
- if (mInCallContactInteractions == null) {
- mInCallContactInteractions =
- new InCallContactInteractions(mContext, isBusiness);
- return true;
- }
-
- return mInCallContactInteractions.switchContactType(isBusiness);
- }
-
- private void updateContactEntry(ContactCacheEntry entry, boolean isPrimary) {
- if (isPrimary) {
- mPrimaryContactInfo = entry;
- updatePrimaryDisplayInfo();
- } else {
- mSecondaryContactInfo = entry;
- updateSecondaryDisplayInfo();
- }
- }
-
- /**
- * Get the highest priority call to display.
- * Goes through the calls and chooses which to return based on priority of which type of call
- * to display to the user. Callers can use the "ignore" feature to get the second best call
- * by passing a previously found primary call as ignore.
- *
- * @param ignore A call to ignore if found.
- */
- private Call getCallToDisplay(CallList callList, Call ignore, boolean skipDisconnected) {
- // Active calls come second. An active call always gets precedent.
- Call retval = callList.getActiveCall();
- if (retval != null && retval != ignore) {
- return retval;
- }
-
- // Sometimes there is intemediate state that two calls are in active even one is about
- // to be on hold.
- retval = callList.getSecondActiveCall();
- if (retval != null && retval != ignore) {
- return retval;
- }
-
- // Disconnected calls get primary position if there are no active calls
- // to let user know quickly what call has disconnected. Disconnected
- // calls are very short lived.
- if (!skipDisconnected) {
- retval = callList.getDisconnectingCall();
- if (retval != null && retval != ignore) {
- return retval;
- }
- retval = callList.getDisconnectedCall();
- if (retval != null && retval != ignore) {
- return retval;
- }
- }
-
- // Then we go to background call (calls on hold)
- retval = callList.getBackgroundCall();
- if (retval != null && retval != ignore) {
- return retval;
- }
-
- // Lastly, we go to a second background call.
- retval = callList.getSecondBackgroundCall();
-
- return retval;
- }
-
- private void updatePrimaryDisplayInfo() {
- final CallCardUi ui = getUi();
- if (ui == null) {
- // TODO: May also occur if search result comes back after ui is destroyed. Look into
- // removing that case completely.
- Log.d(TAG, "updatePrimaryDisplayInfo called but ui is null!");
- return;
- }
-
- if (mPrimary == null) {
- // Clear the primary display info.
- ui.setPrimary(null, null, false, null, null, false, false, false);
- return;
- }
-
- // Hide the contact photo if we are in a video call and the incoming video surface is
- // showing.
- boolean showContactPhoto = !VideoCallPresenter
- .showIncomingVideo(mPrimary.getVideoState(), mPrimary.getState());
-
- // Call placed through a work phone account.
- boolean hasWorkCallProperty = mPrimary.hasProperty(PROPERTY_ENTERPRISE_CALL);
-
- if (mPrimary.isConferenceCall()) {
- Log.d(TAG, "Update primary display info for conference call.");
-
- ui.setPrimary(
- null /* number */,
- getConferenceString(mPrimary),
- false /* nameIsNumber */,
- null /* label */,
- getConferencePhoto(mPrimary),
- false /* isSipCall */,
- showContactPhoto,
- hasWorkCallProperty);
- } else if (mPrimaryContactInfo != null) {
- Log.d(TAG, "Update primary display info for " + mPrimaryContactInfo);
-
- String name = getNameForCall(mPrimaryContactInfo);
- String number;
-
- boolean isChildNumberShown = !TextUtils.isEmpty(mPrimary.getChildNumber());
- boolean isForwardedNumberShown = !TextUtils.isEmpty(mPrimary.getLastForwardedNumber());
- boolean isCallSubjectShown = shouldShowCallSubject(mPrimary);
-
- if (isCallSubjectShown) {
- ui.setCallSubject(mPrimary.getCallSubject());
- } else {
- ui.setCallSubject(null);
- }
-
- if (isCallSubjectShown) {
- number = null;
- } else if (isChildNumberShown) {
- number = mContext.getString(R.string.child_number, mPrimary.getChildNumber());
- } else if (isForwardedNumberShown) {
- // Use last forwarded number instead of second line, if present.
- number = mPrimary.getLastForwardedNumber();
- } else {
- number = getNumberForCall(mPrimaryContactInfo);
- }
-
- ui.showForwardIndicator(isForwardedNumberShown);
- maybeShowHdAudioIcon();
-
- boolean nameIsNumber = name != null && name.equals(mPrimaryContactInfo.number);
- // Call with caller that is a work contact.
- boolean isWorkContact = (mPrimaryContactInfo.userType == ContactsUtils.USER_TYPE_WORK);
- ui.setPrimary(
- number,
- name,
- nameIsNumber,
- isChildNumberShown || isCallSubjectShown ? null : mPrimaryContactInfo.label,
- mPrimaryContactInfo.photo,
- mPrimaryContactInfo.isSipCall,
- showContactPhoto,
- hasWorkCallProperty || isWorkContact);
-
- updateContactInteractions();
- } else {
- // Clear the primary display info.
- ui.setPrimary(null, null, false, null, null, false, false, false);
- }
-
- if (mEmergencyCallListener != null) {
- boolean isEmergencyCall = mPrimary.isEmergencyCall();
- mEmergencyCallListener.onCallUpdated((BaseFragment) ui, isEmergencyCall);
- }
- maybeShowSpamIconAndLabel();
- }
-
- private void updateSecondaryDisplayInfo() {
- final CallCardUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- if (mSecondary == null) {
- // Clear the secondary display info.
- ui.setSecondary(false, null, false, null, null, false /* isConference */,
- false /* isVideoCall */, mIsFullscreen);
- return;
- }
-
- if (mSecondary.isConferenceCall()) {
- ui.setSecondary(
- true /* show */,
- getConferenceString(mSecondary),
- false /* nameIsNumber */,
- null /* label */,
- getCallProviderLabel(mSecondary),
- true /* isConference */,
- mSecondary.isVideoCall(mContext),
- mIsFullscreen);
- } else if (mSecondaryContactInfo != null) {
- Log.d(TAG, "updateSecondaryDisplayInfo() " + mSecondaryContactInfo);
- String name = getNameForCall(mSecondaryContactInfo);
- boolean nameIsNumber = name != null && name.equals(mSecondaryContactInfo.number);
- ui.setSecondary(
- true /* show */,
- name,
- nameIsNumber,
- mSecondaryContactInfo.label,
- getCallProviderLabel(mSecondary),
- false /* isConference */,
- mSecondary.isVideoCall(mContext),
- mIsFullscreen);
- } else {
- // Clear the secondary display info.
- ui.setSecondary(false, null, false, null, null, false /* isConference */,
- false /* isVideoCall */, mIsFullscreen);
- }
- }
-
-
- /**
- * Gets the phone account to display for a call.
- */
- private PhoneAccount getAccountForCall(Call call) {
- PhoneAccountHandle accountHandle = call.getAccountHandle();
- if (accountHandle == null) {
- return null;
- }
- return TelecomManagerCompat.getPhoneAccount(
- InCallPresenter.getInstance().getTelecomManager(),
- accountHandle);
- }
-
- /**
- * Returns the gateway number for any existing outgoing call.
- */
- private String getGatewayNumber() {
- if (hasOutgoingGatewayCall()) {
- return getNumberFromHandle(mPrimary.getGatewayInfo().getGatewayAddress());
- }
- return null;
- }
-
- /**
- * Return the string label to represent the call provider
- */
- private String getCallProviderLabel(Call call) {
- PhoneAccount account = getAccountForCall(call);
- TelecomManager mgr = InCallPresenter.getInstance().getTelecomManager();
- if (account != null && !TextUtils.isEmpty(account.getLabel())
- && TelecomManagerCompat.getCallCapablePhoneAccounts(mgr).size() > 1) {
- return account.getLabel().toString();
- }
- return null;
- }
-
- /**
- * Returns the label (line of text above the number/name) for any given call.
- * For example, "calling via [Account/Google Voice]" for outgoing calls.
- */
- private String getConnectionLabel() {
- StatusHints statusHints = mPrimary.getTelecomCall().getDetails().getStatusHints();
- if (statusHints != null && !TextUtils.isEmpty(statusHints.getLabel())) {
- return statusHints.getLabel().toString();
- }
-
- if (hasOutgoingGatewayCall() && getUi() != null) {
- // Return the label for the gateway app on outgoing calls.
- final PackageManager pm = mContext.getPackageManager();
- try {
- ApplicationInfo info = pm.getApplicationInfo(
- mPrimary.getGatewayInfo().getGatewayProviderPackageName(), 0);
- return pm.getApplicationLabel(info).toString();
- } catch (PackageManager.NameNotFoundException e) {
- Log.e(this, "Gateway Application Not Found.", e);
- return null;
- }
- }
- return getCallProviderLabel(mPrimary);
- }
-
- private Drawable getCallStateIcon() {
- // Return connection icon if one exists.
- StatusHints statusHints = mPrimary.getTelecomCall().getDetails().getStatusHints();
- if (statusHints != null && statusHints.getIcon() != null) {
- Drawable icon = statusHints.getIcon().loadDrawable(mContext);
- if (icon != null) {
- return icon;
- }
- }
-
- return null;
- }
-
- private boolean hasOutgoingGatewayCall() {
- // We only display the gateway information while STATE_DIALING so return false for any other
- // call state.
- // TODO: mPrimary can be null because this is called from updatePrimaryDisplayInfo which
- // is also called after a contact search completes (call is not present yet). Split the
- // UI update so it can receive independent updates.
- if (mPrimary == null) {
- return false;
- }
- return Call.State.isDialing(mPrimary.getState()) && mPrimary.getGatewayInfo() != null &&
- !mPrimary.getGatewayInfo().isEmpty();
- }
-
- /**
- * Gets the name to display for the call.
- */
- @NeededForTesting
- String getNameForCall(ContactCacheEntry contactInfo) {
- String preferredName = ContactDisplayUtils.getPreferredDisplayName(
- contactInfo.namePrimary,
- contactInfo.nameAlternative,
- mContactsPreferences);
- if (TextUtils.isEmpty(preferredName)) {
- return contactInfo.number;
- }
- return preferredName;
- }
-
- /**
- * Gets the number to display for a call.
- */
- @NeededForTesting
- String getNumberForCall(ContactCacheEntry contactInfo) {
- // If the name is empty, we use the number for the name...so don't show a second
- // number in the number field
- String preferredName = ContactDisplayUtils.getPreferredDisplayName(
- contactInfo.namePrimary,
- contactInfo.nameAlternative,
- mContactsPreferences);
- if (TextUtils.isEmpty(preferredName)) {
- return contactInfo.location;
- }
- return contactInfo.number;
- }
-
- public void secondaryInfoClicked() {
- if (mSecondary == null) {
- Log.w(this, "Secondary info clicked but no secondary call.");
- return;
- }
-
- Log.i(this, "Swapping call to foreground: " + mSecondary);
- TelecomAdapter.getInstance().unholdCall(mSecondary.getId());
- }
-
- public void endCallClicked() {
- if (mPrimary == null) {
- return;
- }
-
- Log.i(this, "Disconnecting call: " + mPrimary);
- final String callId = mPrimary.getId();
- mPrimary.setState(Call.State.DISCONNECTING);
- CallList.getInstance().onUpdate(mPrimary);
- TelecomAdapter.getInstance().disconnectCall(callId);
- }
-
- private String getNumberFromHandle(Uri handle) {
- return handle == null ? "" : handle.getSchemeSpecificPart();
- }
-
- /**
- * Handles a change to the fullscreen mode of the in-call UI.
- *
- * @param isFullscreenMode {@code True} if the in-call UI is entering full screen mode.
- */
- @Override
- public void onFullscreenModeChanged(boolean isFullscreenMode) {
- mIsFullscreen = isFullscreenMode;
- final CallCardUi ui = getUi();
- if (ui == null) {
- return;
- }
- ui.setCallCardVisible(!isFullscreenMode);
- ui.setSecondaryInfoVisible(!isFullscreenMode);
- maybeShowManageConferenceCallButton();
- }
-
- @Override
- public void onSecondaryCallerInfoVisibilityChanged(boolean isVisible, int height) {
- // No-op - the Call Card is the origin of this event.
- }
-
- private boolean isPrimaryCallActive() {
- return mPrimary != null && mPrimary.getState() == Call.State.ACTIVE;
- }
-
- private String getConferenceString(Call call) {
- boolean isGenericConference = call.hasProperty(Details.PROPERTY_GENERIC_CONFERENCE);
- Log.v(this, "getConferenceString: " + isGenericConference);
-
- final int resId = isGenericConference
- ? R.string.card_title_in_call : R.string.card_title_conf_call;
- return mContext.getResources().getString(resId);
- }
-
- private Drawable getConferencePhoto(Call call) {
- boolean isGenericConference = call.hasProperty(Details.PROPERTY_GENERIC_CONFERENCE);
- Log.v(this, "getConferencePhoto: " + isGenericConference);
-
- final int resId = isGenericConference
- ? R.drawable.img_phone : R.drawable.img_conference;
- Drawable photo = mContext.getResources().getDrawable(resId);
- photo.setAutoMirrored(true);
- return photo;
- }
-
- private boolean shouldShowEndCallButton(Call primary, int callState) {
- if (primary == null) {
- return false;
- }
- if ((!Call.State.isConnectingOrConnected(callState)
- && callState != Call.State.DISCONNECTING) || callState == Call.State.INCOMING) {
- return false;
- }
- if (mPrimary.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- return false;
- }
- return true;
- }
-
- private void maybeSendAccessibilityEvent(InCallState oldState, InCallState newState,
- boolean primaryChanged) {
- if (mContext == null) {
- return;
- }
- final AccessibilityManager am = (AccessibilityManager) mContext.getSystemService(
- Context.ACCESSIBILITY_SERVICE);
- if (!am.isEnabled()) {
- return;
- }
- // Announce the current call if it's new incoming/outgoing call or primary call is changed
- // due to switching calls between two ongoing calls (one is on hold).
- if ((oldState != InCallState.OUTGOING && newState == InCallState.OUTGOING)
- || (oldState != InCallState.INCOMING && newState == InCallState.INCOMING)
- || primaryChanged) {
- if (getUi() != null) {
- getUi().sendAccessibilityAnnouncement();
- }
- }
- }
-
- /**
- * Determines whether the call subject should be visible on the UI. For the call subject to be
- * visible, the call has to be in an incoming or waiting state, and the subject must not be
- * empty.
- *
- * @param call The call.
- * @return {@code true} if the subject should be shown, {@code false} otherwise.
- */
- private boolean shouldShowCallSubject(Call call) {
- if (call == null) {
- return false;
- }
-
- boolean isIncomingOrWaiting = mPrimary.getState() == Call.State.INCOMING ||
- mPrimary.getState() == Call.State.CALL_WAITING;
- return isIncomingOrWaiting && !TextUtils.isEmpty(call.getCallSubject()) &&
- call.getNumberPresentation() == TelecomManager.PRESENTATION_ALLOWED &&
- call.isCallSubjectSupported();
- }
-
- /**
- * Determines whether the "note sent" toast should be shown. It should be shown for a new
- * outgoing call with a subject.
- *
- * @param call The call
- * @return {@code true} if the toast should be shown, {@code false} otherwise.
- */
- private boolean shouldShowNoteSentToast(Call call) {
- return call != null && hasCallSubject(call) && (call.getState() == Call.State.DIALING
- || call.getState() == Call.State.CONNECTING);
- }
-
- private static boolean hasCallSubject(Call call) {
- return !TextUtils.isEmpty(call.getTelecomCall().getDetails().getIntentExtras()
- .getString(TelecomManager.EXTRA_CALL_SUBJECT));
- }
-
- public interface CallCardUi extends Ui {
- void setVisible(boolean on);
- void setContactContextTitle(View listHeaderView);
- void setContactContextContent(ListAdapter listAdapter);
- void showContactContext(boolean show);
- void setCallCardVisible(boolean visible);
- void setPrimary(String number, String name, boolean nameIsNumber, String label,
- Drawable photo, boolean isSipCall, boolean isContactPhotoShown, boolean isWorkCall);
- void setSecondary(boolean show, String name, boolean nameIsNumber, String label,
- String providerLabel, boolean isConference, boolean isVideoCall,
- boolean isFullscreen);
- void setSecondaryInfoVisible(boolean visible);
- void setCallState(int state, int videoState, int sessionModificationState,
- DisconnectCause disconnectCause, String connectionLabel,
- Drawable connectionIcon, String gatewayNumber, boolean isWifi,
- boolean isConference, boolean isWorkCall);
- void setPrimaryCallElapsedTime(boolean show, long duration);
- void setPrimaryName(String name, boolean nameIsNumber);
- void setPrimaryImage(Drawable image, boolean isVisible);
- void setPrimaryPhoneNumber(String phoneNumber);
- void setPrimaryLabel(String label);
- void setEndCallButtonEnabled(boolean enabled, boolean animate);
- void setCallbackNumber(String number, boolean isEmergencyCalls);
- void setCallSubject(String callSubject);
- void setProgressSpinnerVisible(boolean visible);
- void showHdAudioIndicator(boolean visible);
- void showForwardIndicator(boolean visible);
- void showSpamIndicator(boolean visible);
- void showManageConferenceCallButton(boolean visible);
- boolean isManageConferenceVisible();
- boolean isCallSubjectVisible();
- void animateForNewOutgoingCall();
- void sendAccessibilityAnnouncement();
- void showNoteSentToast();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallList.java b/InCallUI/src/com/android/incallui/CallList.java
deleted file mode 100644
index 48870f68a311300fd8adec0736cc60976d4206f0..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallList.java
+++ /dev/null
@@ -1,695 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.os.Handler;
-import android.os.Message;
-import android.os.Trace;
-import android.telecom.DisconnectCause;
-import android.telecom.PhoneAccount;
-
-import com.android.contacts.common.testing.NeededForTesting;
-import com.android.dialer.logging.Logger;
-import com.android.dialer.service.ExtendedCallInfoService;
-import com.android.incallui.util.TelecomCallUtil;
-
-import com.google.common.base.Preconditions;
-import com.google.common.collect.Maps;
-
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.CopyOnWriteArrayList;
-import java.util.concurrent.atomic.AtomicBoolean;
-
-/**
- * Maintains the list of active calls and notifies interested classes of changes to the call list
- * as they are received from the telephony stack. Primary listener of changes to this class is
- * InCallPresenter.
- */
-public class CallList {
-
- private static final int DISCONNECTED_CALL_SHORT_TIMEOUT_MS = 200;
- private static final int DISCONNECTED_CALL_MEDIUM_TIMEOUT_MS = 2000;
- private static final int DISCONNECTED_CALL_LONG_TIMEOUT_MS = 5000;
-
- private static final int EVENT_DISCONNECTED_TIMEOUT = 1;
- private static final long BLOCK_QUERY_TIMEOUT_MS = 1000;
-
- private static CallList sInstance = new CallList();
-
- private final HashMap mCallById = new HashMap<>();
- private final HashMap mCallByTelecomCall = new HashMap<>();
- private final HashMap> mCallTextReponsesMap = Maps.newHashMap();
- /**
- * ConcurrentHashMap constructor params: 8 is initial table size, 0.9f is
- * load factor before resizing, 1 means we only expect a single thread to
- * access the map so make only a single shard
- */
- private final Set mListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final HashMap> mCallUpdateListenerMap = Maps
- .newHashMap();
- private final Set mPendingDisconnectCalls = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private ExtendedCallInfoService mExtendedCallInfoService;
-
- /**
- * Static singleton accessor method.
- */
- public static CallList getInstance() {
- return sInstance;
- }
-
- /**
- * USED ONLY FOR TESTING
- * Testing-only constructor. Instance should only be acquired through getInstance().
- */
- @NeededForTesting
- CallList() {
- }
-
- public void onCallAdded(final android.telecom.Call telecomCall, LatencyReport latencyReport) {
- Trace.beginSection("onCallAdded");
- final Call call = new Call(telecomCall, latencyReport);
- Log.d(this, "onCallAdded: callState=" + call.getState());
-
- if (call.getState() == Call.State.INCOMING ||
- call.getState() == Call.State.CALL_WAITING) {
- onIncoming(call, call.getCannedSmsResponses());
- if (mExtendedCallInfoService != null) {
- String number = TelecomCallUtil.getNumber(telecomCall);
- mExtendedCallInfoService.getExtendedCallInfo(number, null,
- new ExtendedCallInfoService.Listener() {
- @Override
- public void onComplete(boolean isSpam) {
- call.setSpam(isSpam);
- onUpdate(call);
- }
- });
- }
- } else {
- onUpdate(call);
- }
-
- call.logCallInitiationType();
- Trace.endSection();
- }
-
- public void onCallRemoved(android.telecom.Call telecomCall) {
- if (mCallByTelecomCall.containsKey(telecomCall)) {
- Call call = mCallByTelecomCall.get(telecomCall);
- Logger.logCall(call);
- if (updateCallInMap(call)) {
- Log.w(this, "Removing call not previously disconnected " + call.getId());
- }
- updateCallTextMap(call, null);
- }
- }
-
- /**
- * Called when a single call disconnects.
- */
- public void onDisconnect(Call call) {
- if (updateCallInMap(call)) {
- Log.i(this, "onDisconnect: " + call);
- // notify those listening for changes on this specific change
- notifyCallUpdateListeners(call);
- // notify those listening for all disconnects
- notifyListenersOfDisconnect(call);
- }
- }
-
- /**
- * Called when a single call has changed.
- */
- public void onIncoming(Call call, List textMessages) {
- if (updateCallInMap(call)) {
- Log.i(this, "onIncoming - " + call);
- }
- updateCallTextMap(call, textMessages);
-
- for (Listener listener : mListeners) {
- listener.onIncomingCall(call);
- }
- }
-
- public void onUpgradeToVideo(Call call){
- Log.d(this, "onUpgradeToVideo call=" + call);
- for (Listener listener : mListeners) {
- listener.onUpgradeToVideo(call);
- }
- }
- /**
- * Called when a single call has changed.
- */
- public void onUpdate(Call call) {
- Trace.beginSection("onUpdate");
- onUpdateCall(call);
- notifyGenericListeners();
- Trace.endSection();
- }
-
- /**
- * Called when a single call has changed session modification state.
- *
- * @param call The call.
- * @param sessionModificationState The new session modification state.
- */
- public void onSessionModificationStateChange(Call call, int sessionModificationState) {
- final List listeners = mCallUpdateListenerMap.get(call.getId());
- if (listeners != null) {
- for (CallUpdateListener listener : listeners) {
- listener.onSessionModificationStateChange(sessionModificationState);
- }
- }
- }
-
- /**
- * Called when the last forwarded number changes for a call. With IMS, the last forwarded
- * number changes due to a supplemental service notification, so it is not pressent at the
- * start of the call.
- *
- * @param call The call.
- */
- public void onLastForwardedNumberChange(Call call) {
- final List listeners = mCallUpdateListenerMap.get(call.getId());
- if (listeners != null) {
- for (CallUpdateListener listener : listeners) {
- listener.onLastForwardedNumberChange();
- }
- }
- }
-
- /**
- * Called when the child number changes for a call. The child number can be received after a
- * call is initially set up, so we need to be able to inform listeners of the change.
- *
- * @param call The call.
- */
- public void onChildNumberChange(Call call) {
- final List listeners = mCallUpdateListenerMap.get(call.getId());
- if (listeners != null) {
- for (CallUpdateListener listener : listeners) {
- listener.onChildNumberChange();
- }
- }
- }
-
- public void notifyCallUpdateListeners(Call call) {
- final List listeners = mCallUpdateListenerMap.get(call.getId());
- if (listeners != null) {
- for (CallUpdateListener listener : listeners) {
- listener.onCallChanged(call);
- }
- }
- }
-
- /**
- * Add a call update listener for a call id.
- *
- * @param callId The call id to get updates for.
- * @param listener The listener to add.
- */
- public void addCallUpdateListener(String callId, CallUpdateListener listener) {
- List listeners = mCallUpdateListenerMap.get(callId);
- if (listeners == null) {
- listeners = new CopyOnWriteArrayList();
- mCallUpdateListenerMap.put(callId, listeners);
- }
- listeners.add(listener);
- }
-
- /**
- * Remove a call update listener for a call id.
- *
- * @param callId The call id to remove the listener for.
- * @param listener The listener to remove.
- */
- public void removeCallUpdateListener(String callId, CallUpdateListener listener) {
- List listeners = mCallUpdateListenerMap.get(callId);
- if (listeners != null) {
- listeners.remove(listener);
- }
- }
-
- public void addListener(Listener listener) {
- Preconditions.checkNotNull(listener);
-
- mListeners.add(listener);
-
- // Let the listener know about the active calls immediately.
- listener.onCallListChange(this);
- }
-
- public void removeListener(Listener listener) {
- if (listener != null) {
- mListeners.remove(listener);
- }
- }
-
- /**
- * TODO: Change so that this function is not needed. Instead of assuming there is an active
- * call, the code should rely on the status of a specific Call and allow the presenters to
- * update the Call object when the active call changes.
- */
- public Call getIncomingOrActive() {
- Call retval = getIncomingCall();
- if (retval == null) {
- retval = getActiveCall();
- }
- return retval;
- }
-
- public Call getOutgoingOrActive() {
- Call retval = getOutgoingCall();
- if (retval == null) {
- retval = getActiveCall();
- }
- return retval;
- }
-
- /**
- * A call that is waiting for {@link PhoneAccount} selection
- */
- public Call getWaitingForAccountCall() {
- return getFirstCallWithState(Call.State.SELECT_PHONE_ACCOUNT);
- }
-
- public Call getPendingOutgoingCall() {
- return getFirstCallWithState(Call.State.CONNECTING);
- }
-
- public Call getOutgoingCall() {
- Call call = getFirstCallWithState(Call.State.DIALING);
- if (call == null) {
- call = getFirstCallWithState(Call.State.REDIALING);
- }
- return call;
- }
-
- public Call getActiveCall() {
- return getFirstCallWithState(Call.State.ACTIVE);
- }
-
- public Call getSecondActiveCall() {
- return getCallWithState(Call.State.ACTIVE, 1);
- }
-
- public Call getBackgroundCall() {
- return getFirstCallWithState(Call.State.ONHOLD);
- }
-
- public Call getDisconnectedCall() {
- return getFirstCallWithState(Call.State.DISCONNECTED);
- }
-
- public Call getDisconnectingCall() {
- return getFirstCallWithState(Call.State.DISCONNECTING);
- }
-
- public Call getSecondBackgroundCall() {
- return getCallWithState(Call.State.ONHOLD, 1);
- }
-
- public Call getActiveOrBackgroundCall() {
- Call call = getActiveCall();
- if (call == null) {
- call = getBackgroundCall();
- }
- return call;
- }
-
- public Call getIncomingCall() {
- Call call = getFirstCallWithState(Call.State.INCOMING);
- if (call == null) {
- call = getFirstCallWithState(Call.State.CALL_WAITING);
- }
-
- return call;
- }
-
- public Call getFirstCall() {
- Call result = getIncomingCall();
- if (result == null) {
- result = getPendingOutgoingCall();
- }
- if (result == null) {
- result = getOutgoingCall();
- }
- if (result == null) {
- result = getFirstCallWithState(Call.State.ACTIVE);
- }
- if (result == null) {
- result = getDisconnectingCall();
- }
- if (result == null) {
- result = getDisconnectedCall();
- }
- return result;
- }
-
- public boolean hasLiveCall() {
- Call call = getFirstCall();
- if (call == null) {
- return false;
- }
- return call != getDisconnectingCall() && call != getDisconnectedCall();
- }
-
- /**
- * Returns the first call found in the call map with the specified call modification state.
- * @param state The session modification state to search for.
- * @return The first call with the specified state.
- */
- public Call getVideoUpgradeRequestCall() {
- for(Call call : mCallById.values()) {
- if (call.getSessionModificationState() ==
- Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- return call;
- }
- }
- return null;
- }
-
- public Call getCallById(String callId) {
- return mCallById.get(callId);
- }
-
- public Call getCallByTelecomCall(android.telecom.Call telecomCall) {
- return mCallByTelecomCall.get(telecomCall);
- }
-
- public List getTextResponses(String callId) {
- return mCallTextReponsesMap.get(callId);
- }
-
- /**
- * Returns first call found in the call map with the specified state.
- */
- public Call getFirstCallWithState(int state) {
- return getCallWithState(state, 0);
- }
-
- /**
- * Returns the [position]th call found in the call map with the specified state.
- * TODO: Improve this logic to sort by call time.
- */
- public Call getCallWithState(int state, int positionToFind) {
- Call retval = null;
- int position = 0;
- for (Call call : mCallById.values()) {
- if (call.getState() == state) {
- if (position >= positionToFind) {
- retval = call;
- break;
- } else {
- position++;
- }
- }
- }
-
- return retval;
- }
-
- /**
- * This is called when the service disconnects, either expectedly or unexpectedly.
- * For the expected case, it's because we have no calls left. For the unexpected case,
- * it is likely a crash of phone and we need to clean up our calls manually. Without phone,
- * there can be no active calls, so this is relatively safe thing to do.
- */
- public void clearOnDisconnect() {
- for (Call call : mCallById.values()) {
- final int state = call.getState();
- if (state != Call.State.IDLE &&
- state != Call.State.INVALID &&
- state != Call.State.DISCONNECTED) {
-
- call.setState(Call.State.DISCONNECTED);
- call.setDisconnectCause(new DisconnectCause(DisconnectCause.UNKNOWN));
- updateCallInMap(call);
- }
- }
- notifyGenericListeners();
- }
-
- /**
- * Called when the user has dismissed an error dialog. This indicates acknowledgement of
- * the disconnect cause, and that any pending disconnects should immediately occur.
- */
- public void onErrorDialogDismissed() {
- final Iterator iterator = mPendingDisconnectCalls.iterator();
- while (iterator.hasNext()) {
- Call call = iterator.next();
- iterator.remove();
- finishDisconnectedCall(call);
- }
- }
-
- /**
- * Processes an update for a single call.
- *
- * @param call The call to update.
- */
- private void onUpdateCall(Call call) {
- Log.d(this, "\t" + call);
- if (updateCallInMap(call)) {
- Log.i(this, "onUpdate - " + call);
- }
- updateCallTextMap(call, call.getCannedSmsResponses());
- notifyCallUpdateListeners(call);
- }
-
- /**
- * Sends a generic notification to all listeners that something has changed.
- * It is up to the listeners to call back to determine what changed.
- */
- private void notifyGenericListeners() {
- for (Listener listener : mListeners) {
- listener.onCallListChange(this);
- }
- }
-
- private void notifyListenersOfDisconnect(Call call) {
- for (Listener listener : mListeners) {
- listener.onDisconnect(call);
- }
- }
-
- /**
- * Updates the call entry in the local map.
- * @return false if no call previously existed and no call was added, otherwise true.
- */
- private boolean updateCallInMap(Call call) {
- Preconditions.checkNotNull(call);
-
- boolean updated = false;
-
- if (call.getState() == Call.State.DISCONNECTED) {
- // update existing (but do not add!!) disconnected calls
- if (mCallById.containsKey(call.getId())) {
- // For disconnected calls, we want to keep them alive for a few seconds so that the
- // UI has a chance to display anything it needs when a call is disconnected.
-
- // Set up a timer to destroy the call after X seconds.
- final Message msg = mHandler.obtainMessage(EVENT_DISCONNECTED_TIMEOUT, call);
- mHandler.sendMessageDelayed(msg, getDelayForDisconnect(call));
- mPendingDisconnectCalls.add(call);
-
- mCallById.put(call.getId(), call);
- mCallByTelecomCall.put(call.getTelecomCall(), call);
- updated = true;
- }
- } else if (!isCallDead(call)) {
- mCallById.put(call.getId(), call);
- mCallByTelecomCall.put(call.getTelecomCall(), call);
- updated = true;
- } else if (mCallById.containsKey(call.getId())) {
- mCallById.remove(call.getId());
- mCallByTelecomCall.remove(call.getTelecomCall());
- updated = true;
- }
-
- return updated;
- }
-
- private int getDelayForDisconnect(Call call) {
- Preconditions.checkState(call.getState() == Call.State.DISCONNECTED);
-
-
- final int cause = call.getDisconnectCause().getCode();
- final int delay;
- switch (cause) {
- case DisconnectCause.LOCAL:
- delay = DISCONNECTED_CALL_SHORT_TIMEOUT_MS;
- break;
- case DisconnectCause.REMOTE:
- case DisconnectCause.ERROR:
- delay = DISCONNECTED_CALL_MEDIUM_TIMEOUT_MS;
- break;
- case DisconnectCause.REJECTED:
- case DisconnectCause.MISSED:
- case DisconnectCause.CANCELED:
- // no delay for missed/rejected incoming calls and canceled outgoing calls.
- delay = 0;
- break;
- default:
- delay = DISCONNECTED_CALL_LONG_TIMEOUT_MS;
- break;
- }
-
- return delay;
- }
-
- private void updateCallTextMap(Call call, List textResponses) {
- Preconditions.checkNotNull(call);
-
- if (!isCallDead(call)) {
- if (textResponses != null) {
- mCallTextReponsesMap.put(call.getId(), textResponses);
- }
- } else if (mCallById.containsKey(call.getId())) {
- mCallTextReponsesMap.remove(call.getId());
- }
- }
-
- private boolean isCallDead(Call call) {
- final int state = call.getState();
- return Call.State.IDLE == state || Call.State.INVALID == state;
- }
-
- /**
- * Sets up a call for deletion and notifies listeners of change.
- */
- private void finishDisconnectedCall(Call call) {
- if (mPendingDisconnectCalls.contains(call)) {
- mPendingDisconnectCalls.remove(call);
- }
- call.setState(Call.State.IDLE);
- updateCallInMap(call);
- notifyGenericListeners();
- }
-
- /**
- * Notifies all video calls of a change in device orientation.
- *
- * @param rotation The new rotation angle (in degrees).
- */
- public void notifyCallsOfDeviceRotation(int rotation) {
- for (Call call : mCallById.values()) {
- // First, ensure that the call videoState has video enabled (there is no need to set
- // device orientation on a voice call which has not yet been upgraded to video).
- // Second, ensure a VideoCall is set on the call so that the change can be sent to the
- // provider (a VideoCall can be present for a call that does not currently have video,
- // but can be upgraded to video).
-
- // NOTE: is it necessary to use this order because getVideoCall references the class
- // VideoProfile which is not available on APIs <23 (M).
- if (VideoUtils.isVideoCall(call) && call.getVideoCall() != null) {
- call.getVideoCall().setDeviceOrientation(rotation);
- }
- }
- }
-
- /**
- * Handles the timeout for destroying disconnected calls.
- */
- private Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case EVENT_DISCONNECTED_TIMEOUT:
- Log.d(this, "EVENT_DISCONNECTED_TIMEOUT ", msg.obj);
- finishDisconnectedCall((Call) msg.obj);
- break;
- default:
- Log.wtf(this, "Message not expected: " + msg.what);
- break;
- }
- }
- };
-
- public void setExtendedCallInfoService(ExtendedCallInfoService service) {
- mExtendedCallInfoService = service;
- }
-
- public void onInCallUiShown(boolean forFullScreenIntent) {
- for (Call call : mCallById.values()) {
- call.getLatencyReport().onInCallUiShown(forFullScreenIntent);
- }
- }
-
- /**
- * Listener interface for any class that wants to be notified of changes
- * to the call list.
- */
- public interface Listener {
- /**
- * Called when a new incoming call comes in.
- * This is the only method that gets called for incoming calls. Listeners
- * that want to perform an action on incoming call should respond in this method
- * because {@link #onCallListChange} does not automatically get called for
- * incoming calls.
- */
- public void onIncomingCall(Call call);
- /**
- * Called when a new modify call request comes in
- * This is the only method that gets called for modify requests.
- */
- public void onUpgradeToVideo(Call call);
- /**
- * Called anytime there are changes to the call list. The change can be switching call
- * states, updating information, etc. This method will NOT be called for new incoming
- * calls and for calls that switch to disconnected state. Listeners must add actions
- * to those method implementations if they want to deal with those actions.
- */
- public void onCallListChange(CallList callList);
-
- /**
- * Called when a call switches to the disconnected state. This is the only method
- * that will get called upon disconnection.
- */
- public void onDisconnect(Call call);
-
-
- }
-
- public interface CallUpdateListener {
- // TODO: refactor and limit arg to be call state. Caller info is not needed.
- public void onCallChanged(Call call);
-
- /**
- * Notifies of a change to the session modification state for a call.
- *
- * @param sessionModificationState The new session modification state.
- */
- public void onSessionModificationStateChange(int sessionModificationState);
-
- /**
- * Notifies of a change to the last forwarded number for a call.
- */
- public void onLastForwardedNumberChange();
-
- /**
- * Notifies of a change to the child number for a call.
- */
- public void onChildNumberChange();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallTimer.java b/InCallUI/src/com/android/incallui/CallTimer.java
deleted file mode 100644
index d65e633731aafce057ca99f7137cdaf6e50de243..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallTimer.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import android.os.Handler;
-import android.os.SystemClock;
-
-/**
- * Helper class used to keep track of events requiring regular intervals.
- */
-public class CallTimer extends Handler {
- private Runnable mInternalCallback;
- private Runnable mCallback;
- private long mLastReportedTime;
- private long mInterval;
- private boolean mRunning;
-
- public CallTimer(Runnable callback) {
- Preconditions.checkNotNull(callback);
-
- mInterval = 0;
- mLastReportedTime = 0;
- mRunning = false;
- mCallback = callback;
- mInternalCallback = new CallTimerCallback();
- }
-
- public boolean start(long interval) {
- if (interval <= 0) {
- return false;
- }
-
- // cancel any previous timer
- cancel();
-
- mInterval = interval;
- mLastReportedTime = SystemClock.uptimeMillis();
-
- mRunning = true;
- periodicUpdateTimer();
-
- return true;
- }
-
- public void cancel() {
- removeCallbacks(mInternalCallback);
- mRunning = false;
- }
-
- private void periodicUpdateTimer() {
- if (!mRunning) {
- return;
- }
-
- final long now = SystemClock.uptimeMillis();
- long nextReport = mLastReportedTime + mInterval;
- while (now >= nextReport) {
- nextReport += mInterval;
- }
-
- postAtTime(mInternalCallback, nextReport);
- mLastReportedTime = nextReport;
-
- // Run the callback
- mCallback.run();
- }
-
- private class CallTimerCallback implements Runnable {
- @Override
- public void run() {
- periodicUpdateTimer();
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallerInfo.java b/InCallUI/src/com/android/incallui/CallerInfo.java
deleted file mode 100644
index f3d0e0763db823a9f43fb9af60436cf6f47a74d1..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallerInfo.java
+++ /dev/null
@@ -1,585 +0,0 @@
-/*
- * Copyright (C) 2006 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import com.android.dialer.util.PhoneLookupUtil;
-import com.google.common.primitives.Longs;
-
-import android.content.Context;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.provider.ContactsContract.CommonDataKinds.Phone;
-import android.provider.ContactsContract;
-import android.provider.ContactsContract.Contacts;
-import android.provider.ContactsContract.Data;
-import android.provider.ContactsContract.PhoneLookup;
-import android.provider.ContactsContract.RawContacts;
-import android.telephony.PhoneNumberUtils;
-import android.text.TextUtils;
-
-import com.android.contacts.common.compat.CompatUtils;
-import com.android.contacts.common.compat.PhoneLookupSdkCompat;
-import com.android.contacts.common.ContactsUtils;
-import com.android.contacts.common.ContactsUtils.UserType;
-import com.android.contacts.common.util.PhoneNumberHelper;
-import com.android.contacts.common.util.TelephonyManagerUtils;
-import com.android.dialer.R;
-import com.android.dialer.calllog.ContactInfoHelper;
-
-/**
- * Looks up caller information for the given phone number.
- */
-public class CallerInfo {
- private static final String TAG = "CallerInfo";
-
- // We should always use this projection starting from NYC onward.
- private static final String[] DEFAULT_PHONELOOKUP_PROJECTION = new String[] {
- PhoneLookupSdkCompat.CONTACT_ID,
- PhoneLookup.DISPLAY_NAME,
- PhoneLookup.LOOKUP_KEY,
- PhoneLookup.NUMBER,
- PhoneLookup.NORMALIZED_NUMBER,
- PhoneLookup.LABEL,
- PhoneLookup.TYPE,
- PhoneLookup.PHOTO_URI,
- PhoneLookup.CUSTOM_RINGTONE,
- PhoneLookup.SEND_TO_VOICEMAIL
- };
-
- // In pre-N, contact id is stored in {@link PhoneLookup._ID} in non-sip query.
- private static final String[] BACKWARD_COMPATIBLE_NON_SIP_DEFAULT_PHONELOOKUP_PROJECTION =
- new String[] {
- PhoneLookup._ID,
- PhoneLookup.DISPLAY_NAME,
- PhoneLookup.LOOKUP_KEY,
- PhoneLookup.NUMBER,
- PhoneLookup.NORMALIZED_NUMBER,
- PhoneLookup.LABEL,
- PhoneLookup.TYPE,
- PhoneLookup.PHOTO_URI,
- PhoneLookup.CUSTOM_RINGTONE,
- PhoneLookup.SEND_TO_VOICEMAIL
- };
-
- public static String[] getDefaultPhoneLookupProjection(Uri phoneLookupUri) {
- if (CompatUtils.isNCompatible()) {
- return DEFAULT_PHONELOOKUP_PROJECTION;
- }
- // Pre-N
- boolean isSip = phoneLookupUri.getBooleanQueryParameter(
- ContactsContract.PhoneLookup.QUERY_PARAMETER_SIP_ADDRESS, false);
- return (isSip) ? DEFAULT_PHONELOOKUP_PROJECTION
- : BACKWARD_COMPATIBLE_NON_SIP_DEFAULT_PHONELOOKUP_PROJECTION;
- }
-
- /**
- * Please note that, any one of these member variables can be null,
- * and any accesses to them should be prepared to handle such a case.
- *
- * Also, it is implied that phoneNumber is more often populated than
- * name is, (think of calls being dialed/received using numbers where
- * names are not known to the device), so phoneNumber should serve as
- * a dependable fallback when name is unavailable.
- *
- * One other detail here is that this CallerInfo object reflects
- * information found on a connection, it is an OUTPUT that serves
- * mainly to display information to the user. In no way is this object
- * used as input to make a connection, so we can choose to display
- * whatever human-readable text makes sense to the user for a
- * connection. This is especially relevant for the phone number field,
- * since it is the one field that is most likely exposed to the user.
- *
- * As an example:
- * 1. User dials "911"
- * 2. Device recognizes that this is an emergency number
- * 3. We use the "Emergency Number" string instead of "911" in the
- * phoneNumber field.
- *
- * What we're really doing here is treating phoneNumber as an essential
- * field here, NOT name. We're NOT always guaranteed to have a name
- * for a connection, but the number should be displayable.
- */
- public String name;
- public String nameAlternative;
- public String phoneNumber;
- public String normalizedNumber;
- public String forwardingNumber;
- public String geoDescription;
-
- public String cnapName;
- public int numberPresentation;
- public int namePresentation;
- public boolean contactExists;
-
- public String phoneLabel;
- /* Split up the phoneLabel into number type and label name */
- public int numberType;
- public String numberLabel;
-
- public int photoResource;
-
- // Contact ID, which will be 0 if a contact comes from the corp CP2.
- public long contactIdOrZero;
- public String lookupKeyOrNull;
- public boolean needUpdate;
- public Uri contactRefUri;
- public @UserType long userType;
-
- /**
- * Contact display photo URI. If a contact has no display photo but a thumbnail, it'll be
- * the thumbnail URI instead.
- */
- public Uri contactDisplayPhotoUri;
-
- // fields to hold individual contact preference data,
- // including the send to voicemail flag and the ringtone
- // uri reference.
- public Uri contactRingtoneUri;
- public boolean shouldSendToVoicemail;
-
- /**
- * Drawable representing the caller image. This is essentially
- * a cache for the image data tied into the connection /
- * callerinfo object.
- *
- * This might be a high resolution picture which is more suitable
- * for full-screen image view than for smaller icons used in some
- * kinds of notifications.
- *
- * The {@link #isCachedPhotoCurrent} flag indicates if the image
- * data needs to be reloaded.
- */
- public Drawable cachedPhoto;
- /**
- * Bitmap representing the caller image which has possibly lower
- * resolution than {@link #cachedPhoto} and thus more suitable for
- * icons (like notification icons).
- *
- * In usual cases this is just down-scaled image of {@link #cachedPhoto}.
- * If the down-scaling fails, this will just become null.
- *
- * The {@link #isCachedPhotoCurrent} flag indicates if the image
- * data needs to be reloaded.
- */
- public Bitmap cachedPhotoIcon;
- /**
- * Boolean which indicates if {@link #cachedPhoto} and
- * {@link #cachedPhotoIcon} is fresh enough. If it is false,
- * those images aren't pointing to valid objects.
- */
- public boolean isCachedPhotoCurrent;
-
- /**
- * String which holds the call subject sent as extra from the lower layers for this call. This
- * is used to display the no-caller ID reason for restricted/unknown number presentation.
- */
- public String callSubject;
-
- private boolean mIsEmergency;
- private boolean mIsVoiceMail;
-
- public CallerInfo() {
- // TODO: Move all the basic initialization here?
- mIsEmergency = false;
- mIsVoiceMail = false;
- userType = ContactsUtils.USER_TYPE_CURRENT;
- }
-
- /**
- * getCallerInfo given a Cursor.
- * @param context the context used to retrieve string constants
- * @param contactRef the URI to attach to this CallerInfo object
- * @param cursor the first object in the cursor is used to build the CallerInfo object.
- * @return the CallerInfo which contains the caller id for the given
- * number. The returned CallerInfo is null if no number is supplied.
- */
- public static CallerInfo getCallerInfo(Context context, Uri contactRef, Cursor cursor) {
- CallerInfo info = new CallerInfo();
- info.photoResource = 0;
- info.phoneLabel = null;
- info.numberType = 0;
- info.numberLabel = null;
- info.cachedPhoto = null;
- info.isCachedPhotoCurrent = false;
- info.contactExists = false;
- info.userType = ContactsUtils.USER_TYPE_CURRENT;
-
- Log.v(TAG, "getCallerInfo() based on cursor...");
-
- if (cursor != null) {
- if (cursor.moveToFirst()) {
- // TODO: photo_id is always available but not taken
- // care of here. Maybe we should store it in the
- // CallerInfo object as well.
-
- long contactId = 0L;
- int columnIndex;
-
- // Look for the name
- columnIndex = cursor.getColumnIndex(PhoneLookup.DISPLAY_NAME);
- if (columnIndex != -1) {
- info.name = cursor.getString(columnIndex);
- }
-
- // Look for the number
- columnIndex = cursor.getColumnIndex(PhoneLookup.NUMBER);
- if (columnIndex != -1) {
- info.phoneNumber = cursor.getString(columnIndex);
- }
-
- // Look for the normalized number
- columnIndex = cursor.getColumnIndex(PhoneLookup.NORMALIZED_NUMBER);
- if (columnIndex != -1) {
- info.normalizedNumber = cursor.getString(columnIndex);
- }
-
- // Look for the label/type combo
- columnIndex = cursor.getColumnIndex(PhoneLookup.LABEL);
- if (columnIndex != -1) {
- int typeColumnIndex = cursor.getColumnIndex(PhoneLookup.TYPE);
- if (typeColumnIndex != -1) {
- info.numberType = cursor.getInt(typeColumnIndex);
- info.numberLabel = cursor.getString(columnIndex);
- info.phoneLabel = Phone.getTypeLabel(context.getResources(),
- info.numberType, info.numberLabel)
- .toString();
- }
- }
-
- // Look for the person_id.
- columnIndex = getColumnIndexForPersonId(contactRef, cursor);
- if (columnIndex != -1) {
- contactId = cursor.getLong(columnIndex);
- // QuickContacts in M doesn't support enterprise contact id
- if (contactId != 0 && (ContactsUtils.FLAG_N_FEATURE
- || !Contacts.isEnterpriseContactId(contactId))) {
- info.contactIdOrZero = contactId;
- Log.v(TAG, "==> got info.contactIdOrZero: " + info.contactIdOrZero);
-
- // cache the lookup key for later use with person_id to create lookup URIs
- columnIndex = cursor.getColumnIndex(PhoneLookup.LOOKUP_KEY);
- if (columnIndex != -1) {
- info.lookupKeyOrNull = cursor.getString(columnIndex);
- }
- }
- } else {
- // No valid columnIndex, so we can't look up person_id.
- Log.v(TAG, "Couldn't find contactId column for " + contactRef);
- // Watch out: this means that anything that depends on
- // person_id will be broken (like contact photo lookups in
- // the in-call UI, for example.)
- }
-
- // Display photo URI.
- columnIndex = cursor.getColumnIndex(PhoneLookup.PHOTO_URI);
- if ((columnIndex != -1) && (cursor.getString(columnIndex) != null)) {
- info.contactDisplayPhotoUri = Uri.parse(cursor.getString(columnIndex));
- } else {
- info.contactDisplayPhotoUri = null;
- }
-
- // look for the custom ringtone, create from the string stored
- // in the database.
- columnIndex = cursor.getColumnIndex(PhoneLookup.CUSTOM_RINGTONE);
- if ((columnIndex != -1) && (cursor.getString(columnIndex) != null)) {
- if (TextUtils.isEmpty(cursor.getString(columnIndex))) {
- // make it consistent with frameworks/base/.../CallerInfo.java
- info.contactRingtoneUri = Uri.EMPTY;
- } else {
- info.contactRingtoneUri = Uri.parse(cursor.getString(columnIndex));
- }
- } else {
- info.contactRingtoneUri = null;
- }
-
- // look for the send to voicemail flag, set it to true only
- // under certain circumstances.
- columnIndex = cursor.getColumnIndex(PhoneLookup.SEND_TO_VOICEMAIL);
- info.shouldSendToVoicemail = (columnIndex != -1) &&
- ((cursor.getInt(columnIndex)) == 1);
- info.contactExists = true;
-
- // Determine userType by directoryId and contactId
- final String directory = contactRef == null ? null
- : contactRef.getQueryParameter(ContactsContract.DIRECTORY_PARAM_KEY);
- final Long directoryId = directory == null ? null : Longs.tryParse(directory);
- info.userType = ContactsUtils.determineUserType(directoryId, contactId);
-
- info.nameAlternative = ContactInfoHelper.lookUpDisplayNameAlternative(
- context, info.lookupKeyOrNull, info.userType, directoryId);
- }
- cursor.close();
- }
-
- info.needUpdate = false;
- info.name = normalize(info.name);
- info.contactRefUri = contactRef;
-
- return info;
- }
-
- /**
- * getCallerInfo given a URI, look up in the call-log database
- * for the uri unique key.
- * @param context the context used to get the ContentResolver
- * @param contactRef the URI used to lookup caller id
- * @return the CallerInfo which contains the caller id for the given
- * number. The returned CallerInfo is null if no number is supplied.
- */
- private static CallerInfo getCallerInfo(Context context, Uri contactRef) {
-
- return getCallerInfo(context, contactRef,
- context.getContentResolver().query(contactRef, null, null, null, null));
- }
-
- /**
- * Performs another lookup if previous lookup fails and it's a SIP call
- * and the peer's username is all numeric. Look up the username as it
- * could be a PSTN number in the contact database.
- *
- * @param context the query context
- * @param number the original phone number, could be a SIP URI
- * @param previousResult the result of previous lookup
- * @return previousResult if it's not the case
- */
- static CallerInfo doSecondaryLookupIfNecessary(Context context,
- String number, CallerInfo previousResult) {
- if (!previousResult.contactExists
- && PhoneNumberHelper.isUriNumber(number)) {
- String username = PhoneNumberHelper.getUsernameFromUriNumber(number);
- if (PhoneNumberUtils.isGlobalPhoneNumber(username)) {
- previousResult = getCallerInfo(context,
- Uri.withAppendedPath(PhoneLookup.ENTERPRISE_CONTENT_FILTER_URI,
- Uri.encode(username)));
- }
- }
- return previousResult;
- }
-
- // Accessors
-
- /**
- * @return true if the caller info is an emergency number.
- */
- public boolean isEmergencyNumber() {
- return mIsEmergency;
- }
-
- /**
- * @return true if the caller info is a voicemail number.
- */
- public boolean isVoiceMailNumber() {
- return mIsVoiceMail;
- }
-
- /**
- * Mark this CallerInfo as an emergency call.
- * @param context To lookup the localized 'Emergency Number' string.
- * @return this instance.
- */
- /* package */ CallerInfo markAsEmergency(Context context) {
- name = context.getString(R.string.emergency_call_dialog_number_for_display);
- phoneNumber = null;
-
- photoResource = R.drawable.img_phone;
- mIsEmergency = true;
- return this;
- }
-
-
- /**
- * Mark this CallerInfo as a voicemail call. The voicemail label
- * is obtained from the telephony manager. Caller must hold the
- * READ_PHONE_STATE permission otherwise the phoneNumber will be
- * set to null.
- * @return this instance.
- */
- /* package */ CallerInfo markAsVoiceMail(Context context) {
- mIsVoiceMail = true;
-
- try {
- // For voicemail calls, we display the voice mail tag
- // instead of the real phone number in the "number"
- // field.
- name = TelephonyManagerUtils.getVoiceMailAlphaTag(context);
- phoneNumber = null;
- } catch (SecurityException se) {
- // Should never happen: if this process does not have
- // permission to retrieve VM tag, it should not have
- // permission to retrieve VM number and would not call
- // this method.
- // Leave phoneNumber untouched.
- Log.e(TAG, "Cannot access VoiceMail.", se);
- }
- // TODO: There is no voicemail picture?
- // FIXME: FIND ANOTHER ICON
- // photoResource = android.R.drawable.badge_voicemail;
- return this;
- }
-
- private static String normalize(String s) {
- if (s == null || s.length() > 0) {
- return s;
- } else {
- return null;
- }
- }
-
- /**
- * Returns the column index to use to find the "person_id" field in
- * the specified cursor, based on the contact URI that was originally
- * queried.
- *
- * This is a helper function for the getCallerInfo() method that takes
- * a Cursor. Looking up the person_id is nontrivial (compared to all
- * the other CallerInfo fields) since the column we need to use
- * depends on what query we originally ran.
- *
- * Watch out: be sure to not do any database access in this method, since
- * it's run from the UI thread (see comments below for more info.)
- *
- * @return the columnIndex to use (with cursor.getLong()) to get the
- * person_id, or -1 if we couldn't figure out what colum to use.
- *
- * TODO: Add a unittest for this method. (This is a little tricky to
- * test, since we'll need a live contacts database to test against,
- * preloaded with at least some phone numbers and SIP addresses. And
- * we'll probably have to hardcode the column indexes we expect, so
- * the test might break whenever the contacts schema changes. But we
- * can at least make sure we handle all the URI patterns we claim to,
- * and that the mime types match what we expect...)
- */
- private static int getColumnIndexForPersonId(Uri contactRef, Cursor cursor) {
- // TODO: This is pretty ugly now, see bug 2269240 for
- // more details. The column to use depends upon the type of URL:
- // - content://com.android.contacts/data/phones ==> use the "contact_id" column
- // - content://com.android.contacts/phone_lookup ==> use the "_ID" column
- // - content://com.android.contacts/data ==> use the "contact_id" column
- // If it's none of the above, we leave columnIndex=-1 which means
- // that the person_id field will be left unset.
- //
- // The logic here *used* to be based on the mime type of contactRef
- // (for example Phone.CONTENT_ITEM_TYPE would tell us to use the
- // RawContacts.CONTACT_ID column). But looking up the mime type requires
- // a call to context.getContentResolver().getType(contactRef), which
- // isn't safe to do from the UI thread since it can cause an ANR if
- // the contacts provider is slow or blocked (like during a sync.)
- //
- // So instead, figure out the column to use for person_id by just
- // looking at the URI itself.
-
- Log.v(TAG, "- getColumnIndexForPersonId: contactRef URI = '"
- + contactRef + "'...");
- // Warning: Do not enable the following logging (due to ANR risk.)
- // if (VDBG) Rlog.v(TAG, "- MIME type: "
- // + context.getContentResolver().getType(contactRef));
-
- String url = contactRef.toString();
- String columnName = null;
- if (url.startsWith("content://com.android.contacts/data/phones")) {
- // Direct lookup in the Phone table.
- // MIME type: Phone.CONTENT_ITEM_TYPE (= "vnd.android.cursor.item/phone_v2")
- Log.v(TAG, "'data/phones' URI; using RawContacts.CONTACT_ID");
- columnName = RawContacts.CONTACT_ID;
- } else if (url.startsWith("content://com.android.contacts/data")) {
- // Direct lookup in the Data table.
- // MIME type: Data.CONTENT_TYPE (= "vnd.android.cursor.dir/data")
- Log.v(TAG, "'data' URI; using Data.CONTACT_ID");
- // (Note Data.CONTACT_ID and RawContacts.CONTACT_ID are equivalent.)
- columnName = Data.CONTACT_ID;
- } else if (url.startsWith("content://com.android.contacts/phone_lookup")) {
- // Lookup in the PhoneLookup table, which provides "fuzzy matching"
- // for phone numbers.
- // MIME type: PhoneLookup.CONTENT_TYPE (= "vnd.android.cursor.dir/phone_lookup")
- Log.v(TAG, "'phone_lookup' URI; using PhoneLookup._ID");
- columnName = PhoneLookupUtil.getContactIdColumnNameForUri(contactRef);
- } else {
- Log.v(TAG, "Unexpected prefix for contactRef '" + url + "'");
- }
- int columnIndex = (columnName != null) ? cursor.getColumnIndex(columnName) : -1;
- Log.v(TAG, "==> Using column '" + columnName
- + "' (columnIndex = " + columnIndex + ") for person_id lookup...");
- return columnIndex;
- }
-
- /**
- * Updates this CallerInfo's geoDescription field, based on the raw
- * phone number in the phoneNumber field.
- *
- * (Note that the various getCallerInfo() methods do *not* set the
- * geoDescription automatically; you need to call this method
- * explicitly to get it.)
- *
- * @param context the context used to look up the current locale / country
- * @param fallbackNumber if this CallerInfo's phoneNumber field is empty,
- * this specifies a fallback number to use instead.
- */
- public void updateGeoDescription(Context context, String fallbackNumber) {
- String number = TextUtils.isEmpty(phoneNumber) ? fallbackNumber : phoneNumber;
- geoDescription = com.android.dialer.util.PhoneNumberUtil.getGeoDescription(context, number);
- }
-
- /**
- * @return a string debug representation of this instance.
- */
- @Override
- public String toString() {
- // Warning: never check in this file with VERBOSE_DEBUG = true
- // because that will result in PII in the system log.
- final boolean VERBOSE_DEBUG = false;
-
- if (VERBOSE_DEBUG) {
- return new StringBuilder(384)
- .append(super.toString() + " { ")
- .append("\nname: " + name)
- .append("\nphoneNumber: " + phoneNumber)
- .append("\nnormalizedNumber: " + normalizedNumber)
- .append("\forwardingNumber: " + forwardingNumber)
- .append("\ngeoDescription: " + geoDescription)
- .append("\ncnapName: " + cnapName)
- .append("\nnumberPresentation: " + numberPresentation)
- .append("\nnamePresentation: " + namePresentation)
- .append("\ncontactExists: " + contactExists)
- .append("\nphoneLabel: " + phoneLabel)
- .append("\nnumberType: " + numberType)
- .append("\nnumberLabel: " + numberLabel)
- .append("\nphotoResource: " + photoResource)
- .append("\ncontactIdOrZero: " + contactIdOrZero)
- .append("\nneedUpdate: " + needUpdate)
- .append("\ncontactRefUri: " + contactRefUri)
- .append("\ncontactRingtoneUri: " + contactRingtoneUri)
- .append("\ncontactDisplayPhotoUri: " + contactDisplayPhotoUri)
- .append("\nshouldSendToVoicemail: " + shouldSendToVoicemail)
- .append("\ncachedPhoto: " + cachedPhoto)
- .append("\nisCachedPhotoCurrent: " + isCachedPhotoCurrent)
- .append("\nemergency: " + mIsEmergency)
- .append("\nvoicemail: " + mIsVoiceMail)
- .append("\nuserType: " + userType)
- .append(" }")
- .toString();
- } else {
- return new StringBuilder(128)
- .append(super.toString() + " { ")
- .append("name " + ((name == null) ? "null" : "non-null"))
- .append(", phoneNumber " + ((phoneNumber == null) ? "null" : "non-null"))
- .append(" }")
- .toString();
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallerInfoAsyncQuery.java b/InCallUI/src/com/android/incallui/CallerInfoAsyncQuery.java
deleted file mode 100644
index f7f0cbb5dbba87ceec6ca553398f0b44d6078c16..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallerInfoAsyncQuery.java
+++ /dev/null
@@ -1,599 +0,0 @@
-/*
- * Copyright (C) 2006 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import com.google.common.primitives.Longs;
-
-import android.Manifest;
-import android.content.AsyncQueryHandler;
-import android.content.ContentResolver;
-import android.content.Context;
-import android.database.Cursor;
-import android.database.SQLException;
-import android.net.Uri;
-import android.os.Handler;
-import android.os.Looper;
-import android.os.Message;
-import android.provider.ContactsContract;
-import android.provider.ContactsContract.Directory;
-import android.telephony.PhoneNumberUtils;
-import android.text.TextUtils;
-
-import com.android.contacts.common.ContactsUtils;
-import com.android.contacts.common.compat.DirectoryCompat;
-import com.android.contacts.common.util.PermissionsUtil;
-import com.android.contacts.common.util.TelephonyManagerUtils;
-import com.android.dialer.R;
-import com.android.dialer.calllog.ContactInfoHelper;
-import com.android.dialer.service.CachedNumberLookupService;
-import com.android.dialer.service.CachedNumberLookupService.CachedContactInfo;
-import com.android.dialerbind.ObjectFactory;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Locale;
-
-/**
- * Helper class to make it easier to run asynchronous caller-id lookup queries.
- * @see CallerInfo
- *
- */
-public class CallerInfoAsyncQuery {
- private static final boolean DBG = false;
- private static final String LOG_TAG = "CallerInfoAsyncQuery";
-
- private static final int EVENT_NEW_QUERY = 1;
- private static final int EVENT_ADD_LISTENER = 2;
- private static final int EVENT_END_OF_QUEUE = 3;
- private static final int EVENT_EMERGENCY_NUMBER = 4;
- private static final int EVENT_VOICEMAIL_NUMBER = 5;
-
- private CallerInfoAsyncQueryHandler mHandler;
-
- // If the CallerInfo query finds no contacts, should we use the
- // PhoneNumberOfflineGeocoder to look up a "geo description"?
- // (TODO: This could become a flag in config.xml if it ever needs to be
- // configured on a per-product basis.)
- private static final boolean ENABLE_UNKNOWN_NUMBER_GEO_DESCRIPTION = true;
-
- /**
- * Interface for a CallerInfoAsyncQueryHandler result return.
- */
- public interface OnQueryCompleteListener {
- /**
- * Called when the query is complete.
- */
- public void onQueryComplete(int token, Object cookie, CallerInfo ci);
- }
-
-
- /**
- * Wrap the cookie from the WorkerArgs with additional information needed by our
- * classes.
- */
- private static final class CookieWrapper {
- public OnQueryCompleteListener listener;
- public Object cookie;
- public int event;
- public String number;
- }
-
- /**
- * Simple exception used to communicate problems with the query pool.
- */
- public static class QueryPoolException extends SQLException {
- public QueryPoolException(String error) {
- super(error);
- }
- }
-
- /**
- * Our own implementation of the AsyncQueryHandler.
- */
- private class CallerInfoAsyncQueryHandler extends AsyncQueryHandler {
-
- @Override
- public void startQuery(int token, Object cookie, Uri uri, String[] projection,
- String selection, String[] selectionArgs, String orderBy) {
- if (DBG) {
- // Show stack trace with the arguments.
- android.util.Log.d(LOG_TAG, "InCall: startQuery: url=" + uri +
- " projection=[" + Arrays.toString(projection) + "]" +
- " selection=" + selection + " " +
- " args=[" + Arrays.toString(selectionArgs) + "]",
- new RuntimeException("STACKTRACE"));
- }
- super.startQuery(token, cookie, uri, projection, selection, selectionArgs, orderBy);
- }
-
- /**
- * The information relevant to each CallerInfo query. Each query may have multiple
- * listeners, so each AsyncCursorInfo is associated with 2 or more CookieWrapper
- * objects in the queue (one with a new query event, and one with a end event, with
- * 0 or more additional listeners in between).
- */
- private Context mQueryContext;
- private Uri mQueryUri;
- private CallerInfo mCallerInfo;
-
- /**
- * Our own query worker thread.
- *
- * This thread handles the messages enqueued in the looper. The normal sequence
- * of events is that a new query shows up in the looper queue, followed by 0 or
- * more add listener requests, and then an end request. Of course, these requests
- * can be interlaced with requests from other tokens, but is irrelevant to this
- * handler since the handler has no state.
- *
- * Note that we depend on the queue to keep things in order; in other words, the
- * looper queue must be FIFO with respect to input from the synchronous startQuery
- * calls and output to this handleMessage call.
- *
- * This use of the queue is required because CallerInfo objects may be accessed
- * multiple times before the query is complete. All accesses (listeners) must be
- * queued up and informed in order when the query is complete.
- */
- protected class CallerInfoWorkerHandler extends WorkerHandler {
- public CallerInfoWorkerHandler(Looper looper) {
- super(looper);
- }
-
- @Override
- public void handleMessage(Message msg) {
- WorkerArgs args = (WorkerArgs) msg.obj;
- CookieWrapper cw = (CookieWrapper) args.cookie;
-
- if (cw == null) {
- // Normally, this should never be the case for calls originating
- // from within this code.
- // However, if there is any code that this Handler calls (such as in
- // super.handleMessage) that DOES place unexpected messages on the
- // queue, then we need pass these messages on.
- Log.d(this, "Unexpected command (CookieWrapper is null): " + msg.what +
- " ignored by CallerInfoWorkerHandler, passing onto parent.");
-
- super.handleMessage(msg);
- } else {
- Log.d(this, "Processing event: " + cw.event + " token (arg1): " + msg.arg1 +
- " command: " + msg.what + " query URI: " +
- sanitizeUriToString(args.uri));
-
- switch (cw.event) {
- case EVENT_NEW_QUERY:
- //start the sql command.
- super.handleMessage(msg);
- break;
-
- // shortcuts to avoid query for recognized numbers.
- case EVENT_EMERGENCY_NUMBER:
- case EVENT_VOICEMAIL_NUMBER:
-
- case EVENT_ADD_LISTENER:
- case EVENT_END_OF_QUEUE:
- // query was already completed, so just send the reply.
- // passing the original token value back to the caller
- // on top of the event values in arg1.
- Message reply = args.handler.obtainMessage(msg.what);
- reply.obj = args;
- reply.arg1 = msg.arg1;
-
- reply.sendToTarget();
-
- break;
- default:
- }
- }
- }
- }
-
-
- /**
- * Asynchronous query handler class for the contact / callerinfo object.
- */
- private CallerInfoAsyncQueryHandler(Context context) {
- super(context.getContentResolver());
- }
-
- @Override
- protected Handler createHandler(Looper looper) {
- return new CallerInfoWorkerHandler(looper);
- }
-
- /**
- * Overrides onQueryComplete from AsyncQueryHandler.
- *
- * This method takes into account the state of this class; we construct the CallerInfo
- * object only once for each set of listeners. When the query thread has done its work
- * and calls this method, we inform the remaining listeners in the queue, until we're
- * out of listeners. Once we get the message indicating that we should expect no new
- * listeners for this CallerInfo object, we release the AsyncCursorInfo back into the
- * pool.
- */
- @Override
- protected void onQueryComplete(int token, Object cookie, Cursor cursor) {
- try {
- Log.d(this, "##### onQueryComplete() ##### query complete for token: " + token);
-
- //get the cookie and notify the listener.
- CookieWrapper cw = (CookieWrapper) cookie;
- if (cw == null) {
- // Normally, this should never be the case for calls originating
- // from within this code.
- // However, if there is any code that calls this method, we should
- // check the parameters to make sure they're viable.
- Log.d(this, "Cookie is null, ignoring onQueryComplete() request.");
- return;
- }
-
- if (cw.event == EVENT_END_OF_QUEUE) {
- release();
- return;
- }
-
- // check the token and if needed, create the callerinfo object.
- if (mCallerInfo == null) {
- if ((mQueryContext == null) || (mQueryUri == null)) {
- throw new QueryPoolException
- ("Bad context or query uri, or CallerInfoAsyncQuery already released.");
- }
-
- // adjust the callerInfo data as needed, and only if it was set from the
- // initial query request.
- // Change the callerInfo number ONLY if it is an emergency number or the
- // voicemail number, and adjust other data (including photoResource)
- // accordingly.
- if (cw.event == EVENT_EMERGENCY_NUMBER) {
- // Note we're setting the phone number here (refer to javadoc
- // comments at the top of CallerInfo class).
- mCallerInfo = new CallerInfo().markAsEmergency(mQueryContext);
- } else if (cw.event == EVENT_VOICEMAIL_NUMBER) {
- mCallerInfo = new CallerInfo().markAsVoiceMail(mQueryContext);
- } else {
- mCallerInfo = CallerInfo.getCallerInfo(mQueryContext, mQueryUri, cursor);
- Log.d(this, "==> Got mCallerInfo: " + mCallerInfo);
-
- CallerInfo newCallerInfo = CallerInfo.doSecondaryLookupIfNecessary(
- mQueryContext, cw.number, mCallerInfo);
- if (newCallerInfo != mCallerInfo) {
- mCallerInfo = newCallerInfo;
- Log.d(this, "#####async contact look up with numeric username"
- + mCallerInfo);
- }
-
- // Final step: look up the geocoded description.
- if (ENABLE_UNKNOWN_NUMBER_GEO_DESCRIPTION) {
- // Note we do this only if we *don't* have a valid name (i.e. if
- // no contacts matched the phone number of the incoming call),
- // since that's the only case where the incoming-call UI cares
- // about this field.
- //
- // (TODO: But if we ever want the UI to show the geoDescription
- // even when we *do* match a contact, we'll need to either call
- // updateGeoDescription() unconditionally here, or possibly add a
- // new parameter to CallerInfoAsyncQuery.startQuery() to force
- // the geoDescription field to be populated.)
-
- if (TextUtils.isEmpty(mCallerInfo.name)) {
- // Actually when no contacts match the incoming phone number,
- // the CallerInfo object is totally blank here (i.e. no name
- // *or* phoneNumber). So we need to pass in cw.number as
- // a fallback number.
- mCallerInfo.updateGeoDescription(mQueryContext, cw.number);
- }
- }
-
- // Use the number entered by the user for display.
- if (!TextUtils.isEmpty(cw.number)) {
- mCallerInfo.phoneNumber = PhoneNumberUtils.formatNumber(cw.number,
- mCallerInfo.normalizedNumber,
- TelephonyManagerUtils.getCurrentCountryIso(mQueryContext,
- Locale.getDefault()));
- }
- }
-
- Log.d(this, "constructing CallerInfo object for token: " + token);
-
- //notify that we can clean up the queue after this.
- CookieWrapper endMarker = new CookieWrapper();
- endMarker.event = EVENT_END_OF_QUEUE;
- startQuery(token, endMarker, null, null, null, null, null);
- }
-
- //notify the listener that the query is complete.
- if (cw.listener != null) {
- Log.d(this, "notifying listener: " + cw.listener.getClass().toString() +
- " for token: " + token + mCallerInfo);
- cw.listener.onQueryComplete(token, cw.cookie, mCallerInfo);
- }
- } finally {
- // The cursor may have been closed in CallerInfo.getCallerInfo()
- if (cursor != null && !cursor.isClosed()) {
- cursor.close();
- }
- }
- }
- }
-
- /**
- * Private constructor for factory methods.
- */
- private CallerInfoAsyncQuery() {
- }
-
- public static void startQuery(final int token, final Context context, final CallerInfo info,
- final OnQueryCompleteListener listener, final Object cookie) {
- Log.d(LOG_TAG, "##### CallerInfoAsyncQuery startContactProviderQuery()... #####");
- Log.d(LOG_TAG, "- number: " + info.phoneNumber);
- Log.d(LOG_TAG, "- cookie: " + cookie);
- if (!PermissionsUtil.hasPermission(context, Manifest.permission.READ_CONTACTS)) {
- Log.w(LOG_TAG, "Dialer doesn't have permission to read contacts.");
- listener.onQueryComplete(token, cookie, info);
- return;
- }
-
- OnQueryCompleteListener contactsProviderQueryCompleteListener =
- new OnQueryCompleteListener() {
- @Override
- public void onQueryComplete(int token, Object cookie, CallerInfo ci) {
- Log.d(LOG_TAG, "contactsProviderQueryCompleteListener done");
- // If there are no other directory queries, make sure that the listener is
- // notified of this result. see b/27621628
- if ((ci != null && ci.contactExists) ||
- !startOtherDirectoriesQuery(token, context, info, listener, cookie)) {
- if (listener != null && ci != null) {
- listener.onQueryComplete(token, cookie, ci);
- }
- }
- }
- };
- startDefaultDirectoryQuery(token, context, info, contactsProviderQueryCompleteListener,
- cookie);
- }
-
- // Private methods
- private static CallerInfoAsyncQuery startDefaultDirectoryQuery(int token, Context context,
- CallerInfo info, OnQueryCompleteListener listener, Object cookie) {
- // Construct the URI object and query params, and start the query.
- Uri uri = ContactInfoHelper.getContactInfoLookupUri(info.phoneNumber);
- return startQueryInternal(token, context, info, listener, cookie, uri);
- }
-
- /**
- * Factory method to start the query based on a CallerInfo object.
- *
- * Note: if the number contains an "@" character we treat it
- * as a SIP address, and look it up directly in the Data table
- * rather than using the PhoneLookup table.
- * TODO: But eventually we should expose two separate methods, one for
- * numbers and one for SIP addresses, and then have
- * PhoneUtils.startGetCallerInfo() decide which one to call based on
- * the phone type of the incoming connection.
- */
- private static CallerInfoAsyncQuery startQueryInternal(int token, Context context,
- CallerInfo info, OnQueryCompleteListener listener, Object cookie, Uri contactRef) {
- if (DBG) {
- Log.d(LOG_TAG, "==> contactRef: " + sanitizeUriToString(contactRef));
- }
-
- CallerInfoAsyncQuery c = new CallerInfoAsyncQuery();
- c.allocate(context, contactRef);
-
- //create cookieWrapper, start query
- CookieWrapper cw = new CookieWrapper();
- cw.listener = listener;
- cw.cookie = cookie;
- cw.number = info.phoneNumber;
-
- // check to see if these are recognized numbers, and use shortcuts if we can.
- if (PhoneNumberUtils.isLocalEmergencyNumber(context, info.phoneNumber)) {
- cw.event = EVENT_EMERGENCY_NUMBER;
- } else if (info.isVoiceMailNumber()) {
- cw.event = EVENT_VOICEMAIL_NUMBER;
- } else {
- cw.event = EVENT_NEW_QUERY;
- }
-
-
- String[] proejection = CallerInfo.getDefaultPhoneLookupProjection(contactRef);
- c.mHandler.startQuery(token,
- cw, // cookie
- contactRef, // uri
- proejection, // projection
- null, // selection
- null, // selectionArgs
- null); // orderBy
- return c;
- }
-
- // Return value indicates if listener was notified.
- private static boolean startOtherDirectoriesQuery(int token, Context context, CallerInfo info,
- OnQueryCompleteListener listener, Object cookie) {
- long[] directoryIds = getDirectoryIds(context);
- int size = directoryIds.length;
- if (size == 0) {
- return false;
- }
-
- DirectoryQueryCompleteListenerFactory listenerFactory =
- new DirectoryQueryCompleteListenerFactory(context, size, listener);
-
- // The current implementation of multiple async query runs in single handler thread
- // in AsyncQueryHandler.
- // intermediateListener.onQueryComplete is also called from the same caller thread.
- // TODO(b/26019872): use thread pool instead of single thread.
- for (int i = 0; i < size; i++) {
- long directoryId = directoryIds[i];
- Uri uri = ContactInfoHelper.getContactInfoLookupUri(info.phoneNumber, directoryId);
- if (DBG) {
- Log.d(LOG_TAG, "directoryId: " + directoryId + " uri: " + uri);
- }
- OnQueryCompleteListener intermediateListener =
- listenerFactory.newListener(directoryId);
- startQueryInternal(token, context, info, intermediateListener, cookie, uri);
- }
- return true;
- }
-
- /* Directory lookup related code - START */
- private static final String[] DIRECTORY_PROJECTION = new String[] {Directory._ID};
-
- private static long[] getDirectoryIds(Context context) {
- ArrayList results = new ArrayList<>();
-
- Uri uri = Directory.CONTENT_URI;
- if (ContactsUtils.FLAG_N_FEATURE) {
- uri = Uri.withAppendedPath(ContactsContract.AUTHORITY_URI, "directories_enterprise");
- }
-
- ContentResolver cr = context.getContentResolver();
- Cursor cursor = cr.query(uri, DIRECTORY_PROJECTION, null, null, null);
- addDirectoryIdsFromCursor(cursor, results);
-
- return Longs.toArray(results);
- }
-
- private static void addDirectoryIdsFromCursor(Cursor cursor, ArrayList results) {
- if (cursor != null) {
- int idIndex = cursor.getColumnIndex(Directory._ID);
- while (cursor.moveToNext()) {
- long id = cursor.getLong(idIndex);
- if (DirectoryCompat.isRemoteDirectoryId(id)) {
- results.add(id);
- }
- }
- cursor.close();
- }
- }
-
- private static final class DirectoryQueryCompleteListenerFactory {
- // Make sure listener to be called once and only once
- private int mCount;
- private boolean mIsListenerCalled;
- private final OnQueryCompleteListener mListener;
- private final Context mContext;
- private final CachedNumberLookupService mCachedNumberLookupService =
- ObjectFactory.newCachedNumberLookupService();
-
- private class DirectoryQueryCompleteListener implements OnQueryCompleteListener {
- private final long mDirectoryId;
-
- DirectoryQueryCompleteListener(long directoryId) {
- mDirectoryId = directoryId;
- }
-
- @Override
- public void onQueryComplete(int token, Object cookie, CallerInfo ci) {
- onDirectoryQueryComplete(token, cookie, ci, mDirectoryId);
- }
- }
-
- DirectoryQueryCompleteListenerFactory(Context context, int size,
- OnQueryCompleteListener listener) {
- mCount = size;
- mListener = listener;
- mIsListenerCalled = false;
- mContext = context;
- }
-
- private void onDirectoryQueryComplete(int token, Object cookie, CallerInfo ci,
- long directoryId) {
- boolean shouldCallListener = false;
- synchronized (this) {
- mCount = mCount - 1;
- if (!mIsListenerCalled && (ci.contactExists || mCount == 0)) {
- mIsListenerCalled = true;
- shouldCallListener = true;
- }
- }
-
- // Don't call callback in synchronized block because mListener.onQueryComplete may
- // take long time to complete
- if (shouldCallListener && mListener != null) {
- addCallerInfoIntoCache(ci, directoryId);
- mListener.onQueryComplete(token, cookie, ci);
- }
- }
-
- private void addCallerInfoIntoCache(CallerInfo ci, long directoryId) {
- if (ci.contactExists && mCachedNumberLookupService != null) {
- // 1. Cache caller info
- CachedContactInfo cachedContactInfo = CallerInfoUtils
- .buildCachedContactInfo(mCachedNumberLookupService, ci);
- String directoryLabel = mContext.getString(R.string.directory_search_label);
- cachedContactInfo.setDirectorySource(directoryLabel, directoryId);
- mCachedNumberLookupService.addContact(mContext, cachedContactInfo);
-
- // 2. Cache photo
- if (ci.contactDisplayPhotoUri != null && ci.normalizedNumber != null) {
- try (InputStream in = mContext.getContentResolver()
- .openInputStream(ci.contactDisplayPhotoUri)) {
- if (in != null) {
- mCachedNumberLookupService.addPhoto(mContext, ci.normalizedNumber, in);
- }
- } catch (IOException e) {
- Log.e(LOG_TAG, "failed to fetch directory contact photo", e);
- }
-
- }
- }
- }
-
- public OnQueryCompleteListener newListener(long directoryId) {
- return new DirectoryQueryCompleteListener(directoryId);
- }
- }
- /* Directory lookup related code - END */
-
- /**
- * Method to create a new CallerInfoAsyncQueryHandler object, ensuring correct
- * state of context and uri.
- */
- private void allocate(Context context, Uri contactRef) {
- if ((context == null) || (contactRef == null)){
- throw new QueryPoolException("Bad context or query uri.");
- }
- mHandler = new CallerInfoAsyncQueryHandler(context);
- mHandler.mQueryContext = context;
- mHandler.mQueryUri = contactRef;
- }
-
- /**
- * Releases the relevant data.
- */
- private void release() {
- mHandler.mQueryContext = null;
- mHandler.mQueryUri = null;
- mHandler.mCallerInfo = null;
- mHandler = null;
- }
-
- private static String sanitizeUriToString(Uri uri) {
- if (uri != null) {
- String uriString = uri.toString();
- int indexOfLastSlash = uriString.lastIndexOf('/');
- if (indexOfLastSlash > 0) {
- return uriString.substring(0, indexOfLastSlash) + "/xxxxxxx";
- } else {
- return uriString;
- }
- } else {
- return "";
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CallerInfoUtils.java b/InCallUI/src/com/android/incallui/CallerInfoUtils.java
deleted file mode 100644
index 289b652fc2fca5348d74db1fed11d354ad2e00a9..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CallerInfoUtils.java
+++ /dev/null
@@ -1,234 +0,0 @@
-package com.android.incallui;
-
-import android.content.Context;
-import android.content.Loader;
-import android.content.Loader.OnLoadCompleteListener;
-import android.net.Uri;
-import android.telecom.PhoneAccount;
-import android.telecom.TelecomManager;
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.android.contacts.common.model.Contact;
-import com.android.contacts.common.model.ContactLoader;
-import com.android.dialer.R;
-import com.android.dialer.calllog.ContactInfo;
-import com.android.dialer.service.CachedNumberLookupService;
-import com.android.dialer.service.CachedNumberLookupService.CachedContactInfo;
-import com.android.dialer.util.TelecomUtil;
-
-import java.util.Arrays;
-
-/**
- * Utility methods for contact and caller info related functionality
- */
-public class CallerInfoUtils {
-
- private static final String TAG = CallerInfoUtils.class.getSimpleName();
-
- /** Define for not a special CNAP string */
- private static final int CNAP_SPECIAL_CASE_NO = -1;
-
- public CallerInfoUtils() {
- }
-
- private static final int QUERY_TOKEN = -1;
-
- /**
- * This is called to get caller info for a call. This will return a CallerInfo
- * object immediately based off information in the call, but
- * more information is returned to the OnQueryCompleteListener (which contains
- * information about the phone number label, user's name, etc).
- */
- public static CallerInfo getCallerInfoForCall(Context context, Call call,
- CallerInfoAsyncQuery.OnQueryCompleteListener listener) {
- CallerInfo info = buildCallerInfo(context, call);
-
- // TODO: Have phoneapp send a Uri when it knows the contact that triggered this call.
-
- if (info.numberPresentation == TelecomManager.PRESENTATION_ALLOWED) {
- // Start the query with the number provided from the call.
- Log.d(TAG, "==> Actually starting CallerInfoAsyncQuery.startQuery()...");
- CallerInfoAsyncQuery.startQuery(QUERY_TOKEN, context, info, listener, call);
- }
- return info;
- }
-
- public static CallerInfo buildCallerInfo(Context context, Call call) {
- CallerInfo info = new CallerInfo();
-
- // Store CNAP information retrieved from the Connection (we want to do this
- // here regardless of whether the number is empty or not).
- info.cnapName = call.getCnapName();
- info.name = info.cnapName;
- info.numberPresentation = call.getNumberPresentation();
- info.namePresentation = call.getCnapNamePresentation();
- info.callSubject = call.getCallSubject();
-
- String number = call.getNumber();
- if (!TextUtils.isEmpty(number)) {
- final String[] numbers = number.split("&");
- number = numbers[0];
- if (numbers.length > 1) {
- info.forwardingNumber = numbers[1];
- }
-
- number = modifyForSpecialCnapCases(context, info, number, info.numberPresentation);
- info.phoneNumber = number;
- }
-
- // Because the InCallUI is immediately launched before the call is connected, occasionally
- // a voicemail call will be passed to InCallUI as a "voicemail:" URI without a number.
- // This call should still be handled as a voicemail call.
- if ((call.getHandle() != null &&
- PhoneAccount.SCHEME_VOICEMAIL.equals(call.getHandle().getScheme())) ||
- isVoiceMailNumber(context, call)) {
- info.markAsVoiceMail(context);
- }
-
- ContactInfoCache.getInstance(context).maybeInsertCnapInformationIntoCache(context, call,
- info);
-
- return info;
- }
-
- /**
- * Creates a new {@link CachedContactInfo} from a {@link CallerInfo}
- *
- * @param lookupService the {@link CachedNumberLookupService} used to build a
- * new {@link CachedContactInfo}
- * @param {@link CallerInfo} object
- * @return a CachedContactInfo object created from this CallerInfo
- * @throws NullPointerException if lookupService or ci are null
- */
- public static CachedContactInfo buildCachedContactInfo(CachedNumberLookupService lookupService,
- CallerInfo ci) {
- ContactInfo info = new ContactInfo();
- info.name = ci.name;
- info.type = ci.numberType;
- info.label = ci.phoneLabel;
- info.number = ci.phoneNumber;
- info.normalizedNumber = ci.normalizedNumber;
- info.photoUri = ci.contactDisplayPhotoUri;
- info.userType = ci.userType;
-
- CachedContactInfo cacheInfo = lookupService.buildCachedContactInfo(info);
- cacheInfo.setLookupKey(ci.lookupKeyOrNull);
- return cacheInfo;
- }
-
- public static boolean isVoiceMailNumber(Context context, Call call) {
- return TelecomUtil.isVoicemailNumber(context,
- call.getTelecomCall().getDetails().getAccountHandle(),
- call.getNumber());
- }
-
- /**
- * Handles certain "corner cases" for CNAP. When we receive weird phone numbers
- * from the network to indicate different number presentations, convert them to
- * expected number and presentation values within the CallerInfo object.
- * @param number number we use to verify if we are in a corner case
- * @param presentation presentation value used to verify if we are in a corner case
- * @return the new String that should be used for the phone number
- */
- /* package */static String modifyForSpecialCnapCases(Context context, CallerInfo ci,
- String number, int presentation) {
- // Obviously we return number if ci == null, but still return number if
- // number == null, because in these cases the correct string will still be
- // displayed/logged after this function returns based on the presentation value.
- if (ci == null || number == null) return number;
-
- Log.d(TAG, "modifyForSpecialCnapCases: initially, number="
- + toLogSafePhoneNumber(number)
- + ", presentation=" + presentation + " ci " + ci);
-
- // "ABSENT NUMBER" is a possible value we could get from the network as the
- // phone number, so if this happens, change it to "Unknown" in the CallerInfo
- // and fix the presentation to be the same.
- final String[] absentNumberValues =
- context.getResources().getStringArray(R.array.absent_num);
- if (Arrays.asList(absentNumberValues).contains(number)
- && presentation == TelecomManager.PRESENTATION_ALLOWED) {
- number = context.getString(R.string.unknown);
- ci.numberPresentation = TelecomManager.PRESENTATION_UNKNOWN;
- }
-
- // Check for other special "corner cases" for CNAP and fix them similarly. Corner
- // cases only apply if we received an allowed presentation from the network, so check
- // if we think we have an allowed presentation, or if the CallerInfo presentation doesn't
- // match the presentation passed in for verification (meaning we changed it previously
- // because it's a corner case and we're being called from a different entry point).
- if (ci.numberPresentation == TelecomManager.PRESENTATION_ALLOWED
- || (ci.numberPresentation != presentation
- && presentation == TelecomManager.PRESENTATION_ALLOWED)) {
- // For all special strings, change number & numberPrentation.
- if (isCnapSpecialCaseRestricted(number)) {
- number = context.getString(R.string.private_num);
- ci.numberPresentation = TelecomManager.PRESENTATION_RESTRICTED;
- } else if (isCnapSpecialCaseUnknown(number)) {
- number = context.getString(R.string.unknown);
- ci.numberPresentation = TelecomManager.PRESENTATION_UNKNOWN;
- }
- Log.d(TAG, "SpecialCnap: number=" + toLogSafePhoneNumber(number)
- + "; presentation now=" + ci.numberPresentation);
- }
- Log.d(TAG, "modifyForSpecialCnapCases: returning number string="
- + toLogSafePhoneNumber(number));
- return number;
- }
-
- private static boolean isCnapSpecialCaseRestricted(String n) {
- return n.equals("PRIVATE") || n.equals("P") || n.equals("RES");
- }
-
- private static boolean isCnapSpecialCaseUnknown(String n) {
- return n.equals("UNAVAILABLE") || n.equals("UNKNOWN") || n.equals("UNA") || n.equals("U");
- }
-
- /* package */static String toLogSafePhoneNumber(String number) {
- // For unknown number, log empty string.
- if (number == null) {
- return "";
- }
-
- // Todo: Figure out an equivalent for VDBG
- if (false) {
- // When VDBG is true we emit PII.
- return number;
- }
-
- // Do exactly same thing as Uri#toSafeString() does, which will enable us to compare
- // sanitized phone numbers.
- StringBuilder builder = new StringBuilder();
- for (int i = 0; i < number.length(); i++) {
- char c = number.charAt(i);
- if (c == '-' || c == '@' || c == '.' || c == '&') {
- builder.append(c);
- } else {
- builder.append('x');
- }
- }
- return builder.toString();
- }
-
- /**
- * Send a notification using a {@link ContactLoader} to inform the sync adapter that we are
- * viewing a particular contact, so that it can download the high-res photo.
- */
- public static void sendViewNotification(Context context, Uri contactUri) {
- final ContactLoader loader = new ContactLoader(context, contactUri,
- true /* postViewNotification */);
- loader.registerListener(0, new OnLoadCompleteListener() {
- @Override
- public void onLoadComplete(
- Loader loader, Contact contact) {
- try {
- loader.reset();
- } catch (RuntimeException e) {
- Log.e(TAG, "Error resetting loader", e);
- }
- }
- });
- loader.startLoading();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/CircularRevealFragment.java b/InCallUI/src/com/android/incallui/CircularRevealFragment.java
deleted file mode 100644
index 01bd253ec2a58d0136452d80d4a54ac91113f3db..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/CircularRevealFragment.java
+++ /dev/null
@@ -1,170 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.animation.Animator;
-import android.animation.AnimatorListenerAdapter;
-import android.app.Activity;
-import android.app.Fragment;
-import android.app.FragmentManager;
-import android.graphics.Outline;
-import android.graphics.Point;
-import android.os.Bundle;
-import android.view.Display;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewAnimationUtils;
-import android.view.ViewGroup;
-import android.view.ViewOutlineProvider;
-import android.view.ViewTreeObserver;
-import android.view.ViewTreeObserver.OnPreDrawListener;
-
-import com.android.contacts.common.util.MaterialColorMapUtils.MaterialPalette;
-import com.android.dialer.R;
-
-public class CircularRevealFragment extends Fragment {
- static final String TAG = "CircularRevealFragment";
-
- private Point mTouchPoint;
- private OnCircularRevealCompleteListener mListener;
- private boolean mAnimationStarted;
-
- interface OnCircularRevealCompleteListener {
- public void onCircularRevealComplete(FragmentManager fm);
- }
-
- public static void startCircularReveal(FragmentManager fm, Point touchPoint,
- OnCircularRevealCompleteListener listener) {
- if (fm.findFragmentByTag(TAG) == null) {
- fm.beginTransaction().add(R.id.main,
- new CircularRevealFragment(touchPoint, listener), TAG)
- .commitAllowingStateLoss();
- } else {
- Log.w(TAG, "An instance of CircularRevealFragment already exists");
- }
- }
-
- public static void endCircularReveal(FragmentManager fm) {
- final Fragment fragment = fm.findFragmentByTag(TAG);
- if (fragment != null) {
- fm.beginTransaction().remove(fragment).commitAllowingStateLoss();
- }
- }
-
- /**
- * Empty constructor used only by the {@link FragmentManager}.
- */
- public CircularRevealFragment() {}
-
- public CircularRevealFragment(Point touchPoint, OnCircularRevealCompleteListener listener) {
- mTouchPoint = touchPoint;
- mListener = listener;
- }
-
- @Override
- public void onResume() {
- super.onResume();
- if (!mAnimationStarted) {
- // Only run the animation once for each instance of the fragment
- startOutgoingAnimation(InCallPresenter.getInstance().getThemeColors());
- }
- mAnimationStarted = true;
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- return inflater.inflate(R.layout.outgoing_call_animation, container, false);
- }
-
- public void startOutgoingAnimation(MaterialPalette palette) {
- final Activity activity = getActivity();
- if (activity == null) {
- Log.w(this, "Asked to do outgoing call animation when not attached");
- return;
- }
-
- final View view = activity.getWindow().getDecorView();
-
- // The circle starts from an initial size of 0 so clip it such that it is invisible.
- // Otherwise the first frame is drawn with a fully opaque screen which causes jank. When
- // the animation later starts, this clip will be clobbered by the circular reveal clip.
- // See ViewAnimationUtils.createCircularReveal.
- view.setOutlineProvider(new ViewOutlineProvider() {
- @Override
- public void getOutline(View view, Outline outline) {
- // Using (0, 0, 0, 0) will not work since the outline will simply be treated as
- // an empty outline.
- outline.setOval(-1, -1, 0, 0);
- }
- });
- view.setClipToOutline(true);
-
- if (palette != null) {
- view.findViewById(R.id.outgoing_call_animation_circle).setBackgroundColor(
- palette.mPrimaryColor);
- activity.getWindow().setStatusBarColor(palette.mSecondaryColor);
- }
-
- view.getViewTreeObserver().addOnPreDrawListener(new OnPreDrawListener() {
- @Override
- public boolean onPreDraw() {
- final ViewTreeObserver vto = view.getViewTreeObserver();
- if (vto.isAlive()) {
- vto.removeOnPreDrawListener(this);
- }
- final Animator animator = getRevealAnimator(mTouchPoint);
- if (animator != null) {
- animator.addListener(new AnimatorListenerAdapter() {
- @Override
- public void onAnimationEnd(Animator animation) {
- view.setClipToOutline(false);
- if (mListener != null) {
- mListener.onCircularRevealComplete(getFragmentManager());
- }
- }
- });
- animator.start();
- }
- return false;
- }
- });
- }
-
- private Animator getRevealAnimator(Point touchPoint) {
- final Activity activity = getActivity();
- if (activity == null) {
- return null;
- }
- final View view = activity.getWindow().getDecorView();
- final Display display = activity.getWindowManager().getDefaultDisplay();
- final Point size = new Point();
- display.getSize(size);
-
- int startX = size.x / 2;
- int startY = size.y / 2;
- if (touchPoint != null) {
- startX = touchPoint.x;
- startY = touchPoint.y;
- }
-
- final Animator valueAnimator = ViewAnimationUtils.createCircularReveal(view,
- startX, startY, 0, Math.max(size.x, size.y));
- valueAnimator.setDuration(getResources().getInteger(R.integer.reveal_animation_duration));
- return valueAnimator;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ConferenceManagerFragment.java b/InCallUI/src/com/android/incallui/ConferenceManagerFragment.java
deleted file mode 100644
index fe941c8c500f4dfae47d38ba47b500968307cda1..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ConferenceManagerFragment.java
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.app.ActionBar;
-import android.content.Context;
-import android.os.Bundle;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ListView;
-
-import com.android.contacts.common.ContactPhotoManager;
-import com.android.dialer.R;
-
-import java.util.List;
-
-/**
- * Fragment that allows the user to manage a conference call.
- */
-public class ConferenceManagerFragment
- extends BaseFragment
- implements ConferenceManagerPresenter.ConferenceManagerUi {
-
- private static final String KEY_IS_VISIBLE = "key_conference_is_visible";
-
- private ListView mConferenceParticipantList;
- private int mActionBarElevation;
- private ContactPhotoManager mContactPhotoManager;
- private LayoutInflater mInflater;
- private ConferenceParticipantListAdapter mConferenceParticipantListAdapter;
- private boolean mIsVisible;
- private boolean mIsRecreating;
-
- @Override
- public ConferenceManagerPresenter createPresenter() {
- return new ConferenceManagerPresenter();
- }
-
- @Override
- public ConferenceManagerPresenter.ConferenceManagerUi getUi() {
- return this;
- }
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- if (savedInstanceState != null) {
- mIsRecreating = true;
- mIsVisible = savedInstanceState.getBoolean(KEY_IS_VISIBLE);
- }
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- final View parent =
- inflater.inflate(R.layout.conference_manager_fragment, container, false);
-
- mConferenceParticipantList = (ListView) parent.findViewById(R.id.participantList);
- mContactPhotoManager =
- ContactPhotoManager.getInstance(getActivity().getApplicationContext());
- mActionBarElevation =
- (int) getResources().getDimension(R.dimen.incall_action_bar_elevation);
- mInflater = LayoutInflater.from(getActivity().getApplicationContext());
-
- return parent;
- }
-
- @Override
- public void onResume() {
- super.onResume();
- if (mIsRecreating) {
- onVisibilityChanged(mIsVisible);
- }
- }
-
- @Override
- public void onSaveInstanceState(Bundle outState) {
- outState.putBoolean(KEY_IS_VISIBLE, mIsVisible);
- super.onSaveInstanceState(outState);
- }
-
- public void onVisibilityChanged(boolean isVisible) {
- mIsVisible = isVisible;
- ActionBar actionBar = getActivity().getActionBar();
- if (isVisible) {
- actionBar.setTitle(R.string.manageConferenceLabel);
- actionBar.setElevation(mActionBarElevation);
- actionBar.setHideOffset(0);
- actionBar.show();
-
- final CallList calls = CallList.getInstance();
- getPresenter().init(getActivity(), calls);
- // Request focus on the list of participants for accessibility purposes. This ensures
- // that once the list of participants is shown, the first participant is announced.
- mConferenceParticipantList.requestFocus();
- } else {
- actionBar.setElevation(0);
- actionBar.setHideOffset(actionBar.getHeight());
- }
- }
-
- @Override
- public boolean isFragmentVisible() {
- return isVisible();
- }
-
- @Override
- public void update(Context context, List participants, boolean parentCanSeparate) {
- if (mConferenceParticipantListAdapter == null) {
- mConferenceParticipantListAdapter = new ConferenceParticipantListAdapter(
- mConferenceParticipantList, context, mInflater, mContactPhotoManager);
-
- mConferenceParticipantList.setAdapter(mConferenceParticipantListAdapter);
- }
- mConferenceParticipantListAdapter.updateParticipants(participants, parentCanSeparate);
- }
-
- @Override
- public void refreshCall(Call call) {
- mConferenceParticipantListAdapter.refreshCall(call);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ConferenceManagerPresenter.java b/InCallUI/src/com/android/incallui/ConferenceManagerPresenter.java
deleted file mode 100644
index 6fb6e5dda10142a08f0af7ac7e5911b364945189..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ConferenceManagerPresenter.java
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-
-import com.android.incallui.InCallPresenter.InCallDetailsListener;
-import com.android.incallui.InCallPresenter.InCallState;
-import com.android.incallui.InCallPresenter.InCallStateListener;
-import com.android.incallui.InCallPresenter.IncomingCallListener;
-
-import com.google.common.base.Preconditions;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * Logic for call buttons.
- */
-public class ConferenceManagerPresenter
- extends Presenter
- implements InCallStateListener, InCallDetailsListener, IncomingCallListener {
-
- private Context mContext;
-
- @Override
- public void onUiReady(ConferenceManagerUi ui) {
- super.onUiReady(ui);
-
- // register for call state changes last
- InCallPresenter.getInstance().addListener(this);
- InCallPresenter.getInstance().addIncomingCallListener(this);
- }
-
- @Override
- public void onUiUnready(ConferenceManagerUi ui) {
- super.onUiUnready(ui);
-
- InCallPresenter.getInstance().removeListener(this);
- InCallPresenter.getInstance().removeIncomingCallListener(this);
- }
-
- @Override
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList) {
- if (getUi().isFragmentVisible()) {
- Log.v(this, "onStateChange" + newState);
- if (newState == InCallState.INCALL) {
- final Call call = callList.getActiveOrBackgroundCall();
- if (call != null && call.isConferenceCall()) {
- Log.v(this, "Number of existing calls is " +
- String.valueOf(call.getChildCallIds().size()));
- update(callList);
- } else {
- InCallPresenter.getInstance().showConferenceCallManager(false);
- }
- } else {
- InCallPresenter.getInstance().showConferenceCallManager(false);
- }
- }
- }
-
- @Override
- public void onDetailsChanged(Call call, android.telecom.Call.Details details) {
- boolean canDisconnect = details.can(
- android.telecom.Call.Details.CAPABILITY_DISCONNECT_FROM_CONFERENCE);
- boolean canSeparate = details.can(
- android.telecom.Call.Details.CAPABILITY_SEPARATE_FROM_CONFERENCE);
-
- if (call.can(android.telecom.Call.Details.CAPABILITY_DISCONNECT_FROM_CONFERENCE)
- != canDisconnect
- || call.can(android.telecom.Call.Details.CAPABILITY_SEPARATE_FROM_CONFERENCE)
- != canSeparate) {
- getUi().refreshCall(call);
- }
-
- if (!details.can(
- android.telecom.Call.Details.CAPABILITY_MANAGE_CONFERENCE)) {
- InCallPresenter.getInstance().showConferenceCallManager(false);
- }
- }
-
- @Override
- public void onIncomingCall(InCallState oldState, InCallState newState, Call call) {
- // When incoming call exists, set conference ui invisible.
- if (getUi().isFragmentVisible()) {
- Log.d(this, "onIncomingCall()... Conference ui is showing, hide it.");
- InCallPresenter.getInstance().showConferenceCallManager(false);
- }
- }
-
- public void init(Context context, CallList callList) {
- mContext = Preconditions.checkNotNull(context);
- mContext = context;
- update(callList);
- }
-
- /**
- * Updates the conference participant adapter.
- *
- * @param callList The callList.
- */
- private void update(CallList callList) {
- // callList is non null, but getActiveOrBackgroundCall() may return null
- final Call currentCall = callList.getActiveOrBackgroundCall();
- if (currentCall == null) {
- return;
- }
-
- ArrayList calls = new ArrayList<>(currentCall.getChildCallIds().size());
- for (String callerId : currentCall.getChildCallIds()) {
- calls.add(callList.getCallById(callerId));
- }
-
- Log.d(this, "Number of calls is " + String.valueOf(calls.size()));
-
- // Users can split out a call from the conference call if either the active call or the
- // holding call is empty. If both are filled, users can not split out another call.
- final boolean hasActiveCall = (callList.getActiveCall() != null);
- final boolean hasHoldingCall = (callList.getBackgroundCall() != null);
- boolean canSeparate = !(hasActiveCall && hasHoldingCall);
-
- getUi().update(mContext, calls, canSeparate);
- }
-
- public interface ConferenceManagerUi extends Ui {
- boolean isFragmentVisible();
- void update(Context context, List participants, boolean parentCanSeparate);
- void refreshCall(Call call);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ConferenceParticipantListAdapter.java b/InCallUI/src/com/android/incallui/ConferenceParticipantListAdapter.java
deleted file mode 100644
index d68ae1f6f7fe745126238037a32434918b685fd4..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ConferenceParticipantListAdapter.java
+++ /dev/null
@@ -1,533 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.MoreObjects;
-
-import android.content.Context;
-import android.net.Uri;
-import android.support.annotation.Nullable;
-import android.text.BidiFormatter;
-import android.text.TextDirectionHeuristics;
-import android.text.TextUtils;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-import android.widget.ImageView;
-import android.widget.ListView;
-import android.widget.TextView;
-
-import com.android.contacts.common.ContactPhotoManager;
-import com.android.contacts.common.ContactPhotoManager.DefaultImageRequest;
-import com.android.contacts.common.compat.PhoneNumberUtilsCompat;
-import com.android.contacts.common.preference.ContactsPreferences;
-import com.android.contacts.common.util.ContactDisplayUtils;
-import com.android.dialer.R;
-import com.android.incallui.ContactInfoCache.ContactCacheEntry;
-
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Objects;
-
-/**
- * Adapter for a ListView containing conference call participant information.
- */
-public class ConferenceParticipantListAdapter extends BaseAdapter {
-
- /**
- * Internal class which represents a participant. Includes a reference to the {@link Call} and
- * the corresponding {@link ContactCacheEntry} for the participant.
- */
- private class ParticipantInfo {
- private Call mCall;
- private ContactCacheEntry mContactCacheEntry;
- private boolean mCacheLookupComplete = false;
-
- public ParticipantInfo(Call call, ContactCacheEntry contactCacheEntry) {
- mCall = call;
- mContactCacheEntry = contactCacheEntry;
- }
-
- public Call getCall() {
- return mCall;
- }
-
- public void setCall(Call call) {
- mCall = call;
- }
-
- public ContactCacheEntry getContactCacheEntry() {
- return mContactCacheEntry;
- }
-
- public void setContactCacheEntry(ContactCacheEntry entry) {
- mContactCacheEntry = entry;
- }
-
- public boolean isCacheLookupComplete() {
- return mCacheLookupComplete;
- }
-
- public void setCacheLookupComplete(boolean cacheLookupComplete) {
- mCacheLookupComplete = cacheLookupComplete;
- }
-
- @Override
- public boolean equals(Object o) {
- if (o instanceof ParticipantInfo) {
- ParticipantInfo p = (ParticipantInfo) o;
- return
- Objects.equals(p.getCall().getId(), mCall.getId());
- }
- return false;
- }
-
- @Override
- public int hashCode() {
- return mCall.getId().hashCode();
- }
- }
-
- /**
- * Callback class used when making requests to the {@link ContactInfoCache} to resolve contact
- * info and contact photos for conference participants.
- */
- public static class ContactLookupCallback implements ContactInfoCache.ContactInfoCacheCallback {
- private final WeakReference mListAdapter;
-
- public ContactLookupCallback(ConferenceParticipantListAdapter listAdapter) {
- mListAdapter = new WeakReference(listAdapter);
- }
-
- /**
- * Called when contact info has been resolved.
- *
- * @param callId The call id.
- * @param entry The new contact information.
- */
- @Override
- public void onContactInfoComplete(String callId, ContactCacheEntry entry) {
- update(callId, entry);
- }
-
- /**
- * Called when contact photo has been loaded into the cache.
- *
- * @param callId The call id.
- * @param entry The new contact information.
- */
- @Override
- public void onImageLoadComplete(String callId, ContactCacheEntry entry) {
- update(callId, entry);
- }
-
- @Override
- public void onContactInteractionsInfoComplete(String callId, ContactCacheEntry entry) {}
-
- /**
- * Updates the contact information for a participant.
- *
- * @param callId The call id.
- * @param entry The new contact information.
- */
- private void update(String callId, ContactCacheEntry entry) {
- ConferenceParticipantListAdapter listAdapter = mListAdapter.get();
- if (listAdapter != null) {
- listAdapter.updateContactInfo(callId, entry);
- }
- }
- }
-
- /**
- * Listener used to handle tap of the "disconnect' button for a participant.
- */
- private View.OnClickListener mDisconnectListener = new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- View parent = (View) v.getParent();
- String callId = (String) parent.getTag();
- TelecomAdapter.getInstance().disconnectCall(callId);
- }
- };
-
- /**
- * Listener used to handle tap of the "separate' button for a participant.
- */
- private View.OnClickListener mSeparateListener = new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- View parent = (View) v.getParent();
- String callId = (String) parent.getTag();
- TelecomAdapter.getInstance().separateCall(callId);
- }
- };
-
- /**
- * The ListView containing the participant information.
- */
- private final ListView mListView;
-
- /**
- * The conference participants to show in the ListView.
- */
- private List mConferenceParticipants = new ArrayList<>();
-
- /**
- * Hashmap to make accessing participant info by call Id faster.
- */
- private final HashMap mParticipantsByCallId = new HashMap<>();
-
- /**
- * The context.
- */
- private final Context mContext;
-
- /**
- * ContactsPreferences used to lookup displayName preferences
- */
- @Nullable private final ContactsPreferences mContactsPreferences;
-
- /**
- * The layout inflater used to inflate new views.
- */
- private final LayoutInflater mLayoutInflater;
-
- /**
- * Contact photo manager to retrieve cached contact photo information.
- */
- private final ContactPhotoManager mContactPhotoManager;
-
- /**
- * {@code True} if the conference parent supports separating calls from the conference.
- */
- private boolean mParentCanSeparate;
-
- /**
- * Creates an instance of the ConferenceParticipantListAdapter.
- *
- * @param listView The listview.
- * @param context The context.
- * @param layoutInflater The layout inflater.
- * @param contactPhotoManager The contact photo manager, used to load contact photos.
- */
- public ConferenceParticipantListAdapter(ListView listView, Context context,
- LayoutInflater layoutInflater, ContactPhotoManager contactPhotoManager) {
-
- mListView = listView;
- mContext = context;
- mContactsPreferences = ContactsPreferencesFactory.newContactsPreferences(mContext);
- mLayoutInflater = layoutInflater;
- mContactPhotoManager = contactPhotoManager;
- }
-
- /**
- * Updates the adapter with the new conference participant information provided.
- *
- * @param conferenceParticipants The list of conference participants.
- * @param parentCanSeparate {@code True} if the parent supports separating calls from the
- * conference.
- */
- public void updateParticipants(List conferenceParticipants, boolean parentCanSeparate) {
- if (mContactsPreferences != null) {
- mContactsPreferences.refreshValue(ContactsPreferences.DISPLAY_ORDER_KEY);
- mContactsPreferences.refreshValue(ContactsPreferences.SORT_ORDER_KEY);
- }
- mParentCanSeparate = parentCanSeparate;
- updateParticipantInfo(conferenceParticipants);
- }
-
- /**
- * Determines the number of participants in the conference.
- *
- * @return The number of participants.
- */
- @Override
- public int getCount() {
- return mConferenceParticipants.size();
- }
-
- /**
- * Retrieves an item from the list of participants.
- *
- * @param position Position of the item whose data we want within the adapter's
- * data set.
- * @return The {@link ParticipantInfo}.
- */
- @Override
- public Object getItem(int position) {
- return mConferenceParticipants.get(position);
- }
-
- /**
- * Retreives the adapter-specific item id for an item at a specified position.
- *
- * @param position The position of the item within the adapter's data set whose row id we want.
- * @return The item id.
- */
- @Override
- public long getItemId(int position) {
- return position;
- }
-
- /**
- * Refreshes call information for the call passed in.
- *
- * @param call The new call information.
- */
- public void refreshCall(Call call) {
- String callId = call.getId();
-
- if (mParticipantsByCallId.containsKey(callId)) {
- ParticipantInfo participantInfo = mParticipantsByCallId.get(callId);
- participantInfo.setCall(call);
- refreshView(callId);
- }
- }
-
- /**
- * Attempts to refresh the view for the specified call ID. This ensures the contact info and
- * photo loaded from cache are updated.
- *
- * @param callId The call id.
- */
- private void refreshView(String callId) {
- int first = mListView.getFirstVisiblePosition();
- int last = mListView.getLastVisiblePosition();
-
- for (int position = 0; position <= last - first; position++) {
- View view = mListView.getChildAt(position);
- String rowCallId = (String) view.getTag();
- if (rowCallId.equals(callId)) {
- getView(position+first, view, mListView);
- break;
- }
- }
- }
-
- /**
- * Creates or populates an existing conference participant row.
- *
- * @param position The position of the item within the adapter's data set of the item whose view
- * we want.
- * @param convertView The old view to reuse, if possible.
- * @param parent The parent that this view will eventually be attached to
- * @return The populated view.
- */
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- // Make sure we have a valid convertView to start with
- final View result = convertView == null
- ? mLayoutInflater.inflate(R.layout.caller_in_conference, parent, false)
- : convertView;
-
- ParticipantInfo participantInfo = mConferenceParticipants.get(position);
- Call call = participantInfo.getCall();
- ContactCacheEntry contactCache = participantInfo.getContactCacheEntry();
-
- final ContactInfoCache cache = ContactInfoCache.getInstance(mContext);
-
- // If a cache lookup has not yet been performed to retrieve the contact information and
- // photo, do it now.
- if (!participantInfo.isCacheLookupComplete()) {
- cache.findInfo(participantInfo.getCall(),
- participantInfo.getCall().getState() == Call.State.INCOMING,
- new ContactLookupCallback(this));
- }
-
- boolean thisRowCanSeparate = mParentCanSeparate && call.getTelecomCall().getDetails().can(
- android.telecom.Call.Details.CAPABILITY_SEPARATE_FROM_CONFERENCE);
- boolean thisRowCanDisconnect = call.getTelecomCall().getDetails().can(
- android.telecom.Call.Details.CAPABILITY_DISCONNECT_FROM_CONFERENCE);
-
- setCallerInfoForRow(result, contactCache.namePrimary,
- ContactDisplayUtils.getPreferredDisplayName(contactCache.namePrimary,
- contactCache.nameAlternative, mContactsPreferences),
- contactCache.number, contactCache.label,
- contactCache.lookupKey, contactCache.displayPhotoUri, thisRowCanSeparate,
- thisRowCanDisconnect);
-
- // Tag the row in the conference participant list with the call id to make it easier to
- // find calls when contact cache information is loaded.
- result.setTag(call.getId());
-
- return result;
- }
-
- /**
- * Replaces the contact info for a participant and triggers a refresh of the UI.
- *
- * @param callId The call id.
- * @param entry The new contact info.
- */
- /* package */ void updateContactInfo(String callId, ContactCacheEntry entry) {
- if (mParticipantsByCallId.containsKey(callId)) {
- ParticipantInfo participantInfo = mParticipantsByCallId.get(callId);
- participantInfo.setContactCacheEntry(entry);
- participantInfo.setCacheLookupComplete(true);
- refreshView(callId);
- }
- }
-
- /**
- * Sets the caller information for a row in the conference participant list.
- *
- * @param view The view to set the details on.
- * @param callerName The participant's name.
- * @param callerNumber The participant's phone number.
- * @param callerNumberType The participant's phone number typ.e
- * @param lookupKey The lookup key for the participant (for photo lookup).
- * @param photoUri The URI of the contact photo.
- * @param thisRowCanSeparate {@code True} if this participant can separate from the conference.
- * @param thisRowCanDisconnect {@code True} if this participant can be disconnected.
- */
- private final void setCallerInfoForRow(View view, String callerName, String preferredName,
- String callerNumber, String callerNumberType, String lookupKey, Uri photoUri,
- boolean thisRowCanSeparate, boolean thisRowCanDisconnect) {
-
- final ImageView photoView = (ImageView) view.findViewById(R.id.callerPhoto);
- final TextView nameTextView = (TextView) view.findViewById(R.id.conferenceCallerName);
- final TextView numberTextView = (TextView) view.findViewById(R.id.conferenceCallerNumber);
- final TextView numberTypeTextView = (TextView) view.findViewById(
- R.id.conferenceCallerNumberType);
- final View endButton = view.findViewById(R.id.conferenceCallerDisconnect);
- final View separateButton = view.findViewById(R.id.conferenceCallerSeparate);
-
- endButton.setVisibility(thisRowCanDisconnect ? View.VISIBLE : View.GONE);
- if (thisRowCanDisconnect) {
- endButton.setOnClickListener(mDisconnectListener);
- } else {
- endButton.setOnClickListener(null);
- }
-
- separateButton.setVisibility(thisRowCanSeparate ? View.VISIBLE : View.GONE);
- if (thisRowCanSeparate) {
- separateButton.setOnClickListener(mSeparateListener);
- } else {
- separateButton.setOnClickListener(null);
- }
-
- DefaultImageRequest imageRequest = (photoUri != null) ? null :
- new DefaultImageRequest(callerName, lookupKey, true /* isCircularPhoto */);
-
- mContactPhotoManager.loadDirectoryPhoto(photoView, photoUri, false, true, imageRequest);
-
- // set the caller name
- nameTextView.setText(preferredName);
-
- // set the caller number in subscript, or make the field disappear.
- if (TextUtils.isEmpty(callerNumber)) {
- numberTextView.setVisibility(View.GONE);
- numberTypeTextView.setVisibility(View.GONE);
- } else {
- numberTextView.setVisibility(View.VISIBLE);
- numberTextView.setText(PhoneNumberUtilsCompat.createTtsSpannable(
- BidiFormatter.getInstance().unicodeWrap(
- callerNumber, TextDirectionHeuristics.LTR)));
- numberTypeTextView.setVisibility(View.VISIBLE);
- numberTypeTextView.setText(callerNumberType);
- }
- }
-
- /**
- * Updates the participant info list which is bound to the ListView. Stores the call and
- * contact info for all entries. The list is sorted alphabetically by participant name.
- *
- * @param conferenceParticipants The calls which make up the conference participants.
- */
- private void updateParticipantInfo(List conferenceParticipants) {
- final ContactInfoCache cache = ContactInfoCache.getInstance(mContext);
- boolean newParticipantAdded = false;
- HashSet newCallIds = new HashSet<>(conferenceParticipants.size());
-
- // Update or add conference participant info.
- for (Call call : conferenceParticipants) {
- String callId = call.getId();
- newCallIds.add(callId);
- ContactCacheEntry contactCache = cache.getInfo(callId);
- if (contactCache == null) {
- contactCache = ContactInfoCache.buildCacheEntryFromCall(mContext, call,
- call.getState() == Call.State.INCOMING);
- }
-
- if (mParticipantsByCallId.containsKey(callId)) {
- ParticipantInfo participantInfo = mParticipantsByCallId.get(callId);
- participantInfo.setCall(call);
- participantInfo.setContactCacheEntry(contactCache);
- } else {
- newParticipantAdded = true;
- ParticipantInfo participantInfo = new ParticipantInfo(call, contactCache);
- mConferenceParticipants.add(participantInfo);
- mParticipantsByCallId.put(call.getId(), participantInfo);
- }
- }
-
- // Remove any participants that no longer exist.
- Iterator> it =
- mParticipantsByCallId.entrySet().iterator();
- while (it.hasNext()) {
- Map.Entry entry = it.next();
- String existingCallId = entry.getKey();
- if (!newCallIds.contains(existingCallId)) {
- ParticipantInfo existingInfo = entry.getValue();
- mConferenceParticipants.remove(existingInfo);
- it.remove();
- }
- }
-
- if (newParticipantAdded) {
- // Sort the list of participants by contact name.
- sortParticipantList();
- }
- notifyDataSetChanged();
- }
-
- /**
- * Sorts the participant list by contact name.
- */
- private void sortParticipantList() {
- Collections.sort(mConferenceParticipants, new Comparator() {
- public int compare(ParticipantInfo p1, ParticipantInfo p2) {
- // Contact names might be null, so replace with empty string.
- ContactCacheEntry c1 = p1.getContactCacheEntry();
- String p1Name = MoreObjects.firstNonNull(
- ContactDisplayUtils.getPreferredSortName(
- c1.namePrimary,
- c1.nameAlternative,
- mContactsPreferences),
- "");
-
- ContactCacheEntry c2 = p2.getContactCacheEntry();
- String p2Name = MoreObjects.firstNonNull(
- ContactDisplayUtils.getPreferredSortName(
- c2.namePrimary,
- c2.nameAlternative,
- mContactsPreferences),
- "");
-
- return p1Name.compareToIgnoreCase(p2Name);
- }
- });
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ContactInfoCache.java b/InCallUI/src/com/android/incallui/ContactInfoCache.java
deleted file mode 100644
index 9d6fc462729cff0e3c37a8cee791ed977f5f9c46..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ContactInfoCache.java
+++ /dev/null
@@ -1,699 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.MoreObjects;
-import com.google.common.base.Preconditions;
-import com.google.common.collect.Maps;
-import com.google.common.collect.Sets;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.location.Address;
-import android.media.RingtoneManager;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Looper;
-import android.provider.ContactsContract;
-import android.provider.ContactsContract.CommonDataKinds.Phone;
-import android.provider.ContactsContract.Contacts;
-import android.provider.ContactsContract.DisplayNameSources;
-import android.telecom.TelecomManager;
-import android.text.TextUtils;
-import android.util.Pair;
-
-import com.android.contacts.common.ContactsUtils;
-import com.android.contacts.common.util.PhoneNumberHelper;
-import com.android.dialer.R;
-import com.android.dialer.calllog.ContactInfo;
-import com.android.dialer.service.CachedNumberLookupService;
-import com.android.dialer.service.CachedNumberLookupService.CachedContactInfo;
-import com.android.dialer.util.MoreStrings;
-import com.android.incallui.Call.LogState;
-import com.android.incallui.service.PhoneNumberService;
-import com.android.incalluibind.ObjectFactory;
-
-import org.json.JSONException;
-import org.json.JSONObject;
-
-import java.util.Calendar;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Set;
-
-/**
- * Class responsible for querying Contact Information for Call objects. Can perform asynchronous
- * requests to the Contact Provider for information as well as respond synchronously for any data
- * that it currently has cached from previous queries. This class always gets called from the UI
- * thread so it does not need thread protection.
- */
-public class ContactInfoCache implements ContactsAsyncHelper.OnImageLoadCompleteListener {
-
- private static final String TAG = ContactInfoCache.class.getSimpleName();
- private static final int TOKEN_UPDATE_PHOTO_FOR_CALL_STATE = 0;
-
- private final Context mContext;
- private final PhoneNumberService mPhoneNumberService;
- private final CachedNumberLookupService mCachedNumberLookupService;
- private final HashMap mInfoMap = Maps.newHashMap();
- private final HashMap> mCallBacks = Maps.newHashMap();
-
- private static ContactInfoCache sCache = null;
-
- private Drawable mDefaultContactPhotoDrawable;
- private Drawable mConferencePhotoDrawable;
- private ContactUtils mContactUtils;
-
- public static synchronized ContactInfoCache getInstance(Context mContext) {
- if (sCache == null) {
- sCache = new ContactInfoCache(mContext.getApplicationContext());
- }
- return sCache;
- }
-
- private ContactInfoCache(Context context) {
- mContext = context;
- mPhoneNumberService = ObjectFactory.newPhoneNumberService(context);
- mCachedNumberLookupService =
- com.android.dialerbind.ObjectFactory.newCachedNumberLookupService();
- mContactUtils = ObjectFactory.getContactUtilsInstance(context);
-
- }
-
- public ContactCacheEntry getInfo(String callId) {
- return mInfoMap.get(callId);
- }
-
- public static ContactCacheEntry buildCacheEntryFromCall(Context context, Call call,
- boolean isIncoming) {
- final ContactCacheEntry entry = new ContactCacheEntry();
-
- // TODO: get rid of caller info.
- final CallerInfo info = CallerInfoUtils.buildCallerInfo(context, call);
- ContactInfoCache.populateCacheEntry(context, info, entry, call.getNumberPresentation(),
- isIncoming);
- return entry;
- }
-
- public void maybeInsertCnapInformationIntoCache(Context context, final Call call,
- final CallerInfo info) {
- if (mCachedNumberLookupService == null || TextUtils.isEmpty(info.cnapName)
- || mInfoMap.get(call.getId()) != null) {
- return;
- }
- final Context applicationContext = context.getApplicationContext();
- Log.i(TAG, "Found contact with CNAP name - inserting into cache");
- new AsyncTask() {
- @Override
- protected Void doInBackground(Void... params) {
- ContactInfo contactInfo = new ContactInfo();
- CachedContactInfo cacheInfo = mCachedNumberLookupService.buildCachedContactInfo(
- contactInfo);
- cacheInfo.setSource(CachedContactInfo.SOURCE_TYPE_CNAP, "CNAP", 0);
- contactInfo.name = info.cnapName;
- contactInfo.number = call.getNumber();
- contactInfo.type = ContactsContract.CommonDataKinds.Phone.TYPE_MAIN;
- try {
- final JSONObject contactRows = new JSONObject().put(Phone.CONTENT_ITEM_TYPE,
- new JSONObject()
- .put(Phone.NUMBER, contactInfo.number)
- .put(Phone.TYPE, Phone.TYPE_MAIN));
- final String jsonString = new JSONObject()
- .put(Contacts.DISPLAY_NAME, contactInfo.name)
- .put(Contacts.DISPLAY_NAME_SOURCE, DisplayNameSources.STRUCTURED_NAME)
- .put(Contacts.CONTENT_ITEM_TYPE, contactRows).toString();
- cacheInfo.setLookupKey(jsonString);
- } catch (JSONException e) {
- Log.w(TAG, "Creation of lookup key failed when caching CNAP information");
- }
- mCachedNumberLookupService.addContact(applicationContext, cacheInfo);
- return null;
- }
- }.execute();
- }
-
- private class FindInfoCallback implements CallerInfoAsyncQuery.OnQueryCompleteListener {
- private final boolean mIsIncoming;
-
- public FindInfoCallback(boolean isIncoming) {
- mIsIncoming = isIncoming;
- }
-
- @Override
- public void onQueryComplete(int token, Object cookie, CallerInfo callerInfo) {
- findInfoQueryComplete((Call) cookie, callerInfo, mIsIncoming, true);
- }
- }
-
- /**
- * Requests contact data for the Call object passed in.
- * Returns the data through callback. If callback is null, no response is made, however the
- * query is still performed and cached.
- *
- * @param callback The function to call back when the call is found. Can be null.
- */
- public void findInfo(final Call call, final boolean isIncoming,
- ContactInfoCacheCallback callback) {
- Preconditions.checkState(Looper.getMainLooper().getThread() == Thread.currentThread());
- Preconditions.checkNotNull(callback);
-
- final String callId = call.getId();
- final ContactCacheEntry cacheEntry = mInfoMap.get(callId);
- Set callBacks = mCallBacks.get(callId);
-
- // If we have a previously obtained intermediate result return that now
- if (cacheEntry != null) {
- Log.d(TAG, "Contact lookup. In memory cache hit; lookup "
- + (callBacks == null ? "complete" : "still running"));
- callback.onContactInfoComplete(callId, cacheEntry);
- // If no other callbacks are in flight, we're done.
- if (callBacks == null) {
- return;
- }
- }
-
- // If the entry already exists, add callback
- if (callBacks != null) {
- callBacks.add(callback);
- return;
- }
- Log.d(TAG, "Contact lookup. In memory cache miss; searching provider.");
- // New lookup
- callBacks = Sets.newHashSet();
- callBacks.add(callback);
- mCallBacks.put(callId, callBacks);
-
- /**
- * Performs a query for caller information.
- * Save any immediate data we get from the query. An asynchronous query may also be made
- * for any data that we do not already have. Some queries, such as those for voicemail and
- * emergency call information, will not perform an additional asynchronous query.
- */
- final CallerInfo callerInfo = CallerInfoUtils.getCallerInfoForCall(
- mContext, call, new FindInfoCallback(isIncoming));
-
- findInfoQueryComplete(call, callerInfo, isIncoming, false);
- }
-
- private void findInfoQueryComplete(Call call, CallerInfo callerInfo, boolean isIncoming,
- boolean didLocalLookup) {
- final String callId = call.getId();
- int presentationMode = call.getNumberPresentation();
- if (callerInfo.contactExists || callerInfo.isEmergencyNumber() ||
- callerInfo.isVoiceMailNumber()) {
- presentationMode = TelecomManager.PRESENTATION_ALLOWED;
- }
-
- ContactCacheEntry cacheEntry = mInfoMap.get(callId);
- // Ensure we always have a cacheEntry. Replace the existing entry if
- // it has no name or if we found a local contact.
- if (cacheEntry == null || TextUtils.isEmpty(cacheEntry.namePrimary) ||
- callerInfo.contactExists) {
- cacheEntry = buildEntry(mContext, callId, callerInfo, presentationMode, isIncoming);
- mInfoMap.put(callId, cacheEntry);
- }
-
- sendInfoNotifications(callId, cacheEntry);
-
- if (didLocalLookup) {
- // Before issuing a request for more data from other services, we only check that the
- // contact wasn't found in the local DB. We don't check the if the cache entry already
- // has a name because we allow overriding cnap data with data from other services.
- if (!callerInfo.contactExists && mPhoneNumberService != null) {
- Log.d(TAG, "Contact lookup. Local contacts miss, checking remote");
- final PhoneNumberServiceListener listener = new PhoneNumberServiceListener(callId);
- mPhoneNumberService.getPhoneNumberInfo(cacheEntry.number, listener, listener,
- isIncoming);
- } else if (cacheEntry.displayPhotoUri != null) {
- Log.d(TAG, "Contact lookup. Local contact found, starting image load");
- // Load the image with a callback to update the image state.
- // When the load is finished, onImageLoadComplete() will be called.
- cacheEntry.isLoadingPhoto = true;
- ContactsAsyncHelper.startObtainPhotoAsync(TOKEN_UPDATE_PHOTO_FOR_CALL_STATE,
- mContext, cacheEntry.displayPhotoUri, ContactInfoCache.this, callId);
- } else {
- if (callerInfo.contactExists) {
- Log.d(TAG, "Contact lookup done. Local contact found, no image.");
- } else {
- Log.d(TAG, "Contact lookup done. Local contact not found and"
- + " no remote lookup service available.");
- }
- clearCallbacks(callId);
- }
- }
- }
-
- class PhoneNumberServiceListener implements PhoneNumberService.NumberLookupListener,
- PhoneNumberService.ImageLookupListener, ContactUtils.Listener {
- private final String mCallId;
-
- PhoneNumberServiceListener(String callId) {
- mCallId = callId;
- }
-
- @Override
- public void onPhoneNumberInfoComplete(
- final PhoneNumberService.PhoneNumberInfo info) {
- // If we got a miss, this is the end of the lookup pipeline,
- // so clear the callbacks and return.
- if (info == null) {
- Log.d(TAG, "Contact lookup done. Remote contact not found.");
- clearCallbacks(mCallId);
- return;
- }
-
- ContactCacheEntry entry = new ContactCacheEntry();
- entry.namePrimary = info.getDisplayName();
- entry.number = info.getNumber();
- entry.contactLookupResult = info.getLookupSource();
- final int type = info.getPhoneType();
- final String label = info.getPhoneLabel();
- if (type == Phone.TYPE_CUSTOM) {
- entry.label = label;
- } else {
- final CharSequence typeStr = Phone.getTypeLabel(
- mContext.getResources(), type, label);
- entry.label = typeStr == null ? null : typeStr.toString();
- }
- final ContactCacheEntry oldEntry = mInfoMap.get(mCallId);
- if (oldEntry != null) {
- // Location is only obtained from local lookup so persist
- // the value for remote lookups. Once we have a name this
- // field is no longer used; it is persisted here in case
- // the UI is ever changed to use it.
- entry.location = oldEntry.location;
- // Contact specific ringtone is obtained from local lookup.
- entry.contactRingtoneUri = oldEntry.contactRingtoneUri;
- }
-
- // If no image and it's a business, switch to using the default business avatar.
- if (info.getImageUrl() == null && info.isBusiness()) {
- Log.d(TAG, "Business has no image. Using default.");
- entry.photo = mContext.getResources().getDrawable(R.drawable.img_business);
- }
-
- mInfoMap.put(mCallId, entry);
- sendInfoNotifications(mCallId, entry);
-
- if (mContactUtils != null) {
- // This method will callback "onContactInteractionsFound".
- entry.isLoadingContactInteractions =
- mContactUtils.retrieveContactInteractionsFromLookupKey(
- info.getLookupKey(), this);
- }
-
- entry.isLoadingPhoto = info.getImageUrl() != null;
-
- // If there is no image or contact interactions then we should not expect another
- // callback.
- if (!entry.isLoadingPhoto && !entry.isLoadingContactInteractions) {
- // We're done, so clear callbacks
- clearCallbacks(mCallId);
- }
- }
-
- @Override
- public void onImageFetchComplete(Bitmap bitmap) {
- onImageLoadComplete(TOKEN_UPDATE_PHOTO_FOR_CALL_STATE, null, bitmap, mCallId);
- }
-
- @Override
- public void onContactInteractionsFound(Address address,
- List> openingHours) {
- final ContactCacheEntry entry = mInfoMap.get(mCallId);
- if (entry == null) {
- Log.e(this, "Contact context received for empty search entry.");
- clearCallbacks(mCallId);
- return;
- }
-
- entry.isLoadingContactInteractions = false;
-
- Log.v(ContactInfoCache.this, "Setting contact interactions for entry: ", entry);
-
- entry.locationAddress = address;
- entry.openingHours = openingHours;
- sendContactInteractionsNotifications(mCallId, entry);
-
- if (!entry.isLoadingPhoto) {
- clearCallbacks(mCallId);
- }
- }
- }
-
- /**
- * Implemented for ContactsAsyncHelper.OnImageLoadCompleteListener interface.
- * make sure that the call state is reflected after the image is loaded.
- */
- @Override
- public void onImageLoadComplete(int token, Drawable photo, Bitmap photoIcon, Object cookie) {
- Log.d(this, "Image load complete with context: ", mContext);
- // TODO: may be nice to update the image view again once the newer one
- // is available on contacts database.
-
- final String callId = (String) cookie;
- final ContactCacheEntry entry = mInfoMap.get(callId);
-
- if (entry == null) {
- Log.e(this, "Image Load received for empty search entry.");
- clearCallbacks(callId);
- return;
- }
-
- entry.isLoadingPhoto = false;
-
- Log.d(this, "setting photo for entry: ", entry);
-
- // Conference call icons are being handled in CallCardPresenter.
- if (photo != null) {
- Log.v(this, "direct drawable: ", photo);
- entry.photo = photo;
- } else if (photoIcon != null) {
- Log.v(this, "photo icon: ", photoIcon);
- entry.photo = new BitmapDrawable(mContext.getResources(), photoIcon);
- } else {
- Log.v(this, "unknown photo");
- entry.photo = null;
- }
-
- sendImageNotifications(callId, entry);
-
- if (!entry.isLoadingContactInteractions) {
- clearCallbacks(callId);
- }
- }
-
- /**
- * Blows away the stored cache values.
- */
- public void clearCache() {
- mInfoMap.clear();
- mCallBacks.clear();
- }
-
- private ContactCacheEntry buildEntry(Context context, String callId,
- CallerInfo info, int presentation, boolean isIncoming) {
- // The actual strings we're going to display onscreen:
- Drawable photo = null;
-
- final ContactCacheEntry cce = new ContactCacheEntry();
- populateCacheEntry(context, info, cce, presentation, isIncoming);
-
- // This will only be true for emergency numbers
- if (info.photoResource != 0) {
- photo = context.getResources().getDrawable(info.photoResource);
- } else if (info.isCachedPhotoCurrent) {
- if (info.cachedPhoto != null) {
- photo = info.cachedPhoto;
- } else {
- photo = getDefaultContactPhotoDrawable();
- }
- } else if (info.contactDisplayPhotoUri == null) {
- photo = getDefaultContactPhotoDrawable();
- } else {
- cce.displayPhotoUri = info.contactDisplayPhotoUri;
- }
-
- // Support any contact id in N because QuickContacts in N starts supporting enterprise
- // contact id
- if (info.lookupKeyOrNull != null
- && (ContactsUtils.FLAG_N_FEATURE || info.contactIdOrZero != 0)) {
- cce.lookupUri = Contacts.getLookupUri(info.contactIdOrZero, info.lookupKeyOrNull);
- } else {
- Log.v(TAG, "lookup key is null or contact ID is 0 on M. Don't create a lookup uri.");
- cce.lookupUri = null;
- }
-
- cce.photo = photo;
- cce.lookupKey = info.lookupKeyOrNull;
- cce.contactRingtoneUri = info.contactRingtoneUri;
- if (cce.contactRingtoneUri == null || cce.contactRingtoneUri == Uri.EMPTY) {
- cce.contactRingtoneUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_RINGTONE);
- }
-
- return cce;
- }
-
- /**
- * Populate a cache entry from a call (which got converted into a caller info).
- */
- public static void populateCacheEntry(Context context, CallerInfo info, ContactCacheEntry cce,
- int presentation, boolean isIncoming) {
- Preconditions.checkNotNull(info);
- String displayName = null;
- String displayNumber = null;
- String displayLocation = null;
- String label = null;
- boolean isSipCall = false;
-
- // It appears that there is a small change in behaviour with the
- // PhoneUtils' startGetCallerInfo whereby if we query with an
- // empty number, we will get a valid CallerInfo object, but with
- // fields that are all null, and the isTemporary boolean input
- // parameter as true.
-
- // In the past, we would see a NULL callerinfo object, but this
- // ends up causing null pointer exceptions elsewhere down the
- // line in other cases, so we need to make this fix instead. It
- // appears that this was the ONLY call to PhoneUtils
- // .getCallerInfo() that relied on a NULL CallerInfo to indicate
- // an unknown contact.
-
- // Currently, infi.phoneNumber may actually be a SIP address, and
- // if so, it might sometimes include the "sip:" prefix. That
- // prefix isn't really useful to the user, though, so strip it off
- // if present. (For any other URI scheme, though, leave the
- // prefix alone.)
- // TODO: It would be cleaner for CallerInfo to explicitly support
- // SIP addresses instead of overloading the "phoneNumber" field.
- // Then we could remove this hack, and instead ask the CallerInfo
- // for a "user visible" form of the SIP address.
- String number = info.phoneNumber;
-
- if (!TextUtils.isEmpty(number)) {
- isSipCall = PhoneNumberHelper.isUriNumber(number);
- if (number.startsWith("sip:")) {
- number = number.substring(4);
- }
- }
-
- if (TextUtils.isEmpty(info.name)) {
- // No valid "name" in the CallerInfo, so fall back to
- // something else.
- // (Typically, we promote the phone number up to the "name" slot
- // onscreen, and possibly display a descriptive string in the
- // "number" slot.)
- if (TextUtils.isEmpty(number)) {
- // No name *or* number! Display a generic "unknown" string
- // (or potentially some other default based on the presentation.)
- displayName = getPresentationString(context, presentation, info.callSubject);
- Log.d(TAG, " ==> no name *or* number! displayName = " + displayName);
- } else if (presentation != TelecomManager.PRESENTATION_ALLOWED) {
- // This case should never happen since the network should never send a phone #
- // AND a restricted presentation. However we leave it here in case of weird
- // network behavior
- displayName = getPresentationString(context, presentation, info.callSubject);
- Log.d(TAG, " ==> presentation not allowed! displayName = " + displayName);
- } else if (!TextUtils.isEmpty(info.cnapName)) {
- // No name, but we do have a valid CNAP name, so use that.
- displayName = info.cnapName;
- info.name = info.cnapName;
- displayNumber = number;
- Log.d(TAG, " ==> cnapName available: displayName '" + displayName +
- "', displayNumber '" + displayNumber + "'");
- } else {
- // No name; all we have is a number. This is the typical
- // case when an incoming call doesn't match any contact,
- // or if you manually dial an outgoing number using the
- // dialpad.
- displayNumber = number;
-
- // Display a geographical description string if available
- // (but only for incoming calls.)
- if (isIncoming) {
- // TODO (CallerInfoAsyncQuery cleanup): Fix the CallerInfo
- // query to only do the geoDescription lookup in the first
- // place for incoming calls.
- displayLocation = info.geoDescription; // may be null
- Log.d(TAG, "Geodescrption: " + info.geoDescription);
- }
-
- Log.d(TAG, " ==> no name; falling back to number:"
- + " displayNumber '" + Log.pii(displayNumber)
- + "', displayLocation '" + displayLocation + "'");
- }
- } else {
- // We do have a valid "name" in the CallerInfo. Display that
- // in the "name" slot, and the phone number in the "number" slot.
- if (presentation != TelecomManager.PRESENTATION_ALLOWED) {
- // This case should never happen since the network should never send a name
- // AND a restricted presentation. However we leave it here in case of weird
- // network behavior
- displayName = getPresentationString(context, presentation, info.callSubject);
- Log.d(TAG, " ==> valid name, but presentation not allowed!" +
- " displayName = " + displayName);
- } else {
- // Causes cce.namePrimary to be set as info.name below. CallCardPresenter will
- // later determine whether to use the name or nameAlternative when presenting
- displayName = info.name;
- cce.nameAlternative = info.nameAlternative;
- displayNumber = number;
- label = info.phoneLabel;
- Log.d(TAG, " ==> name is present in CallerInfo: displayName '" + displayName
- + "', displayNumber '" + displayNumber + "'");
- }
- }
-
- cce.namePrimary = displayName;
- cce.number = displayNumber;
- cce.location = displayLocation;
- cce.label = label;
- cce.isSipCall = isSipCall;
- cce.userType = info.userType;
-
- if (info.contactExists) {
- cce.contactLookupResult = LogState.LOOKUP_LOCAL_CONTACT;
- }
- }
-
- /**
- * Sends the updated information to call the callbacks for the entry.
- */
- private void sendInfoNotifications(String callId, ContactCacheEntry entry) {
- final Set callBacks = mCallBacks.get(callId);
- if (callBacks != null) {
- for (ContactInfoCacheCallback callBack : callBacks) {
- callBack.onContactInfoComplete(callId, entry);
- }
- }
- }
-
- private void sendImageNotifications(String callId, ContactCacheEntry entry) {
- final Set callBacks = mCallBacks.get(callId);
- if (callBacks != null && entry.photo != null) {
- for (ContactInfoCacheCallback callBack : callBacks) {
- callBack.onImageLoadComplete(callId, entry);
- }
- }
- }
-
- private void sendContactInteractionsNotifications(String callId, ContactCacheEntry entry) {
- final Set callBacks = mCallBacks.get(callId);
- if (callBacks != null) {
- for (ContactInfoCacheCallback callBack : callBacks) {
- callBack.onContactInteractionsInfoComplete(callId, entry);
- }
- }
- }
-
- private void clearCallbacks(String callId) {
- mCallBacks.remove(callId);
- }
-
- /**
- * Gets name strings based on some special presentation modes and the associated custom label.
- */
- private static String getPresentationString(Context context, int presentation,
- String customLabel) {
- String name = context.getString(R.string.unknown);
- if (!TextUtils.isEmpty(customLabel) &&
- ((presentation == TelecomManager.PRESENTATION_UNKNOWN) ||
- (presentation == TelecomManager.PRESENTATION_RESTRICTED))) {
- name = customLabel;
- return name;
- } else {
- if (presentation == TelecomManager.PRESENTATION_RESTRICTED) {
- name = context.getString(R.string.private_num);
- } else if (presentation == TelecomManager.PRESENTATION_PAYPHONE) {
- name = context.getString(R.string.payphone);
- }
- }
- return name;
- }
-
- public Drawable getDefaultContactPhotoDrawable() {
- if (mDefaultContactPhotoDrawable == null) {
- mDefaultContactPhotoDrawable =
- mContext.getResources().getDrawable(R.drawable.img_no_image_automirrored);
- }
- return mDefaultContactPhotoDrawable;
- }
-
- public Drawable getConferenceDrawable() {
- if (mConferencePhotoDrawable == null) {
- mConferencePhotoDrawable =
- mContext.getResources().getDrawable(R.drawable.img_conference_automirrored);
- }
- return mConferencePhotoDrawable;
- }
-
- /**
- * Callback interface for the contact query.
- */
- public interface ContactInfoCacheCallback {
- public void onContactInfoComplete(String callId, ContactCacheEntry entry);
- public void onImageLoadComplete(String callId, ContactCacheEntry entry);
- public void onContactInteractionsInfoComplete(String callId, ContactCacheEntry entry);
- }
-
- public static class ContactCacheEntry {
- public String namePrimary;
- public String nameAlternative;
- public String number;
- public String location;
- public String label;
- public Drawable photo;
- public boolean isSipCall;
- // Note in cache entry whether this is a pending async loading action to know whether to
- // wait for its callback or not.
- public boolean isLoadingPhoto;
- public boolean isLoadingContactInteractions;
- /** This will be used for the "view" notification. */
- public Uri contactUri;
- /** Either a display photo or a thumbnail URI. */
- public Uri displayPhotoUri;
- public Uri lookupUri; // Sent to NotificationMananger
- public String lookupKey;
- public Address locationAddress;
- public List> openingHours;
- public int contactLookupResult = LogState.LOOKUP_NOT_FOUND;
- public long userType = ContactsUtils.USER_TYPE_CURRENT;
- public Uri contactRingtoneUri;
-
- @Override
- public String toString() {
- return MoreObjects.toStringHelper(this)
- .add("name", MoreStrings.toSafeString(namePrimary))
- .add("nameAlternative", MoreStrings.toSafeString(nameAlternative))
- .add("number", MoreStrings.toSafeString(number))
- .add("location", MoreStrings.toSafeString(location))
- .add("label", label)
- .add("photo", photo)
- .add("isSipCall", isSipCall)
- .add("contactUri", contactUri)
- .add("displayPhotoUri", displayPhotoUri)
- .add("locationAddress", locationAddress)
- .add("openingHours", openingHours)
- .add("contactLookupResult", contactLookupResult)
- .add("userType", userType)
- .add("contactRingtoneUri", contactRingtoneUri)
- .toString();
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ContactUtils.java b/InCallUI/src/com/android/incallui/ContactUtils.java
deleted file mode 100644
index 0750af7317e58e601e968193fc0833eec62d5f14..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ContactUtils.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-package com.android.incallui;
-
-import android.content.Context;
-import android.location.Address;
-import android.util.Pair;
-
-import com.android.incalluibind.ObjectFactory;
-
-import java.util.Calendar;
-import java.util.List;
-
-/**
- * Utility functions to help manipulate contact data.
- */
-public abstract class ContactUtils {
- protected Context mContext;
-
- public static ContactUtils getInstance(Context context) {
- return ObjectFactory.getContactUtilsInstance(context);
- }
-
- protected ContactUtils(Context context) {
- mContext = context;
- }
-
- public interface Listener {
- public void onContactInteractionsFound(Address address,
- List> openingHours);
- }
-
- public abstract boolean retrieveContactInteractionsFromLookupKey(String lookupKey,
- Listener listener);
-}
diff --git a/InCallUI/src/com/android/incallui/ContactsAsyncHelper.java b/InCallUI/src/com/android/incallui/ContactsAsyncHelper.java
deleted file mode 100644
index d959fadd4d48f53c6e21004b9e7550e0e352e074..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ContactsAsyncHelper.java
+++ /dev/null
@@ -1,258 +0,0 @@
-/*
- * Copyright (C) 2008 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.app.Notification;
-import android.content.ContentUris;
-import android.content.Context;
-import android.content.res.AssetFileDescriptor;
-import android.graphics.Bitmap;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.os.Handler;
-import android.os.HandlerThread;
-import android.os.Looper;
-import android.os.Message;
-import android.provider.ContactsContract.Contacts;
-
-import com.android.dialer.R;
-
-import java.io.IOException;
-import java.io.InputStream;
-
-/**
- * Helper class for loading contacts photo asynchronously.
- */
-public class ContactsAsyncHelper {
-
- /**
- * Interface for a WorkerHandler result return.
- */
- public interface OnImageLoadCompleteListener {
- /**
- * Called when the image load is complete.
- *
- * @param token Integer passed in {@link ContactsAsyncHelper#startObtainPhotoAsync(int,
- * Context, Uri, OnImageLoadCompleteListener, Object)}.
- * @param photo Drawable object obtained by the async load.
- * @param photoIcon Bitmap object obtained by the async load.
- * @param cookie Object passed in {@link ContactsAsyncHelper#startObtainPhotoAsync(int,
- * Context, Uri, OnImageLoadCompleteListener, Object)}. Can be null iff. the original
- * cookie is null.
- */
- public void onImageLoadComplete(int token, Drawable photo, Bitmap photoIcon,
- Object cookie);
- }
-
- // constants
- private static final int EVENT_LOAD_IMAGE = 1;
-
- private final Handler mResultHandler = new Handler() {
- /** Called when loading is done. */
- @Override
- public void handleMessage(Message msg) {
- WorkerArgs args = (WorkerArgs) msg.obj;
- switch (msg.arg1) {
- case EVENT_LOAD_IMAGE:
- if (args.listener != null) {
- Log.d(this, "Notifying listener: " + args.listener.toString() +
- " image: " + args.displayPhotoUri + " completed");
- args.listener.onImageLoadComplete(msg.what, args.photo, args.photoIcon,
- args.cookie);
- }
- break;
- default:
- }
- }
- };
-
- /** Handler run on a worker thread to load photo asynchronously. */
- private static Handler sThreadHandler;
-
- /** For forcing the system to call its constructor */
- @SuppressWarnings("unused")
- private static ContactsAsyncHelper sInstance;
-
- static {
- sInstance = new ContactsAsyncHelper();
- }
-
- private static final class WorkerArgs {
- public Context context;
- public Uri displayPhotoUri;
- public Drawable photo;
- public Bitmap photoIcon;
- public Object cookie;
- public OnImageLoadCompleteListener listener;
- }
-
- /**
- * Thread worker class that handles the task of opening the stream and loading
- * the images.
- */
- private class WorkerHandler extends Handler {
- public WorkerHandler(Looper looper) {
- super(looper);
- }
-
- @Override
- public void handleMessage(Message msg) {
- WorkerArgs args = (WorkerArgs) msg.obj;
-
- switch (msg.arg1) {
- case EVENT_LOAD_IMAGE:
- InputStream inputStream = null;
- try {
- try {
- inputStream = args.context.getContentResolver()
- .openInputStream(args.displayPhotoUri);
- } catch (Exception e) {
- Log.e(this, "Error opening photo input stream", e);
- }
-
- if (inputStream != null) {
- args.photo = Drawable.createFromStream(inputStream,
- args.displayPhotoUri.toString());
-
- // This assumes Drawable coming from contact database is usually
- // BitmapDrawable and thus we can have (down)scaled version of it.
- args.photoIcon = getPhotoIconWhenAppropriate(args.context, args.photo);
-
- Log.d(ContactsAsyncHelper.this, "Loading image: " + msg.arg1 +
- " token: " + msg.what + " image URI: " + args.displayPhotoUri);
- } else {
- args.photo = null;
- args.photoIcon = null;
- Log.d(ContactsAsyncHelper.this, "Problem with image: " + msg.arg1 +
- " token: " + msg.what + " image URI: " + args.displayPhotoUri +
- ", using default image.");
- }
- } finally {
- if (inputStream != null) {
- try {
- inputStream.close();
- } catch (IOException e) {
- Log.e(this, "Unable to close input stream.", e);
- }
- }
- }
- break;
- default:
- }
-
- // send the reply to the enclosing class.
- Message reply = ContactsAsyncHelper.this.mResultHandler.obtainMessage(msg.what);
- reply.arg1 = msg.arg1;
- reply.obj = msg.obj;
- reply.sendToTarget();
- }
-
- /**
- * Returns a Bitmap object suitable for {@link Notification}'s large icon. This might
- * return null when the given Drawable isn't BitmapDrawable, or if the system fails to
- * create a scaled Bitmap for the Drawable.
- */
- private Bitmap getPhotoIconWhenAppropriate(Context context, Drawable photo) {
- if (!(photo instanceof BitmapDrawable)) {
- return null;
- }
- int iconSize = context.getResources()
- .getDimensionPixelSize(R.dimen.notification_icon_size);
- Bitmap orgBitmap = ((BitmapDrawable) photo).getBitmap();
- int orgWidth = orgBitmap.getWidth();
- int orgHeight = orgBitmap.getHeight();
- int longerEdge = orgWidth > orgHeight ? orgWidth : orgHeight;
- // We want downscaled one only when the original icon is too big.
- if (longerEdge > iconSize) {
- float ratio = ((float) longerEdge) / iconSize;
- int newWidth = (int) (orgWidth / ratio);
- int newHeight = (int) (orgHeight / ratio);
- // If the longer edge is much longer than the shorter edge, the latter may
- // become 0 which will cause a crash.
- if (newWidth <= 0 || newHeight <= 0) {
- Log.w(this, "Photo icon's width or height become 0.");
- return null;
- }
-
- // It is sure ratio >= 1.0f in any case and thus the newly created Bitmap
- // should be smaller than the original.
- return Bitmap.createScaledBitmap(orgBitmap, newWidth, newHeight, true);
- } else {
- return orgBitmap;
- }
- }
- }
-
- /**
- * Private constructor for static class
- */
- private ContactsAsyncHelper() {
- HandlerThread thread = new HandlerThread("ContactsAsyncWorker");
- thread.start();
- sThreadHandler = new WorkerHandler(thread.getLooper());
- }
-
- /**
- * Starts an asynchronous image load. After finishing the load,
- * {@link OnImageLoadCompleteListener#onImageLoadComplete(int, Drawable, Bitmap, Object)}
- * will be called.
- *
- * @param token Arbitrary integer which will be returned as the first argument of
- * {@link OnImageLoadCompleteListener#onImageLoadComplete(int, Drawable, Bitmap, Object)}
- * @param context Context object used to do the time-consuming operation.
- * @param displayPhotoUri Uri to be used to fetch the photo
- * @param listener Callback object which will be used when the asynchronous load is done.
- * Can be null, which means only the asynchronous load is done while there's no way to
- * obtain the loaded photos.
- * @param cookie Arbitrary object the caller wants to remember, which will become the
- * fourth argument of {@link OnImageLoadCompleteListener#onImageLoadComplete(int, Drawable,
- * Bitmap, Object)}. Can be null, at which the callback will also has null for the argument.
- */
- public static final void startObtainPhotoAsync(int token, Context context, Uri displayPhotoUri,
- OnImageLoadCompleteListener listener, Object cookie) {
- // in case the source caller info is null, the URI will be null as well.
- // just update using the placeholder image in this case.
- if (displayPhotoUri == null) {
- Log.wtf("startObjectPhotoAsync", "Uri is missing");
- return;
- }
-
- // Added additional Cookie field in the callee to handle arguments
- // sent to the callback function.
-
- // setup arguments
- WorkerArgs args = new WorkerArgs();
- args.cookie = cookie;
- args.context = context;
- args.displayPhotoUri = displayPhotoUri;
- args.listener = listener;
-
- // setup message arguments
- Message msg = sThreadHandler.obtainMessage(token);
- msg.arg1 = EVENT_LOAD_IMAGE;
- msg.obj = args;
-
- Log.d("startObjectPhotoAsync", "Begin loading image: " + args.displayPhotoUri +
- ", displaying default image for now.");
-
- // notify the thread to begin working
- sThreadHandler.sendMessage(msg);
- }
-
-
-}
diff --git a/InCallUI/src/com/android/incallui/ContactsPreferencesFactory.java b/InCallUI/src/com/android/incallui/ContactsPreferencesFactory.java
deleted file mode 100644
index a9cc93bda2ea446a17a67987b5fe58f6e6d44f73..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ContactsPreferencesFactory.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.support.annotation.Nullable;
-import com.android.dialer.compat.UserManagerCompat;
-
-import com.android.contacts.common.preference.ContactsPreferences;
-import com.android.contacts.common.testing.NeededForTesting;
-
-/**
- * Factory class for {@link ContactsPreferences}.
- */
-public class ContactsPreferencesFactory {
-
- private static boolean sUseTestInstance;
- private static ContactsPreferences sTestInstance;
-
- /**
- * Creates a new {@link ContactsPreferences} object if possible.
- *
- * @param context the context to use when creating the ContactsPreferences.
- * @return a new ContactsPreferences object or {@code null} if the user is locked.
- */
- @Nullable
- public static ContactsPreferences newContactsPreferences(Context context) {
- if (sUseTestInstance) {
- return sTestInstance;
- }
- if (UserManagerCompat.isUserUnlocked(context)) {
- return new ContactsPreferences(context);
- }
- return null;
- }
-
- /**
- * Sets the instance to be returned by all calls to {@link #newContactsPreferences(Context)}.
- *
- * @param testInstance the instance to return.
- */
- @NeededForTesting
- static void setTestInstance(ContactsPreferences testInstance) {
- sUseTestInstance = true;
- sTestInstance = testInstance;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/DialpadFragment.java b/InCallUI/src/com/android/incallui/DialpadFragment.java
deleted file mode 100644
index ad288bdc6c2449c3c443c9b604569f65da15da2d..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/DialpadFragment.java
+++ /dev/null
@@ -1,563 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Looper;
-import android.text.Editable;
-import android.text.method.DialerKeyListener;
-import android.util.AttributeSet;
-import android.view.KeyEvent;
-import android.view.LayoutInflater;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.accessibility.AccessibilityManager;
-import android.widget.EditText;
-import android.widget.LinearLayout;
-import android.widget.TextView;
-
-import com.android.contacts.common.compat.PhoneNumberUtilsCompat;
-import com.android.dialer.R;
-import com.android.phone.common.dialpad.DialpadKeyButton;
-import com.android.phone.common.dialpad.DialpadView;
-
-import java.util.HashMap;
-
-/**
- * Fragment for call control buttons
- */
-public class DialpadFragment extends BaseFragment
- implements DialpadPresenter.DialpadUi, View.OnTouchListener, View.OnKeyListener,
- View.OnHoverListener, View.OnClickListener {
-
- private static final int ACCESSIBILITY_DTMF_STOP_DELAY_MILLIS = 50;
-
- private final int[] mButtonIds = new int[] {R.id.zero, R.id.one, R.id.two, R.id.three,
- R.id.four, R.id.five, R.id.six, R.id.seven, R.id.eight, R.id.nine, R.id.star,
- R.id.pound};
-
- /**
- * LinearLayout with getter and setter methods for the translationY property using floats,
- * for animation purposes.
- */
- public static class DialpadSlidingLinearLayout extends LinearLayout {
-
- public DialpadSlidingLinearLayout(Context context) {
- super(context);
- }
-
- public DialpadSlidingLinearLayout(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public DialpadSlidingLinearLayout(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- }
-
- public float getYFraction() {
- final int height = getHeight();
- if (height == 0) return 0;
- return getTranslationY() / height;
- }
-
- public void setYFraction(float yFraction) {
- setTranslationY(yFraction * getHeight());
- }
- }
-
- private EditText mDtmfDialerField;
-
- /** Hash Map to map a view id to a character*/
- private static final HashMap mDisplayMap =
- new HashMap();
-
- private static final Handler sHandler = new Handler(Looper.getMainLooper());
-
-
- /** Set up the static maps*/
- static {
- // Map the buttons to the display characters
- mDisplayMap.put(R.id.one, '1');
- mDisplayMap.put(R.id.two, '2');
- mDisplayMap.put(R.id.three, '3');
- mDisplayMap.put(R.id.four, '4');
- mDisplayMap.put(R.id.five, '5');
- mDisplayMap.put(R.id.six, '6');
- mDisplayMap.put(R.id.seven, '7');
- mDisplayMap.put(R.id.eight, '8');
- mDisplayMap.put(R.id.nine, '9');
- mDisplayMap.put(R.id.zero, '0');
- mDisplayMap.put(R.id.pound, '#');
- mDisplayMap.put(R.id.star, '*');
- }
-
- // KeyListener used with the "dialpad digits" EditText widget.
- private DTMFKeyListener mDialerKeyListener;
-
- private DialpadView mDialpadView;
-
- private int mCurrentTextColor;
-
- /**
- * Our own key listener, specialized for dealing with DTMF codes.
- * 1. Ignore the backspace since it is irrelevant.
- * 2. Allow ONLY valid DTMF characters to generate a tone and be
- * sent as a DTMF code.
- * 3. All other remaining characters are handled by the superclass.
- *
- * This code is purely here to handle events from the hardware keyboard
- * while the DTMF dialpad is up.
- */
- private class DTMFKeyListener extends DialerKeyListener {
-
- private DTMFKeyListener() {
- super();
- }
-
- /**
- * Overriden to return correct DTMF-dialable characters.
- */
- @Override
- protected char[] getAcceptedChars(){
- return DTMF_CHARACTERS;
- }
-
- /** special key listener ignores backspace. */
- @Override
- public boolean backspace(View view, Editable content, int keyCode,
- KeyEvent event) {
- return false;
- }
-
- /**
- * Return true if the keyCode is an accepted modifier key for the
- * dialer (ALT or SHIFT).
- */
- private boolean isAcceptableModifierKey(int keyCode) {
- switch (keyCode) {
- case KeyEvent.KEYCODE_ALT_LEFT:
- case KeyEvent.KEYCODE_ALT_RIGHT:
- case KeyEvent.KEYCODE_SHIFT_LEFT:
- case KeyEvent.KEYCODE_SHIFT_RIGHT:
- return true;
- default:
- return false;
- }
- }
-
- /**
- * Overriden so that with each valid button press, we start sending
- * a dtmf code and play a local dtmf tone.
- */
- @Override
- public boolean onKeyDown(View view, Editable content,
- int keyCode, KeyEvent event) {
- // if (DBG) log("DTMFKeyListener.onKeyDown, keyCode " + keyCode + ", view " + view);
-
- // find the character
- char c = (char) lookup(event, content);
-
- // if not a long press, and parent onKeyDown accepts the input
- if (event.getRepeatCount() == 0 && super.onKeyDown(view, content, keyCode, event)) {
-
- boolean keyOK = ok(getAcceptedChars(), c);
-
- // if the character is a valid dtmf code, start playing the tone and send the
- // code.
- if (keyOK) {
- Log.d(this, "DTMFKeyListener reading '" + c + "' from input.");
- getPresenter().processDtmf(c);
- } else {
- Log.d(this, "DTMFKeyListener rejecting '" + c + "' from input.");
- }
- return true;
- }
- return false;
- }
-
- /**
- * Overriden so that with each valid button up, we stop sending
- * a dtmf code and the dtmf tone.
- */
- @Override
- public boolean onKeyUp(View view, Editable content,
- int keyCode, KeyEvent event) {
- // if (DBG) log("DTMFKeyListener.onKeyUp, keyCode " + keyCode + ", view " + view);
-
- super.onKeyUp(view, content, keyCode, event);
-
- // find the character
- char c = (char) lookup(event, content);
-
- boolean keyOK = ok(getAcceptedChars(), c);
-
- if (keyOK) {
- Log.d(this, "Stopping the tone for '" + c + "'");
- getPresenter().stopDtmf();
- return true;
- }
-
- return false;
- }
-
- /**
- * Handle individual keydown events when we DO NOT have an Editable handy.
- */
- public boolean onKeyDown(KeyEvent event) {
- char c = lookup(event);
- Log.d(this, "DTMFKeyListener.onKeyDown: event '" + c + "'");
-
- // if not a long press, and parent onKeyDown accepts the input
- if (event.getRepeatCount() == 0 && c != 0) {
- // if the character is a valid dtmf code, start playing the tone and send the
- // code.
- if (ok(getAcceptedChars(), c)) {
- Log.d(this, "DTMFKeyListener reading '" + c + "' from input.");
- getPresenter().processDtmf(c);
- return true;
- } else {
- Log.d(this, "DTMFKeyListener rejecting '" + c + "' from input.");
- }
- }
- return false;
- }
-
- /**
- * Handle individual keyup events.
- *
- * @param event is the event we are trying to stop. If this is null,
- * then we just force-stop the last tone without checking if the event
- * is an acceptable dialer event.
- */
- public boolean onKeyUp(KeyEvent event) {
- if (event == null) {
- //the below piece of code sends stopDTMF event unnecessarily even when a null event
- //is received, hence commenting it.
- /*if (DBG) log("Stopping the last played tone.");
- stopTone();*/
- return true;
- }
-
- char c = lookup(event);
- Log.d(this, "DTMFKeyListener.onKeyUp: event '" + c + "'");
-
- // TODO: stopTone does not take in character input, we may want to
- // consider checking for this ourselves.
- if (ok(getAcceptedChars(), c)) {
- Log.d(this, "Stopping the tone for '" + c + "'");
- getPresenter().stopDtmf();
- return true;
- }
-
- return false;
- }
-
- /**
- * Find the Dialer Key mapped to this event.
- *
- * @return The char value of the input event, otherwise
- * 0 if no matching character was found.
- */
- private char lookup(KeyEvent event) {
- // This code is similar to {@link DialerKeyListener#lookup(KeyEvent, Spannable) lookup}
- int meta = event.getMetaState();
- int number = event.getNumber();
-
- if (!((meta & (KeyEvent.META_ALT_ON | KeyEvent.META_SHIFT_ON)) == 0) || (number == 0)) {
- int match = event.getMatch(getAcceptedChars(), meta);
- number = (match != 0) ? match : number;
- }
-
- return (char) number;
- }
-
- /**
- * Check to see if the keyEvent is dialable.
- */
- boolean isKeyEventAcceptable (KeyEvent event) {
- return (ok(getAcceptedChars(), lookup(event)));
- }
-
- /**
- * Overrides the characters used in {@link DialerKeyListener#CHARACTERS}
- * These are the valid dtmf characters.
- */
- public final char[] DTMF_CHARACTERS = new char[] {
- '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '#', '*'
- };
- }
-
- @Override
- public void onClick(View v) {
- final AccessibilityManager accessibilityManager = (AccessibilityManager)
- v.getContext().getSystemService(Context.ACCESSIBILITY_SERVICE);
- // When accessibility is on, simulate press and release to preserve the
- // semantic meaning of performClick(). Required for Braille support.
- if (accessibilityManager.isEnabled()) {
- final int id = v.getId();
- // Checking the press state prevents double activation.
- if (!v.isPressed() && mDisplayMap.containsKey(id)) {
- getPresenter().processDtmf(mDisplayMap.get(id));
- sHandler.postDelayed(new Runnable() {
- @Override
- public void run() {
- getPresenter().stopDtmf();
- }
- }, ACCESSIBILITY_DTMF_STOP_DELAY_MILLIS);
- }
- }
- if (v.getId() == R.id.dialpad_back) {
- getActivity().onBackPressed();
- }
- }
-
- @Override
- public boolean onHover(View v, MotionEvent event) {
- // When touch exploration is turned on, lifting a finger while inside
- // the button's hover target bounds should perform a click action.
- final AccessibilityManager accessibilityManager = (AccessibilityManager)
- v.getContext().getSystemService(Context.ACCESSIBILITY_SERVICE);
-
- if (accessibilityManager.isEnabled()
- && accessibilityManager.isTouchExplorationEnabled()) {
- final int left = v.getPaddingLeft();
- final int right = (v.getWidth() - v.getPaddingRight());
- final int top = v.getPaddingTop();
- final int bottom = (v.getHeight() - v.getPaddingBottom());
-
- switch (event.getActionMasked()) {
- case MotionEvent.ACTION_HOVER_ENTER:
- // Lift-to-type temporarily disables double-tap activation.
- v.setClickable(false);
- break;
- case MotionEvent.ACTION_HOVER_EXIT:
- final int x = (int) event.getX();
- final int y = (int) event.getY();
- if ((x > left) && (x < right) && (y > top) && (y < bottom)) {
- v.performClick();
- }
- v.setClickable(true);
- break;
- }
- }
-
- return false;
- }
-
- @Override
- public boolean onKey(View v, int keyCode, KeyEvent event) {
- Log.d(this, "onKey: keyCode " + keyCode + ", view " + v);
-
- if (keyCode == KeyEvent.KEYCODE_DPAD_CENTER || keyCode == KeyEvent.KEYCODE_ENTER) {
- int viewId = v.getId();
- if (mDisplayMap.containsKey(viewId)) {
- switch (event.getAction()) {
- case KeyEvent.ACTION_DOWN:
- if (event.getRepeatCount() == 0) {
- getPresenter().processDtmf(mDisplayMap.get(viewId));
- }
- break;
- case KeyEvent.ACTION_UP:
- getPresenter().stopDtmf();
- break;
- }
- // do not return true [handled] here, since we want the
- // press / click animation to be handled by the framework.
- }
- }
- return false;
- }
-
- @Override
- public boolean onTouch(View v, MotionEvent event) {
- Log.d(this, "onTouch");
- int viewId = v.getId();
-
- // if the button is recognized
- if (mDisplayMap.containsKey(viewId)) {
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN:
- // Append the character mapped to this button, to the display.
- // start the tone
- getPresenter().processDtmf(mDisplayMap.get(viewId));
- break;
- case MotionEvent.ACTION_UP:
- case MotionEvent.ACTION_CANCEL:
- // stop the tone on ANY other event, except for MOVE.
- getPresenter().stopDtmf();
- break;
- }
- // do not return true [handled] here, since we want the
- // press / click animation to be handled by the framework.
- }
- return false;
- }
-
- // TODO(klp) Adds hardware keyboard listener
-
- @Override
- public DialpadPresenter createPresenter() {
- return new DialpadPresenter();
- }
-
- @Override
- public DialpadPresenter.DialpadUi getUi() {
- return this;
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- final View parent = inflater.inflate(
- R.layout.incall_dialpad_fragment, container, false);
- mDialpadView = (DialpadView) parent.findViewById(R.id.dialpad_view);
- mDialpadView.setCanDigitsBeEdited(false);
- mDialpadView.setBackgroundResource(R.color.incall_dialpad_background);
- mDtmfDialerField = (EditText) parent.findViewById(R.id.digits);
- if (mDtmfDialerField != null) {
- mDialerKeyListener = new DTMFKeyListener();
- mDtmfDialerField.setKeyListener(mDialerKeyListener);
- // remove the long-press context menus that support
- // the edit (copy / paste / select) functions.
- mDtmfDialerField.setLongClickable(false);
- mDtmfDialerField.setElegantTextHeight(false);
- configureKeypadListeners();
- }
- View backButton = mDialpadView.findViewById(R.id.dialpad_back);
- backButton.setVisibility(View.VISIBLE);
- backButton.setOnClickListener(this);
-
- return parent;
- }
-
- @Override
- public void onResume() {
- super.onResume();
- updateColors();
- }
-
- public void updateColors() {
- int textColor = InCallPresenter.getInstance().getThemeColors().mPrimaryColor;
-
- if (mCurrentTextColor == textColor) {
- return;
- }
-
- DialpadKeyButton dialpadKey;
- for (int i = 0; i < mButtonIds.length; i++) {
- dialpadKey = (DialpadKeyButton) mDialpadView.findViewById(mButtonIds[i]);
- ((TextView) dialpadKey.findViewById(R.id.dialpad_key_number)).setTextColor(textColor);
- }
-
- mCurrentTextColor = textColor;
- }
-
- @Override
- public void onDestroyView() {
- mDialerKeyListener = null;
- super.onDestroyView();
- }
-
- /**
- * Getter for Dialpad text.
- *
- * @return String containing current Dialpad EditText text.
- */
- public String getDtmfText() {
- return mDtmfDialerField.getText().toString();
- }
-
- /**
- * Sets the Dialpad text field with some text.
- *
- * @param text Text to set Dialpad EditText to.
- */
- public void setDtmfText(String text) {
- mDtmfDialerField.setText(PhoneNumberUtilsCompat.createTtsSpannable(text));
- }
-
- @Override
- public void setVisible(boolean on) {
- if (on) {
- getView().setVisibility(View.VISIBLE);
- } else {
- getView().setVisibility(View.INVISIBLE);
- }
- }
-
- /**
- * Starts the slide up animation for the Dialpad keys when the Dialpad is revealed.
- */
- public void animateShowDialpad() {
- final DialpadView dialpadView = (DialpadView) getView().findViewById(R.id.dialpad_view);
- dialpadView.animateShow();
- }
-
- @Override
- public void appendDigitsToField(char digit) {
- if (mDtmfDialerField != null) {
- // TODO: maybe *don't* manually append this digit if
- // mDialpadDigits is focused and this key came from the HW
- // keyboard, since in that case the EditText field will
- // get the key event directly and automatically appends
- // whetever the user types.
- // (Or, a cleaner fix would be to just make mDialpadDigits
- // *not* handle HW key presses. That seems to be more
- // complicated than just setting focusable="false" on it,
- // though.)
- mDtmfDialerField.getText().append(digit);
- }
- }
-
- /**
- * Called externally (from InCallScreen) to play a DTMF Tone.
- */
- /* package */ boolean onDialerKeyDown(KeyEvent event) {
- Log.d(this, "Notifying dtmf key down.");
- if (mDialerKeyListener != null) {
- return mDialerKeyListener.onKeyDown(event);
- } else {
- return false;
- }
- }
-
- /**
- * Called externally (from InCallScreen) to cancel the last DTMF Tone played.
- */
- public boolean onDialerKeyUp(KeyEvent event) {
- Log.d(this, "Notifying dtmf key up.");
- if (mDialerKeyListener != null) {
- return mDialerKeyListener.onKeyUp(event);
- } else {
- return false;
- }
- }
-
- private void configureKeypadListeners() {
- DialpadKeyButton dialpadKey;
- for (int i = 0; i < mButtonIds.length; i++) {
- dialpadKey = (DialpadKeyButton) mDialpadView.findViewById(mButtonIds[i]);
- dialpadKey.setOnTouchListener(this);
- dialpadKey.setOnKeyListener(this);
- dialpadKey.setOnHoverListener(this);
- dialpadKey.setOnClickListener(this);
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/DialpadPresenter.java b/InCallUI/src/com/android/incallui/DialpadPresenter.java
deleted file mode 100644
index 5e24bedefc0f789dd8a802c58f30abf1f3a5c0ce..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/DialpadPresenter.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.telephony.PhoneNumberUtils;
-
-/**
- * Logic for call buttons.
- */
-public class DialpadPresenter extends Presenter
- implements InCallPresenter.InCallStateListener {
-
- private Call mCall;
-
- @Override
- public void onUiReady(DialpadUi ui) {
- super.onUiReady(ui);
- InCallPresenter.getInstance().addListener(this);
- mCall = CallList.getInstance().getOutgoingOrActive();
- }
-
- @Override
- public void onUiUnready(DialpadUi ui) {
- super.onUiUnready(ui);
- InCallPresenter.getInstance().removeListener(this);
- }
-
- @Override
- public void onStateChange(InCallPresenter.InCallState oldState,
- InCallPresenter.InCallState newState, CallList callList) {
- mCall = callList.getOutgoingOrActive();
- Log.d(this, "DialpadPresenter mCall = " + mCall);
- }
-
- /**
- * Processes the specified digit as a DTMF key, by playing the
- * appropriate DTMF tone, and appending the digit to the EditText
- * field that displays the DTMF digits sent so far.
- *
- */
- public final void processDtmf(char c) {
- Log.d(this, "Processing dtmf key " + c);
- // if it is a valid key, then update the display and send the dtmf tone.
- if (PhoneNumberUtils.is12Key(c) && mCall != null) {
- Log.d(this, "updating display and sending dtmf tone for '" + c + "'");
-
- // Append this key to the "digits" widget.
- getUi().appendDigitsToField(c);
- // Plays the tone through Telecom.
- TelecomAdapter.getInstance().playDtmfTone(mCall.getId(), c);
- } else {
- Log.d(this, "ignoring dtmf request for '" + c + "'");
- }
- }
-
- /**
- * Stops the local tone based on the phone type.
- */
- public void stopDtmf() {
- if (mCall != null) {
- Log.d(this, "stopping remote tone");
- TelecomAdapter.getInstance().stopDtmfTone(mCall.getId());
- }
- }
-
- public interface DialpadUi extends Ui {
- void setVisible(boolean on);
- void appendDigitsToField(char digit);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/DistanceHelper.java b/InCallUI/src/com/android/incallui/DistanceHelper.java
deleted file mode 100644
index a4db5fed3b04010d73551a4db221b917880e07ff..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/DistanceHelper.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.incallui;
-
-import android.location.Address;
-
-/**
- * Superclass for a helper class to get the current location and distance to other locations.
- */
-public abstract class DistanceHelper {
- public static final float DISTANCE_NOT_FOUND = -1;
- public static final float MILES_PER_METER = (float) 0.000621371192;
- public static final float KILOMETERS_PER_METER = (float) 0.001;
-
- public interface Listener {
- public void onLocationReady();
- }
-
- public void cleanUp() {}
-
- public float calculateDistance(Address address) {
- return DISTANCE_NOT_FOUND;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ExternalCallList.java b/InCallUI/src/com/android/incallui/ExternalCallList.java
deleted file mode 100644
index 06e0bb975a2cc9cc6680d4e51ea040e968a07e0b..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ExternalCallList.java
+++ /dev/null
@@ -1,105 +0,0 @@
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import com.android.contacts.common.compat.CallSdkCompat;
-
-import android.os.Handler;
-import android.os.Looper;
-import android.telecom.Call;
-import android.util.ArraySet;
-
-import java.util.Collections;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * Tracks the external calls known to the InCall UI.
- *
- * External calls are those with {@link android.telecom.Call.Details#PROPERTY_IS_EXTERNAL_CALL}.
- */
-public class ExternalCallList {
-
- public interface ExternalCallListener {
- void onExternalCallAdded(Call call);
- void onExternalCallRemoved(Call call);
- void onExternalCallUpdated(Call call);
- }
-
- /**
- * Handles {@link android.telecom.Call.Callback} callbacks.
- */
- private final Call.Callback mTelecomCallCallback = new Call.Callback() {
- @Override
- public void onDetailsChanged(Call call, Call.Details details) {
- notifyExternalCallUpdated(call);
- }
- };
-
- private final Set mExternalCalls = new ArraySet<>();
- private final Set mExternalCallListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
-
- /**
- * Begins tracking an external call and notifies listeners of the new call.
- */
- public void onCallAdded(Call telecomCall) {
- Preconditions.checkArgument(telecomCall.getDetails()
- .hasProperty(CallSdkCompat.Details.PROPERTY_IS_EXTERNAL_CALL));
- mExternalCalls.add(telecomCall);
- telecomCall.registerCallback(mTelecomCallCallback, new Handler(Looper.getMainLooper()));
- notifyExternalCallAdded(telecomCall);
- }
-
- /**
- * Stops tracking an external call and notifies listeners of the removal of the call.
- */
- public void onCallRemoved(Call telecomCall) {
- Preconditions.checkArgument(mExternalCalls.contains(telecomCall));
- mExternalCalls.remove(telecomCall);
- telecomCall.unregisterCallback(mTelecomCallCallback);
- notifyExternalCallRemoved(telecomCall);
- }
-
- /**
- * Adds a new listener to external call events.
- */
- public void addExternalCallListener(ExternalCallListener listener) {
- mExternalCallListeners.add(Preconditions.checkNotNull(listener));
- }
-
- /**
- * Removes a listener to external call events.
- */
- public void removeExternalCallListener(ExternalCallListener listener) {
- Preconditions.checkArgument(mExternalCallListeners.contains(listener));
- mExternalCallListeners.remove(Preconditions.checkNotNull(listener));
- }
-
- /**
- * Notifies listeners of the addition of a new external call.
- */
- private void notifyExternalCallAdded(Call call) {
- for (ExternalCallListener listener : mExternalCallListeners) {
- listener.onExternalCallAdded(call);
- }
- }
-
- /**
- * Notifies listeners of the removal of an external call.
- */
- private void notifyExternalCallRemoved(Call call) {
- for (ExternalCallListener listener : mExternalCallListeners) {
- listener.onExternalCallRemoved(call);
- }
- }
-
- /**
- * Notifies listeners of changes to an external call.
- */
- private void notifyExternalCallUpdated(Call call) {
- for (ExternalCallListener listener : mExternalCallListeners) {
- listener.onExternalCallUpdated(call);
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ExternalCallNotifier.java b/InCallUI/src/com/android/incallui/ExternalCallNotifier.java
deleted file mode 100644
index 639a46da0194a95636fb77d93f8f987b326a5258..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ExternalCallNotifier.java
+++ /dev/null
@@ -1,406 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import com.android.contacts.common.ContactsUtils;
-import com.android.contacts.common.compat.CallSdkCompat;
-import com.android.contacts.common.preference.ContactsPreferences;
-import com.android.contacts.common.util.BitmapUtil;
-import com.android.contacts.common.util.ContactDisplayUtils;
-import com.android.dialer.R;
-import com.android.incallui.util.TelecomCallUtil;
-
-import android.app.Notification;
-import android.app.NotificationManager;
-import android.app.PendingIntent;
-import android.content.Context;
-import android.content.Intent;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.drawable.BitmapDrawable;
-import android.net.Uri;
-import android.support.annotation.Nullable;
-import android.telecom.Call;
-import android.telecom.PhoneAccount;
-import android.text.BidiFormatter;
-import android.text.TextDirectionHeuristics;
-import android.text.TextUtils;
-import android.util.ArrayMap;
-
-import java.util.Map;
-
-/**
- * Handles the display of notifications for "external calls".
- *
- * External calls are a representation of a call which is in progress on the user's other device
- * (e.g. another phone, or a watch).
- */
-public class ExternalCallNotifier implements ExternalCallList.ExternalCallListener {
-
- /**
- * Tag used with the notification manager to uniquely identify external call notifications.
- */
- private static final String NOTIFICATION_TAG = "EXTERNAL_CALL";
-
- /**
- * Represents a call and associated cached notification data.
- */
- private static class NotificationInfo {
- private final Call mCall;
- private final int mNotificationId;
- @Nullable private String mContentTitle;
- @Nullable private Bitmap mLargeIcon;
- @Nullable private String mPersonReference;
-
- public NotificationInfo(Call call, int notificationId) {
- Preconditions.checkNotNull(call);
- mCall = call;
- mNotificationId = notificationId;
- }
-
- public Call getCall() {
- return mCall;
- }
-
- public int getNotificationId() {
- return mNotificationId;
- }
-
- public @Nullable String getContentTitle() {
- return mContentTitle;
- }
-
- public @Nullable Bitmap getLargeIcon() {
- return mLargeIcon;
- }
-
- public @Nullable String getPersonReference() {
- return mPersonReference;
- }
-
- public void setContentTitle(@Nullable String contentTitle) {
- mContentTitle = contentTitle;
- }
-
- public void setLargeIcon(@Nullable Bitmap largeIcon) {
- mLargeIcon = largeIcon;
- }
-
- public void setPersonReference(@Nullable String personReference) {
- mPersonReference = personReference;
- }
- }
-
- private final Context mContext;
- private final ContactInfoCache mContactInfoCache;
- private Map mNotifications = new ArrayMap<>();
- private int mNextUniqueNotificationId;
- private ContactsPreferences mContactsPreferences;
-
- /**
- * Initializes a new instance of the external call notifier.
- */
- public ExternalCallNotifier(Context context, ContactInfoCache contactInfoCache) {
- mContext = Preconditions.checkNotNull(context);
- mContactsPreferences = ContactsPreferencesFactory.newContactsPreferences(mContext);
- mContactInfoCache = Preconditions.checkNotNull(contactInfoCache);
- }
-
- /**
- * Handles the addition of a new external call by showing a new notification.
- * Triggered by {@link CallList#onCallAdded(android.telecom.Call)}.
- */
- @Override
- public void onExternalCallAdded(android.telecom.Call call) {
- Log.i(this, "onExternalCallAdded " + call);
- Preconditions.checkArgument(!mNotifications.containsKey(call));
- NotificationInfo info = new NotificationInfo(call, mNextUniqueNotificationId++);
- mNotifications.put(call, info);
-
- showNotifcation(info);
- }
-
- /**
- * Handles the removal of an external call by hiding its associated notification.
- * Triggered by {@link CallList#onCallRemoved(android.telecom.Call)}.
- */
- @Override
- public void onExternalCallRemoved(android.telecom.Call call) {
- Log.i(this, "onExternalCallRemoved " + call);
-
- dismissNotification(call);
- }
-
- /**
- * Handles updates to an external call.
- */
- @Override
- public void onExternalCallUpdated(Call call) {
- Preconditions.checkArgument(mNotifications.containsKey(call));
- postNotification(mNotifications.get(call));
- }
-
- /**
- * Initiates a call pull given a notification ID.
- *
- * @param notificationId The notification ID associated with the external call which is to be
- * pulled.
- */
- public void pullExternalCall(int notificationId) {
- for (NotificationInfo info : mNotifications.values()) {
- if (info.getNotificationId() == notificationId) {
- CallSdkCompat.pullExternalCall(info.getCall());
- return;
- }
- }
- }
-
- /**
- * Shows a notification for a new external call. Performs a contact cache lookup to find any
- * associated photo and information for the call.
- */
- private void showNotifcation(final NotificationInfo info) {
- // We make a call to the contact info cache to query for supplemental data to what the
- // call provides. This includes the contact name and photo.
- // This callback will always get called immediately and synchronously with whatever data
- // it has available, and may make a subsequent call later (same thread) if it had to
- // call into the contacts provider for more data.
- com.android.incallui.Call incallCall = new com.android.incallui.Call(info.getCall(),
- new LatencyReport(), false /* registerCallback */);
-
- mContactInfoCache.findInfo(incallCall, false /* isIncoming */,
- new ContactInfoCache.ContactInfoCacheCallback() {
- @Override
- public void onContactInfoComplete(String callId,
- ContactInfoCache.ContactCacheEntry entry) {
-
- // Ensure notification still exists as the external call could have been
- // removed during async contact info lookup.
- if (mNotifications.containsKey(info.getCall())) {
- saveContactInfo(info, entry);
- }
- }
-
- @Override
- public void onImageLoadComplete(String callId,
- ContactInfoCache.ContactCacheEntry entry) {
-
- // Ensure notification still exists as the external call could have been
- // removed during async contact info lookup.
- if (mNotifications.containsKey(info.getCall())) {
- savePhoto(info, entry);
- }
- }
-
- @Override
- public void onContactInteractionsInfoComplete(String callId,
- ContactInfoCache.ContactCacheEntry entry) {
- }
- });
- }
-
- /**
- * Dismisses a notification for an external call.
- */
- private void dismissNotification(Call call) {
- Preconditions.checkArgument(mNotifications.containsKey(call));
-
- NotificationManager notificationManager =
- (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
- notificationManager.cancel(NOTIFICATION_TAG, mNotifications.get(call).getNotificationId());
-
- mNotifications.remove(call);
- }
-
- /**
- * Attempts to build a large icon to use for the notification based on the contact info and
- * post the updated notification to the notification manager.
- */
- private void savePhoto(NotificationInfo info, ContactInfoCache.ContactCacheEntry entry) {
- Bitmap largeIcon = getLargeIconToDisplay(mContext, entry, info.getCall());
- if (largeIcon != null) {
- largeIcon = getRoundedIcon(mContext, largeIcon);
- }
- info.setLargeIcon(largeIcon);
- postNotification(info);
- }
-
- /**
- * Builds and stores the contact information the notification will display and posts the updated
- * notification to the notification manager.
- */
- private void saveContactInfo(NotificationInfo info, ContactInfoCache.ContactCacheEntry entry) {
- info.setContentTitle(getContentTitle(mContext, mContactsPreferences,
- entry, info.getCall()));
- info.setPersonReference(getPersonReference(entry, info.getCall()));
- postNotification(info);
- }
-
- /**
- * Rebuild an existing or show a new notification given {@link NotificationInfo}.
- */
- private void postNotification(NotificationInfo info) {
- Log.i(this, "postNotification : " + info.getContentTitle());
- Notification.Builder builder = new Notification.Builder(mContext);
- // Set notification as ongoing since calls are long-running versus a point-in-time notice.
- builder.setOngoing(true);
- // Make the notification prioritized over the other normal notifications.
- builder.setPriority(Notification.PRIORITY_HIGH);
- // Set the content ("Ongoing call on another device")
- builder.setContentText(mContext.getString(R.string.notification_external_call));
- builder.setSmallIcon(R.drawable.ic_call_white_24dp);
- builder.setContentTitle(info.getContentTitle());
- builder.setLargeIcon(info.getLargeIcon());
- builder.setColor(mContext.getResources().getColor(R.color.dialer_theme_color));
- builder.addPerson(info.getPersonReference());
-
- // Where the external call supports being transferred to the local device, add an action
- // to the notification to initiate the call pull process.
- if ((info.getCall().getDetails().getCallCapabilities()
- & CallSdkCompat.Details.CAPABILITY_CAN_PULL_CALL)
- == CallSdkCompat.Details.CAPABILITY_CAN_PULL_CALL) {
-
- Intent intent = new Intent(
- NotificationBroadcastReceiver.ACTION_PULL_EXTERNAL_CALL, null, mContext,
- NotificationBroadcastReceiver.class);
- intent.putExtra(NotificationBroadcastReceiver.EXTRA_NOTIFICATION_ID,
- info.getNotificationId());
-
- builder.addAction(new Notification.Action.Builder(R.drawable.ic_call_white_24dp,
- mContext.getText(R.string.notification_transfer_call),
- PendingIntent.getBroadcast(mContext, 0, intent, 0)).build());
- }
-
- /**
- * This builder is used for the notification shown when the device is locked and the user
- * has set their notification settings to 'hide sensitive content'
- * {@see Notification.Builder#setPublicVersion}.
- */
- Notification.Builder publicBuilder = new Notification.Builder(mContext);
- publicBuilder.setSmallIcon(R.drawable.ic_call_white_24dp);
- publicBuilder.setColor(mContext.getResources().getColor(R.color.dialer_theme_color));
-
- builder.setPublicVersion(publicBuilder.build());
- Notification notification = builder.build();
-
- NotificationManager notificationManager =
- (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
- notificationManager.notify(NOTIFICATION_TAG, info.getNotificationId(), notification);
- }
-
- /**
- * Finds a large icon to display in a notification for a call. For conference calls, a
- * conference call icon is used, otherwise if contact info is specified, the user's contact
- * photo or avatar is used.
- *
- * @param context The context.
- * @param contactInfo The contact cache info.
- * @param call The call.
- * @return The large icon to use for the notification.
- */
- private @Nullable Bitmap getLargeIconToDisplay(Context context,
- ContactInfoCache.ContactCacheEntry contactInfo, android.telecom.Call call) {
-
- Bitmap largeIcon = null;
- if (call.getDetails().hasProperty(android.telecom.Call.Details.PROPERTY_CONFERENCE) &&
- !call.getDetails()
- .hasProperty(android.telecom.Call.Details.PROPERTY_GENERIC_CONFERENCE)) {
-
- largeIcon = BitmapFactory.decodeResource(context.getResources(),
- R.drawable.img_conference);
- }
- if (contactInfo.photo != null && (contactInfo.photo instanceof BitmapDrawable)) {
- largeIcon = ((BitmapDrawable) contactInfo.photo).getBitmap();
- }
- return largeIcon;
- }
-
- /**
- * Given a bitmap, returns a rounded version of the icon suitable for display in a notification.
- *
- * @param context The context.
- * @param bitmap The bitmap to round.
- * @return The rounded bitmap.
- */
- private @Nullable Bitmap getRoundedIcon(Context context, @Nullable Bitmap bitmap) {
- if (bitmap == null) {
- return null;
- }
- final int height = (int) context.getResources().getDimension(
- android.R.dimen.notification_large_icon_height);
- final int width = (int) context.getResources().getDimension(
- android.R.dimen.notification_large_icon_width);
- return BitmapUtil.getRoundedBitmap(bitmap, width, height);
- }
-
- /**
- * Builds a notification content title for a call. If the call is a conference call, it is
- * identified as such. Otherwise an attempt is made to show an associated contact name or
- * phone number.
- *
- * @param context The context.
- * @param contactsPreferences Contacts preferences, used to determine the preferred formatting
- * for contact names.
- * @param contactInfo The contact info which was looked up in the contact cache.
- * @param call The call to generate a title for.
- * @return The content title.
- */
- private @Nullable String getContentTitle(Context context,
- @Nullable ContactsPreferences contactsPreferences,
- ContactInfoCache.ContactCacheEntry contactInfo, android.telecom.Call call) {
-
- if (call.getDetails().hasProperty(android.telecom.Call.Details.PROPERTY_CONFERENCE) &&
- !call.getDetails()
- .hasProperty(android.telecom.Call.Details.PROPERTY_GENERIC_CONFERENCE)) {
-
- return context.getResources().getString(R.string.card_title_conf_call);
- }
-
- String preferredName = ContactDisplayUtils.getPreferredDisplayName(contactInfo.namePrimary,
- contactInfo.nameAlternative, contactsPreferences);
- if (TextUtils.isEmpty(preferredName)) {
- return TextUtils.isEmpty(contactInfo.number) ? null : BidiFormatter.getInstance()
- .unicodeWrap(contactInfo.number, TextDirectionHeuristics.LTR);
- }
- return preferredName;
- }
-
- /**
- * Gets a "person reference" for a notification, used by the system to determine whether the
- * notification should be allowed past notification interruption filters.
- *
- * @param contactInfo The contact info from cache.
- * @param call The call.
- * @return the person reference.
- */
- private String getPersonReference(ContactInfoCache.ContactCacheEntry contactInfo,
- Call call) {
-
- String number = TelecomCallUtil.getNumber(call);
- // Query {@link Contacts#CONTENT_LOOKUP_URI} directly with work lookup key is not allowed.
- // So, do not pass {@link Contacts#CONTENT_LOOKUP_URI} to NotificationManager to avoid
- // NotificationManager using it.
- if (contactInfo.lookupUri != null && contactInfo.userType != ContactsUtils.USER_TYPE_WORK) {
- return contactInfo.lookupUri.toString();
- } else if (!TextUtils.isEmpty(number)) {
- return Uri.fromParts(PhoneAccount.SCHEME_TEL, number, null).toString();
- }
- return "";
- }
-}
diff --git a/InCallUI/src/com/android/incallui/FragmentDisplayManager.java b/InCallUI/src/com/android/incallui/FragmentDisplayManager.java
deleted file mode 100644
index 045d999a0834fd1bbaee48211a2db0f83fc34879..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/FragmentDisplayManager.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.app.Fragment;
-
-interface FragmentDisplayManager {
- public void onFragmentAttached(Fragment fragment);
-}
diff --git a/InCallUI/src/com/android/incallui/GlowPadAnswerFragment.java b/InCallUI/src/com/android/incallui/GlowPadAnswerFragment.java
deleted file mode 100644
index 62a8e7829da7c51642528dcc7ea379184e17d397..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/GlowPadAnswerFragment.java
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.os.Bundle;
-import android.telecom.VideoProfile;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.android.dialer.R;
-
-public class GlowPadAnswerFragment extends AnswerFragment {
-
- private GlowPadWrapper mGlowpad;
-
- public GlowPadAnswerFragment() {
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- mGlowpad = (GlowPadWrapper) inflater.inflate(R.layout.answer_fragment,
- container, false);
-
- Log.d(this, "Creating view for answer fragment ", this);
- Log.d(this, "Created from activity", getActivity());
- mGlowpad.setAnswerFragment(this);
-
- return mGlowpad;
- }
-
- @Override
- public void onResume() {
- super.onResume();
- mGlowpad.requestFocus();
- }
-
- @Override
- public void onDestroyView() {
- Log.d(this, "onDestroyView");
- if (mGlowpad != null) {
- mGlowpad.stopPing();
- mGlowpad = null;
- }
- super.onDestroyView();
- }
-
- @Override
- public void onShowAnswerUi(boolean shown) {
- Log.d(this, "Show answer UI: " + shown);
- if (shown) {
- mGlowpad.startPing();
- } else {
- mGlowpad.stopPing();
- }
- }
-
- /**
- * Sets targets on the glowpad according to target set identified by the parameter.
- *
- * @param targetSet Integer identifying the set of targets to use.
- */
- public void showTargets(int targetSet) {
- showTargets(targetSet, VideoProfile.STATE_BIDIRECTIONAL);
- }
-
- /**
- * Sets targets on the glowpad according to target set identified by the parameter.
- *
- * @param targetSet Integer identifying the set of targets to use.
- */
- @Override
- public void showTargets(int targetSet, int videoState) {
- final int targetResourceId;
- final int targetDescriptionsResourceId;
- final int directionDescriptionsResourceId;
- final int handleDrawableResourceId;
- mGlowpad.setVideoState(videoState);
-
- switch (targetSet) {
- case TARGET_SET_FOR_AUDIO_WITH_SMS:
- targetResourceId = R.array.incoming_call_widget_audio_with_sms_targets;
- targetDescriptionsResourceId =
- R.array.incoming_call_widget_audio_with_sms_target_descriptions;
- directionDescriptionsResourceId =
- R.array.incoming_call_widget_audio_with_sms_direction_descriptions;
- handleDrawableResourceId = R.drawable.ic_incall_audio_handle;
- break;
- case TARGET_SET_FOR_VIDEO_WITHOUT_SMS:
- targetResourceId = R.array.incoming_call_widget_video_without_sms_targets;
- targetDescriptionsResourceId =
- R.array.incoming_call_widget_video_without_sms_target_descriptions;
- directionDescriptionsResourceId =
- R.array.incoming_call_widget_video_without_sms_direction_descriptions;
- handleDrawableResourceId = R.drawable.ic_incall_video_handle;
- break;
- case TARGET_SET_FOR_VIDEO_WITH_SMS:
- targetResourceId = R.array.incoming_call_widget_video_with_sms_targets;
- targetDescriptionsResourceId =
- R.array.incoming_call_widget_video_with_sms_target_descriptions;
- directionDescriptionsResourceId =
- R.array.incoming_call_widget_video_with_sms_direction_descriptions;
- handleDrawableResourceId = R.drawable.ic_incall_video_handle;
- break;
- case TARGET_SET_FOR_VIDEO_ACCEPT_REJECT_REQUEST:
- targetResourceId =
- R.array.incoming_call_widget_video_request_targets;
- targetDescriptionsResourceId =
- R.array.incoming_call_widget_video_request_target_descriptions;
- directionDescriptionsResourceId = R.array
- .incoming_call_widget_video_request_target_direction_descriptions;
- handleDrawableResourceId = R.drawable.ic_incall_video_handle;
- break;
- case TARGET_SET_FOR_AUDIO_WITHOUT_SMS:
- default:
- targetResourceId = R.array.incoming_call_widget_audio_without_sms_targets;
- targetDescriptionsResourceId =
- R.array.incoming_call_widget_audio_without_sms_target_descriptions;
- directionDescriptionsResourceId =
- R.array.incoming_call_widget_audio_without_sms_direction_descriptions;
- handleDrawableResourceId = R.drawable.ic_incall_audio_handle;
- break;
- }
-
- if (targetResourceId != mGlowpad.getTargetResourceId()) {
- mGlowpad.setTargetResources(targetResourceId);
- mGlowpad.setTargetDescriptionsResourceId(targetDescriptionsResourceId);
- mGlowpad.setDirectionDescriptionsResourceId(directionDescriptionsResourceId);
- mGlowpad.setHandleDrawable(handleDrawableResourceId);
- mGlowpad.reset(false);
- }
- }
-
- @Override
- protected void onMessageDialogCancel() {
- if (mGlowpad != null) {
- mGlowpad.startPing();
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/GlowPadWrapper.java b/InCallUI/src/com/android/incallui/GlowPadWrapper.java
deleted file mode 100644
index 342f6b4fd667a38b6ff21a3b26572ec5c6ef0da9..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/GlowPadWrapper.java
+++ /dev/null
@@ -1,158 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.os.Handler;
-import android.os.Message;
-import android.telecom.VideoProfile;
-import android.util.AttributeSet;
-import android.view.View;
-
-import com.android.dialer.R;
-import com.android.incallui.widget.multiwaveview.GlowPadView;
-
-/**
- *
- */
-public class GlowPadWrapper extends GlowPadView implements GlowPadView.OnTriggerListener {
-
- // Parameters for the GlowPadView "ping" animation; see triggerPing().
- private static final int PING_MESSAGE_WHAT = 101;
- private static final boolean ENABLE_PING_AUTO_REPEAT = true;
- private static final long PING_REPEAT_DELAY_MS = 1200;
-
- private final Handler mPingHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case PING_MESSAGE_WHAT:
- triggerPing();
- break;
- }
- }
- };
-
- private AnswerFragment mAnswerFragment;
- private boolean mPingEnabled = true;
- private boolean mTargetTriggered = false;
- private int mVideoState = VideoProfile.STATE_BIDIRECTIONAL;
-
- public GlowPadWrapper(Context context) {
- super(context);
- Log.d(this, "class created " + this + " ");
- }
-
- public GlowPadWrapper(Context context, AttributeSet attrs) {
- super(context, attrs);
- Log.d(this, "class created " + this);
- }
-
- @Override
- protected void onFinishInflate() {
- Log.d(this, "onFinishInflate()");
- super.onFinishInflate();
- setOnTriggerListener(this);
- }
-
- public void startPing() {
- Log.d(this, "startPing");
- mPingEnabled = true;
- triggerPing();
- }
-
- public void stopPing() {
- Log.d(this, "stopPing");
- mPingEnabled = false;
- mPingHandler.removeMessages(PING_MESSAGE_WHAT);
- }
-
- private void triggerPing() {
- Log.d(this, "triggerPing(): " + mPingEnabled + " " + this);
- if (mPingEnabled && !mPingHandler.hasMessages(PING_MESSAGE_WHAT)) {
- ping();
-
- if (ENABLE_PING_AUTO_REPEAT) {
- mPingHandler.sendEmptyMessageDelayed(PING_MESSAGE_WHAT, PING_REPEAT_DELAY_MS);
- }
- }
- }
-
- @Override
- public void onGrabbed(View v, int handle) {
- Log.d(this, "onGrabbed()");
- stopPing();
- }
-
- @Override
- public void onReleased(View v, int handle) {
- Log.d(this, "onReleased()");
- if (mTargetTriggered) {
- mTargetTriggered = false;
- } else {
- startPing();
- }
- }
-
- @Override
- public void onTrigger(View v, int target) {
- Log.d(this, "onTrigger() view=" + v + " target=" + target);
- final int resId = getResourceIdForTarget(target);
- if (resId == R.drawable.ic_lockscreen_answer) {
- mAnswerFragment.onAnswer(VideoProfile.STATE_AUDIO_ONLY, getContext());
- mTargetTriggered = true;
- } else if (resId == R.drawable.ic_lockscreen_decline) {
- mAnswerFragment.onDecline(getContext());
- mTargetTriggered = true;
- } else if (resId == R.drawable.ic_lockscreen_text) {
- mAnswerFragment.onText();
- mTargetTriggered = true;
- } else if (resId == R.drawable.ic_videocam || resId == R.drawable.ic_lockscreen_answer_video) {
- mAnswerFragment.onAnswer(mVideoState, getContext());
- mTargetTriggered = true;
- } else if (resId == R.drawable.ic_lockscreen_decline_video) {
- mAnswerFragment.onDeclineUpgradeRequest(getContext());
- mTargetTriggered = true;
- } else {
- // Code should never reach here.
- Log.e(this, "Trigger detected on unhandled resource. Skipping.");
- }
- }
-
- @Override
- public void onGrabbedStateChange(View v, int handle) {
-
- }
-
- @Override
- public void onFinishFinalAnimation() {
-
- }
-
- public void setAnswerFragment(AnswerFragment fragment) {
- mAnswerFragment = fragment;
- }
-
- /**
- * Sets the video state represented by the "video" icon on the glow pad.
- *
- * @param videoState The new video state.
- */
- public void setVideoState(int videoState) {
- mVideoState = videoState;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallActivity.java b/InCallUI/src/com/android/incallui/InCallActivity.java
deleted file mode 100644
index eaaedff2ccd9a57b3e550e5067a149c09ad54522..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallActivity.java
+++ /dev/null
@@ -1,980 +0,0 @@
-/*
- * Copyright (C) 2006 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.app.ActionBar;
-import android.app.Activity;
-import android.app.ActivityManager;
-import android.app.AlertDialog;
-import android.app.DialogFragment;
-import android.app.Fragment;
-import android.app.FragmentManager;
-import android.app.FragmentTransaction;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.DialogInterface.OnClickListener;
-import android.content.Intent;
-import android.content.res.Configuration;
-import android.graphics.Point;
-import android.hardware.SensorManager;
-import android.os.Bundle;
-import android.os.Trace;
-import android.telecom.DisconnectCause;
-import android.telecom.PhoneAccountHandle;
-import android.text.TextUtils;
-import android.view.KeyEvent;
-import android.view.MenuItem;
-import android.view.MotionEvent;
-import android.view.OrientationEventListener;
-import android.view.Surface;
-import android.view.View;
-import android.view.View.OnTouchListener;
-import android.view.Window;
-import android.view.WindowManager;
-import android.view.accessibility.AccessibilityEvent;
-import android.view.animation.Animation;
-import android.view.animation.AnimationUtils;
-
-import com.android.contacts.common.activity.TransactionSafeActivity;
-import com.android.contacts.common.compat.CompatUtils;
-import com.android.contacts.common.interactions.TouchPointManager;
-import com.android.contacts.common.widget.SelectPhoneAccountDialogFragment;
-import com.android.contacts.common.widget.SelectPhoneAccountDialogFragment.SelectPhoneAccountListener;
-import com.android.dialer.R;
-import com.android.dialer.logging.Logger;
-import com.android.dialer.logging.ScreenEvent;
-import com.android.incallui.Call.State;
-import com.android.incallui.util.AccessibilityUtil;
-import com.android.phone.common.animation.AnimUtils;
-import com.android.phone.common.animation.AnimationListenerAdapter;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Locale;
-
-/**
- * Main activity that the user interacts with while in a live call.
- */
-public class InCallActivity extends TransactionSafeActivity implements FragmentDisplayManager {
-
- public static final String TAG = InCallActivity.class.getSimpleName();
-
- public static final String SHOW_DIALPAD_EXTRA = "InCallActivity.show_dialpad";
- public static final String DIALPAD_TEXT_EXTRA = "InCallActivity.dialpad_text";
- public static final String NEW_OUTGOING_CALL_EXTRA = "InCallActivity.new_outgoing_call";
- public static final String FOR_FULL_SCREEN_INTENT = "InCallActivity.for_full_screen_intent";
-
- private static final String TAG_DIALPAD_FRAGMENT = "tag_dialpad_fragment";
- private static final String TAG_CONFERENCE_FRAGMENT = "tag_conference_manager_fragment";
- private static final String TAG_CALLCARD_FRAGMENT = "tag_callcard_fragment";
- private static final String TAG_ANSWER_FRAGMENT = "tag_answer_fragment";
- private static final String TAG_SELECT_ACCT_FRAGMENT = "tag_select_acct_fragment";
-
- private static final int DIALPAD_REQUEST_NONE = 1;
- private static final int DIALPAD_REQUEST_SHOW = 2;
- private static final int DIALPAD_REQUEST_HIDE = 3;
-
- /**
- * This is used to relaunch the activity if resizing beyond which it needs to load different
- * layout file.
- */
- private static final int SCREEN_HEIGHT_RESIZE_THRESHOLD = 500;
-
- private CallButtonFragment mCallButtonFragment;
- private CallCardFragment mCallCardFragment;
- private AnswerFragment mAnswerFragment;
- private DialpadFragment mDialpadFragment;
- private ConferenceManagerFragment mConferenceManagerFragment;
- private FragmentManager mChildFragmentManager;
-
- private AlertDialog mDialog;
- private InCallOrientationEventListener mInCallOrientationEventListener;
-
- /**
- * Used to indicate whether the dialpad should be hidden or shown {@link #onResume}.
- * {@code #DIALPAD_REQUEST_SHOW} indicates that the dialpad should be shown.
- * {@code #DIALPAD_REQUEST_HIDE} indicates that the dialpad should be hidden.
- * {@code #DIALPAD_REQUEST_NONE} indicates no change should be made to dialpad visibility.
- */
- private int mShowDialpadRequest = DIALPAD_REQUEST_NONE;
-
- /**
- * Use to determine if the dialpad should be animated on show.
- */
- private boolean mAnimateDialpadOnShow;
-
- /**
- * Use to determine the DTMF Text which should be pre-populated in the dialpad.
- */
- private String mDtmfText;
-
- /**
- * Use to pass parameters for showing the PostCharDialog to {@link #onResume}
- */
- private boolean mShowPostCharWaitDialogOnResume;
- private String mShowPostCharWaitDialogCallId;
- private String mShowPostCharWaitDialogChars;
-
- private boolean mIsLandscape;
- private Animation mSlideIn;
- private Animation mSlideOut;
- private boolean mDismissKeyguard = false;
-
- AnimationListenerAdapter mSlideOutListener = new AnimationListenerAdapter() {
- @Override
- public void onAnimationEnd(Animation animation) {
- showFragment(TAG_DIALPAD_FRAGMENT, false, true);
- }
- };
-
- private OnTouchListener mDispatchTouchEventListener;
-
- private SelectPhoneAccountListener mSelectAcctListener = new SelectPhoneAccountListener() {
- @Override
- public void onPhoneAccountSelected(PhoneAccountHandle selectedAccountHandle,
- boolean setDefault) {
- InCallPresenter.getInstance().handleAccountSelection(selectedAccountHandle,
- setDefault);
- }
-
- @Override
- public void onDialogDismissed() {
- InCallPresenter.getInstance().cancelAccountSelection();
- }
- };
-
- @Override
- protected void onCreate(Bundle icicle) {
- Log.d(this, "onCreate()... this = " + this);
-
- super.onCreate(icicle);
-
- // set this flag so this activity will stay in front of the keyguard
- // Have the WindowManager filter out touch events that are "too fat".
- int flags = WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED
- | WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON
- | WindowManager.LayoutParams.FLAG_IGNORE_CHEEK_PRESSES;
-
- getWindow().addFlags(flags);
-
- // Setup action bar for the conference call manager.
- requestWindowFeature(Window.FEATURE_ACTION_BAR_OVERLAY);
- ActionBar actionBar = getActionBar();
- if (actionBar != null) {
- actionBar.setDisplayHomeAsUpEnabled(true);
- actionBar.setDisplayShowTitleEnabled(true);
- actionBar.hide();
- }
-
- // TODO(klp): Do we need to add this back when prox sensor is not available?
- // lp.inputFeatures |= WindowManager.LayoutParams.INPUT_FEATURE_DISABLE_USER_ACTIVITY;
-
- setContentView(R.layout.incall_screen);
-
- internalResolveIntent(getIntent());
-
- mIsLandscape = getResources().getConfiguration().orientation ==
- Configuration.ORIENTATION_LANDSCAPE;
-
- final boolean isRtl = TextUtils.getLayoutDirectionFromLocale(Locale.getDefault()) ==
- View.LAYOUT_DIRECTION_RTL;
-
- if (mIsLandscape) {
- mSlideIn = AnimationUtils.loadAnimation(this,
- isRtl ? R.anim.dialpad_slide_in_left : R.anim.dialpad_slide_in_right);
- mSlideOut = AnimationUtils.loadAnimation(this,
- isRtl ? R.anim.dialpad_slide_out_left : R.anim.dialpad_slide_out_right);
- } else {
- mSlideIn = AnimationUtils.loadAnimation(this, R.anim.dialpad_slide_in_bottom);
- mSlideOut = AnimationUtils.loadAnimation(this, R.anim.dialpad_slide_out_bottom);
- }
-
- mSlideIn.setInterpolator(AnimUtils.EASE_IN);
- mSlideOut.setInterpolator(AnimUtils.EASE_OUT);
-
- mSlideOut.setAnimationListener(mSlideOutListener);
-
- // If the dialpad fragment already exists, retrieve it. This is important when rotating as
- // we will not be able to hide or show the dialpad after the rotation otherwise.
- Fragment existingFragment =
- getFragmentManager().findFragmentByTag(DialpadFragment.class.getName());
- if (existingFragment != null) {
- mDialpadFragment = (DialpadFragment) existingFragment;
- }
-
- if (icicle != null) {
- // If the dialpad was shown before, set variables indicating it should be shown and
- // populated with the previous DTMF text. The dialpad is actually shown and populated
- // in onResume() to ensure the hosting CallCardFragment has been inflated and is ready
- // to receive it.
- if (icicle.containsKey(SHOW_DIALPAD_EXTRA)) {
- boolean showDialpad = icicle.getBoolean(SHOW_DIALPAD_EXTRA);
- mShowDialpadRequest = showDialpad ? DIALPAD_REQUEST_SHOW : DIALPAD_REQUEST_HIDE;
- mAnimateDialpadOnShow = false;
- }
- mDtmfText = icicle.getString(DIALPAD_TEXT_EXTRA);
-
- SelectPhoneAccountDialogFragment dialogFragment = (SelectPhoneAccountDialogFragment)
- getFragmentManager().findFragmentByTag(TAG_SELECT_ACCT_FRAGMENT);
- if (dialogFragment != null) {
- dialogFragment.setListener(mSelectAcctListener);
- }
- }
- mInCallOrientationEventListener = new InCallOrientationEventListener(this);
-
- Log.d(this, "onCreate(): exit");
- }
-
- @Override
- protected void onSaveInstanceState(Bundle out) {
- // TODO: The dialpad fragment should handle this as part of its own state
- out.putBoolean(SHOW_DIALPAD_EXTRA,
- mCallButtonFragment != null && mCallButtonFragment.isDialpadVisible());
- if (mDialpadFragment != null) {
- out.putString(DIALPAD_TEXT_EXTRA, mDialpadFragment.getDtmfText());
- }
- super.onSaveInstanceState(out);
- }
-
- @Override
- protected void onStart() {
- Log.d(this, "onStart()...");
- super.onStart();
-
- // setting activity should be last thing in setup process
- InCallPresenter.getInstance().setActivity(this);
- enableInCallOrientationEventListener(getRequestedOrientation() ==
- InCallOrientationEventListener.FULL_SENSOR_SCREEN_ORIENTATION);
-
- InCallPresenter.getInstance().onActivityStarted();
- }
-
- @Override
- protected void onResume() {
- Log.i(this, "onResume()...");
- super.onResume();
-
- InCallPresenter.getInstance().setThemeColors();
- InCallPresenter.getInstance().onUiShowing(true);
-
- // Clear fullscreen state onResume; the stored value may not match reality.
- InCallPresenter.getInstance().clearFullscreen();
-
- // If there is a pending request to show or hide the dialpad, handle that now.
- if (mShowDialpadRequest != DIALPAD_REQUEST_NONE) {
- if (mShowDialpadRequest == DIALPAD_REQUEST_SHOW) {
- // Exit fullscreen so that the user has access to the dialpad hide/show button and
- // can hide the dialpad. Important when showing the dialpad from within dialer.
- InCallPresenter.getInstance().setFullScreen(false, true /* force */);
-
- mCallButtonFragment.displayDialpad(true /* show */,
- mAnimateDialpadOnShow /* animate */);
- mAnimateDialpadOnShow = false;
-
- if (mDialpadFragment != null) {
- mDialpadFragment.setDtmfText(mDtmfText);
- mDtmfText = null;
- }
- } else {
- Log.v(this, "onResume : force hide dialpad");
- if (mDialpadFragment != null) {
- mCallButtonFragment.displayDialpad(false /* show */, false /* animate */);
- }
- }
- mShowDialpadRequest = DIALPAD_REQUEST_NONE;
- }
-
- if (mShowPostCharWaitDialogOnResume) {
- showPostCharWaitDialog(mShowPostCharWaitDialogCallId, mShowPostCharWaitDialogChars);
- }
-
- CallList.getInstance().onInCallUiShown(
- getIntent().getBooleanExtra(FOR_FULL_SCREEN_INTENT, false));
- }
-
- // onPause is guaranteed to be called when the InCallActivity goes
- // in the background.
- @Override
- protected void onPause() {
- Log.d(this, "onPause()...");
- if (mDialpadFragment != null) {
- mDialpadFragment.onDialerKeyUp(null);
- }
-
- InCallPresenter.getInstance().onUiShowing(false);
- if (isFinishing()) {
- InCallPresenter.getInstance().unsetActivity(this);
- }
- super.onPause();
- }
-
- @Override
- protected void onStop() {
- Log.d(this, "onStop()...");
- enableInCallOrientationEventListener(false);
- InCallPresenter.getInstance().updateIsChangingConfigurations();
- InCallPresenter.getInstance().onActivityStopped();
- super.onStop();
- }
-
- @Override
- protected void onDestroy() {
- Log.d(this, "onDestroy()... this = " + this);
- InCallPresenter.getInstance().unsetActivity(this);
- InCallPresenter.getInstance().updateIsChangingConfigurations();
- super.onDestroy();
- }
-
- /**
- * When fragments have a parent fragment, onAttachFragment is not called on the parent
- * activity. To fix this, register our own callback instead that is always called for
- * all fragments.
- *
- * @see {@link BaseFragment#onAttach(Activity)}
- */
- @Override
- public void onFragmentAttached(Fragment fragment) {
- if (fragment instanceof DialpadFragment) {
- mDialpadFragment = (DialpadFragment) fragment;
- } else if (fragment instanceof AnswerFragment) {
- mAnswerFragment = (AnswerFragment) fragment;
- } else if (fragment instanceof CallCardFragment) {
- mCallCardFragment = (CallCardFragment) fragment;
- mChildFragmentManager = mCallCardFragment.getChildFragmentManager();
- } else if (fragment instanceof ConferenceManagerFragment) {
- mConferenceManagerFragment = (ConferenceManagerFragment) fragment;
- } else if (fragment instanceof CallButtonFragment) {
- mCallButtonFragment = (CallButtonFragment) fragment;
- }
- }
-
- @Override
- public void onConfigurationChanged(Configuration newConfig) {
- super.onConfigurationChanged(newConfig);
- Configuration oldConfig = getResources().getConfiguration();
- Log.v(this, String.format(
- "incallui config changed, screen size: w%ddp x h%ddp old:w%ddp x h%ddp",
- newConfig.screenWidthDp, newConfig.screenHeightDp,
- oldConfig.screenWidthDp, oldConfig.screenHeightDp));
- // Recreate this activity if height is changing beyond the threshold to load different
- // layout file.
- if (oldConfig.screenHeightDp < SCREEN_HEIGHT_RESIZE_THRESHOLD &&
- newConfig.screenHeightDp > SCREEN_HEIGHT_RESIZE_THRESHOLD ||
- oldConfig.screenHeightDp > SCREEN_HEIGHT_RESIZE_THRESHOLD &&
- newConfig.screenHeightDp < SCREEN_HEIGHT_RESIZE_THRESHOLD) {
- Log.i(this, String.format(
- "Recreate activity due to resize beyond threshold: %d dp",
- SCREEN_HEIGHT_RESIZE_THRESHOLD));
- recreate();
- }
- }
-
- /**
- * Returns true when the Activity is currently visible.
- */
- /* package */ boolean isVisible() {
- return isSafeToCommitTransactions();
- }
-
- private boolean hasPendingDialogs() {
- return mDialog != null || (mAnswerFragment != null && mAnswerFragment.hasPendingDialogs());
- }
-
- @Override
- public void finish() {
- Log.i(this, "finish(). Dialog showing: " + (mDialog != null));
-
- // skip finish if we are still showing a dialog.
- if (!hasPendingDialogs()) {
- super.finish();
- }
- }
-
- @Override
- protected void onNewIntent(Intent intent) {
- Log.d(this, "onNewIntent: intent = " + intent);
-
- // We're being re-launched with a new Intent. Since it's possible for a
- // single InCallActivity instance to persist indefinitely (even if we
- // finish() ourselves), this sequence can potentially happen any time
- // the InCallActivity needs to be displayed.
-
- // Stash away the new intent so that we can get it in the future
- // by calling getIntent(). (Otherwise getIntent() will return the
- // original Intent from when we first got created!)
- setIntent(intent);
-
- // Activities are always paused before receiving a new intent, so
- // we can count on our onResume() method being called next.
-
- // Just like in onCreate(), handle the intent.
- internalResolveIntent(intent);
- }
-
- @Override
- public void onBackPressed() {
- Log.i(this, "onBackPressed");
-
- // BACK is also used to exit out of any "special modes" of the
- // in-call UI:
- if (!isVisible()) {
- return;
- }
-
- if ((mConferenceManagerFragment == null || !mConferenceManagerFragment.isVisible())
- && (mCallCardFragment == null || !mCallCardFragment.isVisible())) {
- return;
- }
-
- if (mDialpadFragment != null && mDialpadFragment.isVisible()) {
- mCallButtonFragment.displayDialpad(false /* show */, true /* animate */);
- return;
- } else if (mConferenceManagerFragment != null && mConferenceManagerFragment.isVisible()) {
- showConferenceFragment(false);
- return;
- }
-
- // Always disable the Back key while an incoming call is ringing
- final Call call = CallList.getInstance().getIncomingCall();
- if (call != null) {
- Log.i(this, "Consume Back press for an incoming call");
- return;
- }
-
- // Nothing special to do. Fall back to the default behavior.
- super.onBackPressed();
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- final int itemId = item.getItemId();
- if (itemId == android.R.id.home) {
- onBackPressed();
- return true;
- }
- return super.onOptionsItemSelected(item);
- }
-
- @Override
- public boolean onKeyUp(int keyCode, KeyEvent event) {
- // push input to the dialer.
- if (mDialpadFragment != null && (mDialpadFragment.isVisible()) &&
- (mDialpadFragment.onDialerKeyUp(event))) {
- return true;
- } else if (keyCode == KeyEvent.KEYCODE_CALL) {
- // Always consume CALL to be sure the PhoneWindow won't do anything with it
- return true;
- }
- return super.onKeyUp(keyCode, event);
- }
-
- @Override
- public boolean dispatchTouchEvent(MotionEvent ev) {
- if (mDispatchTouchEventListener != null) {
- boolean handled = mDispatchTouchEventListener.onTouch(null, ev);
- if (handled) {
- return true;
- }
- }
- return super.dispatchTouchEvent(ev);
- }
-
- @Override
- public boolean onKeyDown(int keyCode, KeyEvent event) {
- switch (keyCode) {
- case KeyEvent.KEYCODE_CALL:
- boolean handled = InCallPresenter.getInstance().handleCallKey();
- if (!handled) {
- Log.w(this, "InCallActivity should always handle KEYCODE_CALL in onKeyDown");
- }
- // Always consume CALL to be sure the PhoneWindow won't do anything with it
- return true;
-
- // Note there's no KeyEvent.KEYCODE_ENDCALL case here.
- // The standard system-wide handling of the ENDCALL key
- // (see PhoneWindowManager's handling of KEYCODE_ENDCALL)
- // already implements exactly what the UI spec wants,
- // namely (1) "hang up" if there's a current active call,
- // or (2) "don't answer" if there's a current ringing call.
-
- case KeyEvent.KEYCODE_CAMERA:
- // Disable the CAMERA button while in-call since it's too
- // easy to press accidentally.
- return true;
-
- case KeyEvent.KEYCODE_VOLUME_UP:
- case KeyEvent.KEYCODE_VOLUME_DOWN:
- case KeyEvent.KEYCODE_VOLUME_MUTE:
- // Ringer silencing handled by PhoneWindowManager.
- break;
-
- case KeyEvent.KEYCODE_MUTE:
- // toggle mute
- TelecomAdapter.getInstance().mute(!AudioModeProvider.getInstance().getMute());
- return true;
-
- // Various testing/debugging features, enabled ONLY when VERBOSE == true.
- case KeyEvent.KEYCODE_SLASH:
- if (Log.VERBOSE) {
- Log.v(this, "----------- InCallActivity View dump --------------");
- // Dump starting from the top-level view of the entire activity:
- Window w = this.getWindow();
- View decorView = w.getDecorView();
- Log.d(this, "View dump:" + decorView);
- return true;
- }
- break;
- case KeyEvent.KEYCODE_EQUALS:
- // TODO: Dump phone state?
- break;
- }
-
- if (event.getRepeatCount() == 0 && handleDialerKeyDown(keyCode, event)) {
- return true;
- }
- return super.onKeyDown(keyCode, event);
- }
-
- private boolean handleDialerKeyDown(int keyCode, KeyEvent event) {
- Log.v(this, "handleDialerKeyDown: keyCode " + keyCode + ", event " + event + "...");
-
- // As soon as the user starts typing valid dialable keys on the
- // keyboard (presumably to type DTMF tones) we start passing the
- // key events to the DTMFDialer's onDialerKeyDown.
- if (mDialpadFragment != null && mDialpadFragment.isVisible()) {
- return mDialpadFragment.onDialerKeyDown(event);
- }
-
- return false;
- }
-
- public CallButtonFragment getCallButtonFragment() {
- return mCallButtonFragment;
- }
-
- public CallCardFragment getCallCardFragment() {
- return mCallCardFragment;
- }
-
- public AnswerFragment getAnswerFragment() {
- return mAnswerFragment;
- }
-
- private void internalResolveIntent(Intent intent) {
- final String action = intent.getAction();
- if (action.equals(Intent.ACTION_MAIN)) {
- // This action is the normal way to bring up the in-call UI.
- //
- // But we do check here for one extra that can come along with the
- // ACTION_MAIN intent:
-
- if (intent.hasExtra(SHOW_DIALPAD_EXTRA)) {
- // SHOW_DIALPAD_EXTRA can be used here to specify whether the DTMF
- // dialpad should be initially visible. If the extra isn't
- // present at all, we just leave the dialpad in its previous state.
-
- final boolean showDialpad = intent.getBooleanExtra(SHOW_DIALPAD_EXTRA, false);
- Log.d(this, "- internalResolveIntent: SHOW_DIALPAD_EXTRA: " + showDialpad);
-
- relaunchedFromDialer(showDialpad);
- }
-
- boolean newOutgoingCall = false;
- if (intent.getBooleanExtra(NEW_OUTGOING_CALL_EXTRA, false)) {
- intent.removeExtra(NEW_OUTGOING_CALL_EXTRA);
- Call call = CallList.getInstance().getOutgoingCall();
- if (call == null) {
- call = CallList.getInstance().getPendingOutgoingCall();
- }
-
- Bundle extras = null;
- if (call != null) {
- extras = call.getTelecomCall().getDetails().getIntentExtras();
- }
- if (extras == null) {
- // Initialize the extras bundle to avoid NPE
- extras = new Bundle();
- }
-
- Point touchPoint = null;
- if (TouchPointManager.getInstance().hasValidPoint()) {
- // Use the most immediate touch point in the InCallUi if available
- touchPoint = TouchPointManager.getInstance().getPoint();
- } else {
- // Otherwise retrieve the touch point from the call intent
- if (call != null) {
- touchPoint = (Point) extras.getParcelable(TouchPointManager.TOUCH_POINT);
- }
- }
-
- // Start animation for new outgoing call
- CircularRevealFragment.startCircularReveal(getFragmentManager(), touchPoint,
- InCallPresenter.getInstance());
-
- // InCallActivity is responsible for disconnecting a new outgoing call if there
- // is no way of making it (i.e. no valid call capable accounts).
- // If the version is not MSIM compatible, then ignore this code.
- if (CompatUtils.isMSIMCompatible()
- && InCallPresenter.isCallWithNoValidAccounts(call)) {
- TelecomAdapter.getInstance().disconnectCall(call.getId());
- }
-
- dismissKeyguard(true);
- newOutgoingCall = true;
- }
-
- Call pendingAccountSelectionCall = CallList.getInstance().getWaitingForAccountCall();
- if (pendingAccountSelectionCall != null) {
- showCallCardFragment(false);
- Bundle extras =
- pendingAccountSelectionCall.getTelecomCall().getDetails().getIntentExtras();
-
- final List phoneAccountHandles;
- if (extras != null) {
- phoneAccountHandles = extras.getParcelableArrayList(
- android.telecom.Call.AVAILABLE_PHONE_ACCOUNTS);
- } else {
- phoneAccountHandles = new ArrayList<>();
- }
-
- DialogFragment dialogFragment = SelectPhoneAccountDialogFragment.newInstance(
- R.string.select_phone_account_for_calls, true, phoneAccountHandles,
- mSelectAcctListener);
- dialogFragment.show(getFragmentManager(), TAG_SELECT_ACCT_FRAGMENT);
- } else if (!newOutgoingCall) {
- showCallCardFragment(true);
- }
- return;
- }
- }
-
- /**
- * When relaunching from the dialer app, {@code showDialpad} indicates whether the dialpad
- * should be shown on launch.
- *
- * @param showDialpad {@code true} to indicate the dialpad should be shown on launch, and
- * {@code false} to indicate no change should be made to the
- * dialpad visibility.
- */
- private void relaunchedFromDialer(boolean showDialpad) {
- mShowDialpadRequest = showDialpad ? DIALPAD_REQUEST_SHOW : DIALPAD_REQUEST_NONE;
- mAnimateDialpadOnShow = true;
-
- if (mShowDialpadRequest == DIALPAD_REQUEST_SHOW) {
- // If there's only one line in use, AND it's on hold, then we're sure the user
- // wants to use the dialpad toward the exact line, so un-hold the holding line.
- final Call call = CallList.getInstance().getActiveOrBackgroundCall();
- if (call != null && call.getState() == State.ONHOLD) {
- TelecomAdapter.getInstance().unholdCall(call.getId());
- }
- }
- }
-
- public void dismissKeyguard(boolean dismiss) {
- if (mDismissKeyguard == dismiss) {
- return;
- }
- mDismissKeyguard = dismiss;
- if (dismiss) {
- getWindow().addFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD);
- } else {
- getWindow().clearFlags(WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD);
- }
- }
-
- private void showFragment(String tag, boolean show, boolean executeImmediately) {
- Trace.beginSection("showFragment - " + tag);
- final FragmentManager fm = getFragmentManagerForTag(tag);
-
- if (fm == null) {
- Log.w(TAG, "Fragment manager is null for : " + tag);
- return;
- }
-
- Fragment fragment = fm.findFragmentByTag(tag);
- if (!show && fragment == null) {
- // Nothing to show, so bail early.
- return;
- }
-
- final FragmentTransaction transaction = fm.beginTransaction();
- if (show) {
- if (fragment == null) {
- fragment = createNewFragmentForTag(tag);
- transaction.add(getContainerIdForFragment(tag), fragment, tag);
- } else {
- transaction.show(fragment);
- }
- Logger.logScreenView(getScreenTypeForTag(tag), this);
- } else {
- transaction.hide(fragment);
- }
-
- transaction.commitAllowingStateLoss();
- if (executeImmediately) {
- fm.executePendingTransactions();
- }
- Trace.endSection();
- }
-
- private Fragment createNewFragmentForTag(String tag) {
- if (TAG_DIALPAD_FRAGMENT.equals(tag)) {
- mDialpadFragment = new DialpadFragment();
- return mDialpadFragment;
- } else if (TAG_ANSWER_FRAGMENT.equals(tag)) {
- if (AccessibilityUtil.isTalkBackEnabled(this)) {
- mAnswerFragment = new AccessibleAnswerFragment();
- } else {
- mAnswerFragment = new GlowPadAnswerFragment();
- }
- return mAnswerFragment;
- } else if (TAG_CONFERENCE_FRAGMENT.equals(tag)) {
- mConferenceManagerFragment = new ConferenceManagerFragment();
- return mConferenceManagerFragment;
- } else if (TAG_CALLCARD_FRAGMENT.equals(tag)) {
- mCallCardFragment = new CallCardFragment();
- return mCallCardFragment;
- }
- throw new IllegalStateException("Unexpected fragment: " + tag);
- }
-
- private FragmentManager getFragmentManagerForTag(String tag) {
- if (TAG_DIALPAD_FRAGMENT.equals(tag)) {
- return mChildFragmentManager;
- } else if (TAG_ANSWER_FRAGMENT.equals(tag)) {
- return mChildFragmentManager;
- } else if (TAG_CONFERENCE_FRAGMENT.equals(tag)) {
- return getFragmentManager();
- } else if (TAG_CALLCARD_FRAGMENT.equals(tag)) {
- return getFragmentManager();
- }
- throw new IllegalStateException("Unexpected fragment: " + tag);
- }
-
- private int getScreenTypeForTag(String tag) {
- switch (tag) {
- case TAG_DIALPAD_FRAGMENT:
- return ScreenEvent.INCALL_DIALPAD;
- case TAG_CALLCARD_FRAGMENT:
- return ScreenEvent.INCALL;
- case TAG_CONFERENCE_FRAGMENT:
- return ScreenEvent.CONFERENCE_MANAGEMENT;
- case TAG_ANSWER_FRAGMENT:
- return ScreenEvent.INCOMING_CALL;
- default:
- return ScreenEvent.UNKNOWN;
- }
- }
-
- private int getContainerIdForFragment(String tag) {
- if (TAG_DIALPAD_FRAGMENT.equals(tag)) {
- return R.id.answer_and_dialpad_container;
- } else if (TAG_ANSWER_FRAGMENT.equals(tag)) {
- return R.id.answer_and_dialpad_container;
- } else if (TAG_CONFERENCE_FRAGMENT.equals(tag)) {
- return R.id.main;
- } else if (TAG_CALLCARD_FRAGMENT.equals(tag)) {
- return R.id.main;
- }
- throw new IllegalStateException("Unexpected fragment: " + tag);
- }
-
- /**
- * @return {@code true} while the visibility of the dialpad has actually changed.
- */
- public boolean showDialpadFragment(boolean show, boolean animate) {
- // If the dialpad is already visible, don't animate in. If it's gone, don't animate out.
- if ((show && isDialpadVisible()) || (!show && !isDialpadVisible())) {
- return false;
- }
- // We don't do a FragmentTransaction on the hide case because it will be dealt with when
- // the listener is fired after an animation finishes.
- if (!animate) {
- showFragment(TAG_DIALPAD_FRAGMENT, show, true);
- } else {
- if (show) {
- showFragment(TAG_DIALPAD_FRAGMENT, true, true);
- mDialpadFragment.animateShowDialpad();
- }
- mDialpadFragment.getView().startAnimation(show ? mSlideIn : mSlideOut);
- }
- // Note: onDialpadVisibilityChange is called here to ensure that the dialpad FAB
- // repositions itself.
- mCallCardFragment.onDialpadVisibilityChange(show);
-
- final ProximitySensor sensor = InCallPresenter.getInstance().getProximitySensor();
- if (sensor != null) {
- sensor.onDialpadVisible(show);
- }
- return true;
- }
-
- public boolean isDialpadVisible() {
- return mDialpadFragment != null && mDialpadFragment.isVisible();
- }
-
- public void showCallCardFragment(boolean show) {
- showFragment(TAG_CALLCARD_FRAGMENT, show, true);
- }
-
- /**
- * Hides or shows the conference manager fragment.
- *
- * @param show {@code true} if the conference manager should be shown, {@code false} if it
- * should be hidden.
- */
- public void showConferenceFragment(boolean show) {
- showFragment(TAG_CONFERENCE_FRAGMENT, show, true);
- mConferenceManagerFragment.onVisibilityChanged(show);
-
- // Need to hide the call card fragment to ensure that accessibility service does not try to
- // give focus to the call card when the conference manager is visible.
- mCallCardFragment.getView().setVisibility(show ? View.GONE : View.VISIBLE);
- }
-
- public void showAnswerFragment(boolean show) {
- // CallCardFragment is the parent fragment of AnswerFragment.
- // Must create the CallCardFragment first before creating
- // AnswerFragment if CallCardFragment is null.
- if (show && getCallCardFragment() == null) {
- showCallCardFragment(true);
- }
- showFragment(TAG_ANSWER_FRAGMENT, show, true);
- }
-
- public void showPostCharWaitDialog(String callId, String chars) {
- if (isVisible()) {
- final PostCharDialogFragment fragment = new PostCharDialogFragment(callId, chars);
- fragment.show(getFragmentManager(), "postCharWait");
-
- mShowPostCharWaitDialogOnResume = false;
- mShowPostCharWaitDialogCallId = null;
- mShowPostCharWaitDialogChars = null;
- } else {
- mShowPostCharWaitDialogOnResume = true;
- mShowPostCharWaitDialogCallId = callId;
- mShowPostCharWaitDialogChars = chars;
- }
- }
-
- @Override
- public boolean dispatchPopulateAccessibilityEvent(AccessibilityEvent event) {
- if (mCallCardFragment != null) {
- mCallCardFragment.dispatchPopulateAccessibilityEvent(event);
- }
- return super.dispatchPopulateAccessibilityEvent(event);
- }
-
- public void maybeShowErrorDialogOnDisconnect(DisconnectCause disconnectCause) {
- Log.d(this, "maybeShowErrorDialogOnDisconnect");
-
- if (!isFinishing() && !TextUtils.isEmpty(disconnectCause.getDescription())
- && (disconnectCause.getCode() == DisconnectCause.ERROR ||
- disconnectCause.getCode() == DisconnectCause.RESTRICTED)) {
- showErrorDialog(disconnectCause.getDescription());
- }
- }
-
- public void dismissPendingDialogs() {
- if (mDialog != null) {
- mDialog.dismiss();
- mDialog = null;
- }
- if (mAnswerFragment != null) {
- mAnswerFragment.dismissPendingDialogs();
- }
-
- SelectPhoneAccountDialogFragment dialogFragment = (SelectPhoneAccountDialogFragment)
- getFragmentManager().findFragmentByTag(TAG_SELECT_ACCT_FRAGMENT);
- if (dialogFragment != null) {
- dialogFragment.dismiss();
- }
- }
-
- /**
- * Utility function to bring up a generic "error" dialog.
- */
- private void showErrorDialog(CharSequence msg) {
- Log.i(this, "Show Dialog: " + msg);
-
- dismissPendingDialogs();
-
- mDialog = new AlertDialog.Builder(this)
- .setMessage(msg)
- .setPositiveButton(android.R.string.ok, new OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- onDialogDismissed();
- }
- })
- .setOnCancelListener(new OnCancelListener() {
- @Override
- public void onCancel(DialogInterface dialog) {
- onDialogDismissed();
- }
- })
- .create();
-
- mDialog.getWindow().addFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND);
- mDialog.show();
- }
-
- private void onDialogDismissed() {
- mDialog = null;
- CallList.getInstance().onErrorDialogDismissed();
- InCallPresenter.getInstance().onDismissDialog();
- }
-
- public void setExcludeFromRecents(boolean exclude) {
- ActivityManager am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
- List tasks = am.getAppTasks();
- int taskId = getTaskId();
- for (int i = 0; i < tasks.size(); i++) {
- ActivityManager.AppTask task = tasks.get(i);
- if (task.getTaskInfo().id == taskId) {
- try {
- task.setExcludeFromRecents(exclude);
- } catch (RuntimeException e) {
- Log.e(TAG, "RuntimeException when excluding task from recents.", e);
- }
- }
- }
- }
-
-
- public OnTouchListener getDispatchTouchEventListener() {
- return mDispatchTouchEventListener;
- }
-
- public void setDispatchTouchEventListener(OnTouchListener mDispatchTouchEventListener) {
- this.mDispatchTouchEventListener = mDispatchTouchEventListener;
- }
-
- /**
- * Enables the OrientationEventListener if enable flag is true. Disables it if enable is
- * false
- * @param enable true or false.
- */
- public void enableInCallOrientationEventListener(boolean enable) {
- if (enable) {
- mInCallOrientationEventListener.enable(enable);
- } else {
- mInCallOrientationEventListener.disable();
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallAnimationUtils.java b/InCallUI/src/com/android/incallui/InCallAnimationUtils.java
deleted file mode 100644
index 44bb369e61aac9d2faf23f760183ab99e14d415e..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallAnimationUtils.java
+++ /dev/null
@@ -1,184 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.animation.Animator;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.ObjectAnimator;
-import android.graphics.Canvas;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.LayerDrawable;
-import android.view.ViewPropertyAnimator;
-import android.widget.ImageView;
-
-/**
- * Utilities for Animation.
- */
-public class InCallAnimationUtils {
- private static final String LOG_TAG = InCallAnimationUtils.class.getSimpleName();
- /**
- * Turn on when you're interested in fading animation. Intentionally untied from other debug
- * settings.
- */
- private static final boolean FADE_DBG = false;
-
- /**
- * Duration for animations in msec, which can be used with
- * {@link ViewPropertyAnimator#setDuration(long)} for example.
- */
- public static final int ANIMATION_DURATION = 250;
-
- private InCallAnimationUtils() {
- }
-
- /**
- * Drawable achieving cross-fade, just like TransitionDrawable. We can have
- * call-backs via animator object (see also {@link CrossFadeDrawable#getAnimator()}).
- */
- private static class CrossFadeDrawable extends LayerDrawable {
- private final ObjectAnimator mAnimator;
-
- public CrossFadeDrawable(Drawable[] layers) {
- super(layers);
- mAnimator = ObjectAnimator.ofInt(this, "crossFadeAlpha", 0xff, 0);
- }
-
- private int mCrossFadeAlpha;
-
- /**
- * This will be used from ObjectAnimator.
- * Note: this method is protected by proguard.flags so that it won't be removed
- * automatically.
- */
- @SuppressWarnings("unused")
- public void setCrossFadeAlpha(int alpha) {
- mCrossFadeAlpha = alpha;
- invalidateSelf();
- }
-
- public ObjectAnimator getAnimator() {
- return mAnimator;
- }
-
- @Override
- public void draw(Canvas canvas) {
- Drawable first = getDrawable(0);
- Drawable second = getDrawable(1);
-
- if (mCrossFadeAlpha > 0) {
- first.setAlpha(mCrossFadeAlpha);
- first.draw(canvas);
- first.setAlpha(255);
- }
-
- if (mCrossFadeAlpha < 0xff) {
- second.setAlpha(0xff - mCrossFadeAlpha);
- second.draw(canvas);
- second.setAlpha(0xff);
- }
- }
- }
-
- private static CrossFadeDrawable newCrossFadeDrawable(Drawable first, Drawable second) {
- Drawable[] layers = new Drawable[2];
- layers[0] = first;
- layers[1] = second;
- return new CrossFadeDrawable(layers);
- }
-
- /**
- * Starts cross-fade animation using TransitionDrawable. Nothing will happen if "from" and "to"
- * are the same.
- */
- public static void startCrossFade(
- final ImageView imageView, final Drawable from, final Drawable to) {
- // We skip the cross-fade when those two Drawables are equal, or they are BitmapDrawables
- // pointing to the same Bitmap.
- final boolean drawableIsEqual = (from != null && to != null && from.equals(to));
- final boolean hasFromImage = ((from instanceof BitmapDrawable) &&
- ((BitmapDrawable) from).getBitmap() != null);
- final boolean hasToImage = ((to instanceof BitmapDrawable) &&
- ((BitmapDrawable) to).getBitmap() != null);
- final boolean areSameImage = drawableIsEqual || (hasFromImage && hasToImage &&
- ((BitmapDrawable) from).getBitmap().equals(((BitmapDrawable) to).getBitmap()));
-
- if (!areSameImage) {
- if (FADE_DBG) {
- log("Start cross-fade animation for " + imageView
- + "(" + Integer.toHexString(from.hashCode()) + " -> "
- + Integer.toHexString(to.hashCode()) + ")");
- }
-
- CrossFadeDrawable crossFadeDrawable = newCrossFadeDrawable(from, to);
- ObjectAnimator animator = crossFadeDrawable.getAnimator();
- imageView.setImageDrawable(crossFadeDrawable);
- animator.setDuration(ANIMATION_DURATION);
- animator.addListener(new AnimatorListenerAdapter() {
- @Override
- public void onAnimationStart(Animator animation) {
- if (FADE_DBG) {
- log("cross-fade animation start ("
- + Integer.toHexString(from.hashCode()) + " -> "
- + Integer.toHexString(to.hashCode()) + ")");
- }
- }
-
- @Override
- public void onAnimationEnd(Animator animation) {
- if (FADE_DBG) {
- log("cross-fade animation ended ("
- + Integer.toHexString(from.hashCode()) + " -> "
- + Integer.toHexString(to.hashCode()) + ")");
- }
- animation.removeAllListeners();
- // Workaround for issue 6300562; this will force the drawable to the
- // resultant one regardless of animation glitch.
- imageView.setImageDrawable(to);
- }
- });
- animator.start();
-
- /* We could use TransitionDrawable here, but it may cause some weird animation in
- * some corner cases. See issue 6300562
- * TODO: decide which to be used in the long run. TransitionDrawable is old but system
- * one. Ours uses new animation framework and thus have callback (great for testing),
- * while no framework support for the exact class.
-
- Drawable[] layers = new Drawable[2];
- layers[0] = from;
- layers[1] = to;
- TransitionDrawable transitionDrawable = new TransitionDrawable(layers);
- imageView.setImageDrawable(transitionDrawable);
- transitionDrawable.startTransition(ANIMATION_DURATION); */
- imageView.setTag(to);
- } else if (!hasFromImage && hasToImage) {
- imageView.setImageDrawable(to);
- imageView.setTag(to);
- } else {
- if (FADE_DBG) {
- log("*Not* start cross-fade. " + imageView);
- }
- }
- }
-
- // Debugging / testing code
-
- private static void log(String msg) {
- Log.d(LOG_TAG, msg);
- }
-}
\ No newline at end of file
diff --git a/InCallUI/src/com/android/incallui/InCallCameraManager.java b/InCallUI/src/com/android/incallui/InCallCameraManager.java
deleted file mode 100644
index 53000f1ddd2d9ea8a6dc870ba9bfa30656bee1ed..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallCameraManager.java
+++ /dev/null
@@ -1,184 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.graphics.SurfaceTexture;
-import android.hardware.camera2.CameraAccessException;
-import android.hardware.camera2.CameraCharacteristics;
-import android.hardware.camera2.CameraManager;
-import android.hardware.camera2.params.StreamConfigurationMap;
-import android.util.Size;
-
-import java.lang.String;
-import java.util.Collections;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.Set;
-
-/**
- * Used to track which camera is used for outgoing video.
- */
-public class InCallCameraManager {
-
- public interface Listener {
- void onActiveCameraSelectionChanged(boolean isUsingFrontFacingCamera);
- }
-
- private final Set mCameraSelectionListeners = Collections.
- newSetFromMap(new ConcurrentHashMap(8,0.9f,1));
-
- /**
- * The camera ID for the front facing camera.
- */
- private String mFrontFacingCameraId;
-
- /**
- * The camera ID for the rear facing camera.
- */
- private String mRearFacingCameraId;
-
- /**
- * The currently active camera.
- */
- private boolean mUseFrontFacingCamera;
-
- /**
- * Indicates whether the list of cameras has been initialized yet. Initialization is delayed
- * until a video call is present.
- */
- private boolean mIsInitialized = false;
-
- /**
- * The context.
- */
- private Context mContext;
-
- /**
- * Initializes the InCall CameraManager.
- *
- * @param context The current context.
- */
- public InCallCameraManager(Context context) {
- mUseFrontFacingCamera = true;
- mContext = context;
- }
-
- /**
- * Sets whether the front facing camera should be used or not.
- *
- * @param useFrontFacingCamera {@code True} if the front facing camera is to be used.
- */
- public void setUseFrontFacingCamera(boolean useFrontFacingCamera) {
- mUseFrontFacingCamera = useFrontFacingCamera;
- for (Listener listener : mCameraSelectionListeners) {
- listener.onActiveCameraSelectionChanged(mUseFrontFacingCamera);
- }
- }
-
- /**
- * Determines whether the front facing camera is currently in use.
- *
- * @return {@code True} if the front facing camera is in use.
- */
- public boolean isUsingFrontFacingCamera() {
- return mUseFrontFacingCamera;
- }
-
- /**
- * Determines the active camera ID.
- *
- * @return The active camera ID.
- */
- public String getActiveCameraId() {
- maybeInitializeCameraList(mContext);
-
- if (mUseFrontFacingCamera) {
- return mFrontFacingCameraId;
- } else {
- return mRearFacingCameraId;
- }
- }
-
- /**
- * Get the list of cameras available for use.
- *
- * @param context The context.
- */
- private void maybeInitializeCameraList(Context context) {
- if (mIsInitialized || context == null) {
- return;
- }
-
- Log.v(this, "initializeCameraList");
-
- CameraManager cameraManager = null;
- try {
- cameraManager = (CameraManager) context.getSystemService(
- Context.CAMERA_SERVICE);
- } catch (Exception e) {
- Log.e(this, "Could not get camera service.");
- return;
- }
-
- if (cameraManager == null) {
- return;
- }
-
- String[] cameraIds = {};
- try {
- cameraIds = cameraManager.getCameraIdList();
- } catch (CameraAccessException e) {
- Log.d(this, "Could not access camera: "+e);
- // Camera disabled by device policy.
- return;
- }
-
- for (int i = 0; i < cameraIds.length; i++) {
- CameraCharacteristics c = null;
- try {
- c = cameraManager.getCameraCharacteristics(cameraIds[i]);
- } catch (IllegalArgumentException e) {
- // Device Id is unknown.
- } catch (CameraAccessException e) {
- // Camera disabled by device policy.
- }
- if (c != null) {
- int facingCharacteristic = c.get(CameraCharacteristics.LENS_FACING);
- if (facingCharacteristic == CameraCharacteristics.LENS_FACING_FRONT) {
- mFrontFacingCameraId = cameraIds[i];
- } else if (facingCharacteristic == CameraCharacteristics.LENS_FACING_BACK) {
- mRearFacingCameraId = cameraIds[i];
- }
- }
- }
-
- mIsInitialized = true;
- Log.v(this, "initializeCameraList : done");
- }
-
- public void addCameraSelectionListener(Listener listener) {
- if (listener != null) {
- mCameraSelectionListeners.add(listener);
- }
- }
-
- public void removeCameraSelectionListener(Listener listener) {
- if (listener != null) {
- mCameraSelectionListeners.remove(listener);
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallContactInteractions.java b/InCallUI/src/com/android/incallui/InCallContactInteractions.java
deleted file mode 100644
index 88070fe379283f81821951ed64f31616ad8f5166..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallContactInteractions.java
+++ /dev/null
@@ -1,399 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.annotations.VisibleForTesting;
-
-import android.content.Context;
-import android.location.Address;
-import android.text.TextUtils;
-import android.text.format.DateFormat;
-import android.util.Pair;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ArrayAdapter;
-import android.widget.ImageView;
-import android.widget.ListAdapter;
-import android.widget.RelativeLayout;
-import android.widget.RelativeLayout.LayoutParams;
-import android.widget.TextView;
-
-import com.android.dialer.R;
-
-import java.text.ParseException;
-import java.text.SimpleDateFormat;
-import java.util.ArrayList;
-import java.util.Calendar;
-import java.util.Date;
-import java.util.List;
-import java.util.Locale;
-
-/**
- * Wrapper class for objects that are used in generating the context about the contact in the InCall
- * screen.
- *
- * This handles generating the appropriate resource for the ListAdapter based on whether the contact
- * is a business contact or not and logic for the manipulation of data for the call context.
- */
-public class InCallContactInteractions {
- private static final String TAG = InCallContactInteractions.class.getSimpleName();
-
- private Context mContext;
- private InCallContactInteractionsListAdapter mListAdapter;
- private boolean mIsBusiness;
- private View mBusinessHeaderView;
- private LayoutInflater mInflater;
-
- public InCallContactInteractions(Context context, boolean isBusiness) {
- mContext = context;
- mInflater = (LayoutInflater)
- context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- switchContactType(isBusiness);
- }
-
- public InCallContactInteractionsListAdapter getListAdapter() {
- return mListAdapter;
- }
-
- /**
- * Switches the "isBusiness" value, if applicable. Recreates the list adapter with the resource
- * corresponding to the new isBusiness value if the "isBusiness" value is switched.
- *
- * @param isBusiness Whether or not the contact is a business.
- *
- * @return {@code true} if a new list adapter was created, {@code} otherwise.
- */
- public boolean switchContactType(boolean isBusiness) {
- if (mIsBusiness != isBusiness || mListAdapter == null) {
- mIsBusiness = isBusiness;
- mListAdapter = new InCallContactInteractionsListAdapter(mContext,
- mIsBusiness ? R.layout.business_context_info_list_item
- : R.layout.person_context_info_list_item);
- return true;
- }
- return false;
- }
-
- public View getBusinessListHeaderView() {
- if (mBusinessHeaderView == null) {
- mBusinessHeaderView = mInflater.inflate(
- R.layout.business_contact_context_list_header, null);
- }
- return mBusinessHeaderView;
- }
-
- public void setBusinessInfo(Address address, float distance,
- List> openingHours) {
- mListAdapter.clear();
- List info = new ArrayList();
-
- // Hours of operation
- if (openingHours != null) {
- BusinessContextInfo hoursInfo = constructHoursInfo(openingHours);
- if (hoursInfo != null) {
- info.add(hoursInfo);
- }
- }
-
- // Location information
- if (address != null) {
- BusinessContextInfo locationInfo = constructLocationInfo(address, distance);
- info.add(locationInfo);
- }
-
- mListAdapter.addAll(info);
- }
-
- /**
- * Construct a BusinessContextInfo object containing hours of operation information.
- * The format is:
- * [Open now/Closed now]
- * [Hours]
- *
- * @param openingHours
- * @return BusinessContextInfo object with the schedule icon, the heading set to whether the
- * business is open or not and the details set to the hours of operation.
- */
- private BusinessContextInfo constructHoursInfo(List> openingHours) {
- try {
- return constructHoursInfo(Calendar.getInstance(), openingHours);
- } catch (Exception e) {
- // Catch all exceptions here because we don't want any crashes if something goes wrong.
- Log.e(TAG, "Error constructing hours info: ", e);
- }
- return null;
- }
-
- /**
- * Pass in arbitrary current calendar time.
- */
- @VisibleForTesting
- BusinessContextInfo constructHoursInfo(Calendar currentTime,
- List> openingHours) {
- if (currentTime == null || openingHours == null || openingHours.size() == 0) {
- return null;
- }
-
- BusinessContextInfo hoursInfo = new BusinessContextInfo();
- hoursInfo.iconId = R.drawable.ic_schedule_white_24dp;
-
- boolean isOpenNow = false;
- // This variable records which interval the current time is after. 0 denotes none of the
- // intervals, 1 after the first interval, etc. It is also the index of the interval the
- // current time is in (if open) or the next interval (if closed).
- int afterInterval = 0;
- // This variable counts the number of time intervals in today's opening hours.
- int todaysIntervalCount = 0;
-
- for (Pair hours : openingHours) {
- if (hours.first.compareTo(currentTime) <= 0
- && currentTime.compareTo(hours.second) < 0) {
- // If the current time is on or after the opening time and strictly before the
- // closing time, then this business is open.
- isOpenNow = true;
- }
-
- if (currentTime.get(Calendar.DAY_OF_YEAR) == hours.first.get(Calendar.DAY_OF_YEAR)) {
- todaysIntervalCount += 1;
- }
-
- if (currentTime.compareTo(hours.second) > 0) {
- // This assumes that the list of intervals is sorted by time.
- afterInterval += 1;
- }
- }
-
- hoursInfo.heading = isOpenNow ? mContext.getString(R.string.open_now)
- : mContext.getString(R.string.closed_now);
-
- /*
- * The following logic determines what to display in various cases for hours of operation.
- *
- * - Display all intervals if open now and number of intervals is <=2.
- * - Display next closing time if open now and number of intervals is >2.
- * - Display next opening time if currently closed but opens later today.
- * - Display last time it closed today if closed now and tomorrow's hours are unknown.
- * - Display tomorrow's first open time if closed today and tomorrow's hours are known.
- *
- * NOTE: The logic below assumes that the intervals are sorted by ascending time. Possible
- * TODO to modify the logic above and ensure this is true.
- */
- if (isOpenNow) {
- if (todaysIntervalCount == 1) {
- hoursInfo.detail = getTimeSpanStringForHours(openingHours.get(0));
- } else if (todaysIntervalCount == 2) {
- hoursInfo.detail = mContext.getString(
- R.string.opening_hours,
- getTimeSpanStringForHours(openingHours.get(0)),
- getTimeSpanStringForHours(openingHours.get(1)));
- } else if (afterInterval < openingHours.size()) {
- // This check should not be necessary since if it is currently open, we should not
- // be after the last interval, but just in case, we don't want to crash.
- hoursInfo.detail = mContext.getString(
- R.string.closes_today_at,
- getFormattedTimeForCalendar(openingHours.get(afterInterval).second));
- }
- } else { // Currently closed
- final int lastIntervalToday = todaysIntervalCount - 1;
- if (todaysIntervalCount == 0) { // closed today
- hoursInfo.detail = mContext.getString(
- R.string.opens_tomorrow_at,
- getFormattedTimeForCalendar(openingHours.get(0).first));
- } else if (currentTime.after(openingHours.get(lastIntervalToday).second)) {
- // Passed hours for today
- if (todaysIntervalCount < openingHours.size()) {
- // If all of today's intervals are exhausted, assume the next are tomorrow's.
- hoursInfo.detail = mContext.getString(
- R.string.opens_tomorrow_at,
- getFormattedTimeForCalendar(
- openingHours.get(todaysIntervalCount).first));
- } else {
- // Grab the last time it was open today.
- hoursInfo.detail = mContext.getString(
- R.string.closed_today_at,
- getFormattedTimeForCalendar(
- openingHours.get(lastIntervalToday).second));
- }
- } else if (afterInterval < openingHours.size()) {
- // This check should not be necessary since if it is currently before the last
- // interval, afterInterval should be less than the count of intervals, but just in
- // case, we don't want to crash.
- hoursInfo.detail = mContext.getString(
- R.string.opens_today_at,
- getFormattedTimeForCalendar(openingHours.get(afterInterval).first));
- }
- }
-
- return hoursInfo;
- }
-
- String getFormattedTimeForCalendar(Calendar calendar) {
- return DateFormat.getTimeFormat(mContext).format(calendar.getTime());
- }
-
- String getTimeSpanStringForHours(Pair hours) {
- return mContext.getString(R.string.open_time_span,
- getFormattedTimeForCalendar(hours.first),
- getFormattedTimeForCalendar(hours.second));
- }
-
- /**
- * Construct a BusinessContextInfo object with the location information of the business.
- * The format is:
- * [Straight line distance in miles or kilometers]
- * [Address without state/country/etc.]
- *
- * @param address An Address object containing address details of the business
- * @param distance The distance to the location in meters
- * @return A BusinessContextInfo object with the location icon, the heading as the distance to
- * the business and the details containing the address.
- */
- private BusinessContextInfo constructLocationInfo(Address address, float distance) {
- return constructLocationInfo(Locale.getDefault(), address, distance);
- }
-
- @VisibleForTesting
- BusinessContextInfo constructLocationInfo(Locale locale, Address address,
- float distance) {
- if (address == null) {
- return null;
- }
-
- BusinessContextInfo locationInfo = new BusinessContextInfo();
- locationInfo.iconId = R.drawable.ic_location_on_white_24dp;
- if (distance != DistanceHelper.DISTANCE_NOT_FOUND) {
- //TODO: add a setting to allow the user to select "KM" or "MI" as their distance units.
- if (Locale.US.equals(locale)) {
- locationInfo.heading = mContext.getString(R.string.distance_imperial_away,
- distance * DistanceHelper.MILES_PER_METER);
- } else {
- locationInfo.heading = mContext.getString(R.string.distance_metric_away,
- distance * DistanceHelper.KILOMETERS_PER_METER);
- }
- }
- if (address.getLocality() != null) {
- locationInfo.detail = mContext.getString(
- R.string.display_address,
- address.getAddressLine(0),
- address.getLocality());
- } else {
- locationInfo.detail = address.getAddressLine(0);
- }
- return locationInfo;
- }
-
- /**
- * Get the appropriate title for the context.
- * @return The "Business info" title for a business contact and the "Recent messages" title for
- * personal contacts.
- */
- public String getContactContextTitle() {
- return mIsBusiness
- ? mContext.getResources().getString(R.string.business_contact_context_title)
- : mContext.getResources().getString(R.string.person_contact_context_title);
- }
-
- public static abstract class ContactContextInfo {
- public abstract void bindView(View listItem);
- }
-
- public static class BusinessContextInfo extends ContactContextInfo {
- int iconId;
- String heading;
- String detail;
-
- @Override
- public void bindView(View listItem) {
- ImageView imageView = (ImageView) listItem.findViewById(R.id.icon);
- TextView headingTextView = (TextView) listItem.findViewById(R.id.heading);
- TextView detailTextView = (TextView) listItem.findViewById(R.id.detail);
-
- if (this.iconId == 0 || (this.heading == null && this.detail == null)) {
- return;
- }
-
- imageView.setImageDrawable(listItem.getContext().getDrawable(this.iconId));
-
- headingTextView.setText(this.heading);
- headingTextView.setVisibility(TextUtils.isEmpty(this.heading)
- ? View.GONE : View.VISIBLE);
-
- detailTextView.setText(this.detail);
- detailTextView.setVisibility(TextUtils.isEmpty(this.detail)
- ? View.GONE : View.VISIBLE);
-
- }
- }
-
- public static class PersonContextInfo extends ContactContextInfo {
- boolean isIncoming;
- String message;
- String detail;
-
- @Override
- public void bindView(View listItem) {
- TextView messageTextView = (TextView) listItem.findViewById(R.id.message);
- TextView detailTextView = (TextView) listItem.findViewById(R.id.detail);
-
- if (this.message == null || this.detail == null) {
- return;
- }
-
- messageTextView.setBackgroundResource(this.isIncoming ?
- R.drawable.incoming_sms_background : R.drawable.outgoing_sms_background);
- messageTextView.setText(this.message);
- LayoutParams messageLayoutParams = (LayoutParams) messageTextView.getLayoutParams();
- messageLayoutParams.addRule(this.isIncoming?
- RelativeLayout.ALIGN_PARENT_START : RelativeLayout.ALIGN_PARENT_END);
- messageTextView.setLayoutParams(messageLayoutParams);
-
- LayoutParams detailLayoutParams = (LayoutParams) detailTextView.getLayoutParams();
- detailLayoutParams.addRule(this.isIncoming ?
- RelativeLayout.ALIGN_PARENT_START : RelativeLayout.ALIGN_PARENT_END);
- detailTextView.setLayoutParams(detailLayoutParams);
- detailTextView.setText(this.detail);
- }
- }
-
- /**
- * A list adapter for call context information. We use the same adapter for both business and
- * contact context.
- */
- private class InCallContactInteractionsListAdapter extends ArrayAdapter {
- // The resource id of the list item layout.
- int mResId;
-
- public InCallContactInteractionsListAdapter(Context context, int resource) {
- super(context, resource);
- mResId = resource;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- View listItem = mInflater.inflate(mResId, null);
- ContactContextInfo item = getItem(position);
-
- if (item == null) {
- return listItem;
- }
-
- item.bindView(listItem);
- return listItem;
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallDateUtils.java b/InCallUI/src/com/android/incallui/InCallDateUtils.java
deleted file mode 100644
index 3401692ea99c3868a0e74712f8cadfe7ea0caf00..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallDateUtils.java
+++ /dev/null
@@ -1,53 +0,0 @@
-package com.android.incallui;
-
-import android.icu.text.MeasureFormat;
-import android.icu.text.MeasureFormat.FormatWidth;
-import android.icu.util.Measure;
-import android.icu.util.MeasureUnit;
-
-import java.util.ArrayList;
-import java.util.Locale;
-
-/**
- * Methods to parse time and date information in the InCallUi
- */
-public class InCallDateUtils {
-
- /**
- * Return given duration in a human-friendly format. For example, "4 minutes 3 seconds" or
- * "3 hours 1 second". Returns the hours, minutes and seconds in that order if they exist.
- */
- public static String formatDuration(long millis) {
- int hours = 0;
- int minutes = 0;
- int seconds = 0;
- int elapsedSeconds = (int) (millis / 1000);
- if (elapsedSeconds >= 3600) {
- hours = elapsedSeconds / 3600;
- elapsedSeconds -= hours * 3600;
- }
- if (elapsedSeconds >= 60) {
- minutes = elapsedSeconds / 60;
- elapsedSeconds -= minutes * 60;
- }
- seconds = elapsedSeconds;
-
- final ArrayList measures = new ArrayList();
- if (hours > 0) {
- measures.add(new Measure(hours, MeasureUnit.HOUR));
- }
- if (minutes > 0) {
- measures.add(new Measure(minutes, MeasureUnit.MINUTE));
- }
- if (seconds > 0) {
- measures.add(new Measure(seconds, MeasureUnit.SECOND));
- }
-
- if (measures.isEmpty()) {
- return "";
- } else {
- return MeasureFormat.getInstance(Locale.getDefault(), FormatWidth.WIDE)
- .formatMeasures(measures.toArray(new Measure[measures.size()]));
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallOrientationEventListener.java b/InCallUI/src/com/android/incallui/InCallOrientationEventListener.java
deleted file mode 100644
index 3cab6dc3bf947176e50ab0b2204a5dc9ac58b06f..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallOrientationEventListener.java
+++ /dev/null
@@ -1,178 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.content.res.Configuration;
-import android.view.OrientationEventListener;
-import android.hardware.SensorManager;
-import android.view.Surface;
-import android.content.pm.ActivityInfo;
-
-/**
- * This class listens to Orientation events and overrides onOrientationChanged which gets
- * invoked when an orientation change occurs. When that happens, we notify InCallUI registrants
- * of the change.
- */
-public class InCallOrientationEventListener extends OrientationEventListener {
-
- /**
- * Screen orientation angles one of 0, 90, 180, 270, 360 in degrees.
- */
- public static int SCREEN_ORIENTATION_0 = 0;
- public static int SCREEN_ORIENTATION_90 = 90;
- public static int SCREEN_ORIENTATION_180 = 180;
- public static int SCREEN_ORIENTATION_270 = 270;
- public static int SCREEN_ORIENTATION_360 = 360;
-
- public static int FULL_SENSOR_SCREEN_ORIENTATION =
- ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR;
-
- public static int NO_SENSOR_SCREEN_ORIENTATION =
- ActivityInfo.SCREEN_ORIENTATION_NOSENSOR;
-
- /**
- * This is to identify dead zones where we won't notify others of orientation changed.
- * Say for e.g our threshold is x degrees. We will only notify UI when our current rotation is
- * within x degrees right or left of the screen orientation angles. If it's not within those
- * ranges, we return SCREEN_ORIENTATION_UNKNOWN and ignore it.
- */
- private static int SCREEN_ORIENTATION_UNKNOWN = -1;
-
- // Rotation threshold is 10 degrees. So if the rotation angle is within 10 degrees of any of
- // the above angles, we will notify orientation changed.
- private static int ROTATION_THRESHOLD = 10;
-
-
- /**
- * Cache the current rotation of the device.
- */
- private static int sCurrentOrientation = SCREEN_ORIENTATION_0;
- private boolean mEnabled = false;
-
- public InCallOrientationEventListener(Context context) {
- super(context);
- }
-
- /**
- * Handles changes in device orientation. Notifies InCallPresenter of orientation changes.
- *
- * Note that this API receives sensor rotation in degrees as a param and we convert that to
- * one of our screen orientation constants - (one of: {@link SCREEN_ORIENTATION_0},
- * {@link SCREEN_ORIENTATION_90}, {@link SCREEN_ORIENTATION_180},
- * {@link SCREEN_ORIENTATION_270}).
- *
- * @param rotation The new device sensor rotation in degrees
- */
- @Override
- public void onOrientationChanged(int rotation) {
- if (rotation == OrientationEventListener.ORIENTATION_UNKNOWN) {
- return;
- }
-
- final int orientation = toScreenOrientation(rotation);
-
- if (orientation != SCREEN_ORIENTATION_UNKNOWN && sCurrentOrientation != orientation) {
- sCurrentOrientation = orientation;
- InCallPresenter.getInstance().onDeviceOrientationChange(sCurrentOrientation);
- }
- }
-
- /**
- * Enables the OrientationEventListener and notifies listeners of current orientation if
- * notify flag is true
- * @param notify true or false. Notify device orientation changed if true.
- */
- public void enable(boolean notify) {
- if (mEnabled) {
- Log.v(this, "enable: Orientation listener is already enabled. Ignoring...");
- return;
- }
-
- super.enable();
- mEnabled = true;
- if (notify) {
- InCallPresenter.getInstance().onDeviceOrientationChange(sCurrentOrientation);
- }
- }
-
- /**
- * Enables the OrientationEventListener with notify flag defaulting to false.
- */
- public void enable() {
- enable(false);
- }
-
- /**
- * Disables the OrientationEventListener.
- */
- public void disable() {
- if (!mEnabled) {
- Log.v(this, "enable: Orientation listener is already disabled. Ignoring...");
- return;
- }
-
- mEnabled = false;
- super.disable();
- }
-
- /**
- * Returns true the OrientationEventListener is enabled, false otherwise.
- */
- public boolean isEnabled() {
- return mEnabled;
- }
-
- /**
- * Converts sensor rotation in degrees to screen orientation constants.
- * @param rotation sensor rotation angle in degrees
- * @return Screen orientation angle in degrees (0, 90, 180, 270). Returns -1 for degrees not
- * within threshold to identify zones where orientation change should not be trigerred.
- */
- private int toScreenOrientation(int rotation) {
- // Sensor orientation 90 is equivalent to screen orientation 270 and vice versa. This
- // function returns the screen orientation. So we convert sensor rotation 90 to 270 and
- // vice versa here.
- if (isInLeftRange(rotation, SCREEN_ORIENTATION_360, ROTATION_THRESHOLD) ||
- isInRightRange(rotation, SCREEN_ORIENTATION_0, ROTATION_THRESHOLD)) {
- return SCREEN_ORIENTATION_0;
- } else if (isWithinThreshold(rotation, SCREEN_ORIENTATION_90, ROTATION_THRESHOLD)) {
- return SCREEN_ORIENTATION_270;
- } else if (isWithinThreshold(rotation, SCREEN_ORIENTATION_180, ROTATION_THRESHOLD)) {
- return SCREEN_ORIENTATION_180;
- } else if (isWithinThreshold(rotation, SCREEN_ORIENTATION_270, ROTATION_THRESHOLD)) {
- return SCREEN_ORIENTATION_90;
- }
- return SCREEN_ORIENTATION_UNKNOWN;
- }
-
- private static boolean isWithinRange(int value, int begin, int end) {
- return value >= begin && value < end;
- }
-
- private static boolean isWithinThreshold(int value, int center, int threshold) {
- return isWithinRange(value, center - threshold, center + threshold);
- }
-
- private static boolean isInLeftRange(int value, int center, int threshold) {
- return isWithinRange(value, center - threshold, center);
- }
-
- private static boolean isInRightRange(int value, int center, int threshold) {
- return isWithinRange(value, center, center + threshold);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallPresenter.java b/InCallUI/src/com/android/incallui/InCallPresenter.java
deleted file mode 100644
index 0103f61ed00ef201b609bc840fead6cc74d75652..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallPresenter.java
+++ /dev/null
@@ -1,1938 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import android.app.ActivityManager.TaskDescription;
-import android.app.FragmentManager;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.database.ContentObserver;
-import android.graphics.Point;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.SystemClock;
-import android.provider.CallLog;
-import android.telecom.DisconnectCause;
-import android.telecom.PhoneAccount;
-import android.telecom.PhoneAccountHandle;
-import android.telecom.TelecomManager;
-import android.telecom.VideoProfile;
-import android.telephony.PhoneStateListener;
-import android.telephony.TelephonyManager;
-import android.text.TextUtils;
-import android.view.View;
-import android.view.Window;
-import android.view.WindowManager;
-
-import com.android.contacts.common.GeoUtil;
-import com.android.contacts.common.compat.CallSdkCompat;
-import com.android.contacts.common.compat.CompatUtils;
-import com.android.contacts.common.compat.telecom.TelecomManagerCompat;
-import com.android.contacts.common.interactions.TouchPointManager;
-import com.android.contacts.common.testing.NeededForTesting;
-import com.android.contacts.common.util.MaterialColorMapUtils.MaterialPalette;
-import com.android.dialer.R;
-import com.android.dialer.calllog.CallLogAsyncTaskUtil;
-import com.android.dialer.calllog.CallLogAsyncTaskUtil.OnCallLogQueryFinishedListener;
-import com.android.dialer.database.FilteredNumberAsyncQueryHandler;
-import com.android.dialer.database.FilteredNumberAsyncQueryHandler.OnCheckBlockedListener;
-import com.android.dialer.filterednumber.FilteredNumbersUtil;
-import com.android.dialer.logging.InteractionEvent;
-import com.android.dialer.logging.Logger;
-import com.android.dialer.util.TelecomUtil;
-import com.android.incallui.spam.SpamCallListListener;
-import com.android.incallui.util.TelecomCallUtil;
-import com.android.incalluibind.ObjectFactory;
-
-import java.util.Collections;
-import java.util.List;
-import java.util.Locale;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.CopyOnWriteArrayList;
-import java.util.concurrent.atomic.AtomicBoolean;
-
-/**
- * Takes updates from the CallList and notifies the InCallActivity (UI)
- * of the changes.
- * Responsible for starting the activity for a new call and finishing the activity when all calls
- * are disconnected.
- * Creates and manages the in-call state and provides a listener pattern for the presenters
- * that want to listen in on the in-call state changes.
- * TODO: This class has become more of a state machine at this point. Consider renaming.
- */
-public class InCallPresenter implements CallList.Listener,
- CircularRevealFragment.OnCircularRevealCompleteListener,
- InCallVideoCallCallbackNotifier.SessionModificationListener {
-
- private static final String EXTRA_FIRST_TIME_SHOWN =
- "com.android.incallui.intent.extra.FIRST_TIME_SHOWN";
-
- private static final long BLOCK_QUERY_TIMEOUT_MS = 1000;
-
- private static final Bundle EMPTY_EXTRAS = new Bundle();
-
- private static InCallPresenter sInCallPresenter;
-
- /**
- * ConcurrentHashMap constructor params: 8 is initial table size, 0.9f is
- * load factor before resizing, 1 means we only expect a single thread to
- * access the map so make only a single shard
- */
- private final Set mListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final List mIncomingCallListeners = new CopyOnWriteArrayList<>();
- private final Set mDetailsListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final Set mCanAddCallListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final Set mInCallUiListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final Set mOrientationListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final Set mInCallEventListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
-
- private AudioModeProvider mAudioModeProvider;
- private StatusBarNotifier mStatusBarNotifier;
- private ExternalCallNotifier mExternalCallNotifier;
- private ContactInfoCache mContactInfoCache;
- private Context mContext;
- private CallList mCallList;
- private ExternalCallList mExternalCallList;
- private InCallActivity mInCallActivity;
- private InCallState mInCallState = InCallState.NO_CALLS;
- private ProximitySensor mProximitySensor;
- private boolean mServiceConnected = false;
- private boolean mAccountSelectionCancelled = false;
- private InCallCameraManager mInCallCameraManager = null;
- private AnswerPresenter mAnswerPresenter = new AnswerPresenter();
- private FilteredNumberAsyncQueryHandler mFilteredQueryHandler;
- private CallList.Listener mSpamCallListListener;
-
- /**
- * Whether or not we are currently bound and waiting for Telecom to send us a new call.
- */
- private boolean mBoundAndWaitingForOutgoingCall;
-
- /**
- * If there is no actual call currently in the call list, this will be used as a fallback
- * to determine the theme color for InCallUI.
- */
- private PhoneAccountHandle mPendingPhoneAccountHandle;
-
- /**
- * Determines if the InCall UI is in fullscreen mode or not.
- */
- private boolean mIsFullScreen = false;
-
- private final android.telecom.Call.Callback mCallCallback = new android.telecom.Call.Callback() {
- @Override
- public void onPostDialWait(android.telecom.Call telecomCall,
- String remainingPostDialSequence) {
- final Call call = mCallList.getCallByTelecomCall(telecomCall);
- if (call == null) {
- Log.w(this, "Call not found in call list: " + telecomCall);
- return;
- }
- onPostDialCharWait(call.getId(), remainingPostDialSequence);
- }
-
- @Override
- public void onDetailsChanged(android.telecom.Call telecomCall,
- android.telecom.Call.Details details) {
- final Call call = mCallList.getCallByTelecomCall(telecomCall);
- if (call == null) {
- Log.w(this, "Call not found in call list: " + telecomCall);
- return;
- }
- for (InCallDetailsListener listener : mDetailsListeners) {
- listener.onDetailsChanged(call, details);
- }
- }
-
- @Override
- public void onConferenceableCallsChanged(android.telecom.Call telecomCall,
- List conferenceableCalls) {
- Log.i(this, "onConferenceableCallsChanged: " + telecomCall);
- onDetailsChanged(telecomCall, telecomCall.getDetails());
- }
- };
-
- private PhoneStateListener mPhoneStateListener = new PhoneStateListener() {
- public void onCallStateChanged(int state, String incomingNumber) {
- if (state == TelephonyManager.CALL_STATE_RINGING) {
- if (FilteredNumbersUtil.hasRecentEmergencyCall(mContext)) {
- return;
- }
- // Check if the number is blocked, to silence the ringer.
- String countryIso = GeoUtil.getCurrentCountryIso(mContext);
- mFilteredQueryHandler.isBlockedNumber(
- mOnCheckBlockedListener, incomingNumber, countryIso);
- }
- }
- };
-
- private final OnCheckBlockedListener mOnCheckBlockedListener = new OnCheckBlockedListener() {
- @Override
- public void onCheckComplete(final Integer id) {
- if (id != null) {
- // Silence the ringer now to prevent ringing and vibration before the call is
- // terminated when Telecom attempts to add it.
- TelecomUtil.silenceRinger(mContext);
- }
- }
- };
-
- /**
- * Observes the CallLog to delete the call log entry for the blocked call after it is added.
- * Times out if too much time has passed.
- */
- private class BlockedNumberContentObserver extends ContentObserver {
- private static final int TIMEOUT_MS = 5000;
-
- private Handler mHandler;
- private String mNumber;
- private long mTimeAddedMs;
-
- private Runnable mTimeoutRunnable = new Runnable() {
- @Override
- public void run() {
- unregister();
- }
- };
-
- public BlockedNumberContentObserver(Handler handler, String number, long timeAddedMs) {
- super(handler);
-
- mHandler = handler;
- mNumber = number;
- mTimeAddedMs = timeAddedMs;
- }
-
- @Override
- public void onChange(boolean selfChange) {
- CallLogAsyncTaskUtil.deleteBlockedCall(mContext, mNumber, mTimeAddedMs,
- new OnCallLogQueryFinishedListener() {
- @Override
- public void onQueryFinished(boolean hasEntry) {
- if (mContext != null && hasEntry) {
- unregister();
- }
- }
- });
- }
-
- public void register() {
- if (mContext != null) {
- mContext.getContentResolver().registerContentObserver(
- CallLog.CONTENT_URI, true, this);
- mHandler.postDelayed(mTimeoutRunnable, TIMEOUT_MS);
- }
- }
-
- private void unregister() {
- if (mContext != null) {
- mHandler.removeCallbacks(mTimeoutRunnable);
- mContext.getContentResolver().unregisterContentObserver(this);
- }
- }
- };
-
- /**
- * Is true when the activity has been previously started. Some code needs to know not just if
- * the activity is currently up, but if it had been previously shown in foreground for this
- * in-call session (e.g., StatusBarNotifier). This gets reset when the session ends in the
- * tear-down method.
- */
- private boolean mIsActivityPreviouslyStarted = false;
-
- /**
- * Whether or not InCallService is bound to Telecom.
- */
- private boolean mServiceBound = false;
-
- /**
- * When configuration changes Android kills the current activity and starts a new one.
- * The flag is used to check if full clean up is necessary (activity is stopped and new
- * activity won't be started), or if a new activity will be started right after the current one
- * is destroyed, and therefore no need in release all resources.
- */
- private boolean mIsChangingConfigurations = false;
-
- /** Display colors for the UI. Consists of a primary color and secondary (darker) color */
- private MaterialPalette mThemeColors;
-
- private TelecomManager mTelecomManager;
- private TelephonyManager mTelephonyManager;
-
- public static synchronized InCallPresenter getInstance() {
- if (sInCallPresenter == null) {
- sInCallPresenter = new InCallPresenter();
- }
- return sInCallPresenter;
- }
-
- @NeededForTesting
- static synchronized void setInstance(InCallPresenter inCallPresenter) {
- sInCallPresenter = inCallPresenter;
- }
-
- public InCallState getInCallState() {
- return mInCallState;
- }
-
- public CallList getCallList() {
- return mCallList;
- }
-
- public void setUp(Context context,
- CallList callList,
- ExternalCallList externalCallList,
- AudioModeProvider audioModeProvider,
- StatusBarNotifier statusBarNotifier,
- ExternalCallNotifier externalCallNotifier,
- ContactInfoCache contactInfoCache,
- ProximitySensor proximitySensor) {
- if (mServiceConnected) {
- Log.i(this, "New service connection replacing existing one.");
- // retain the current resources, no need to create new ones.
- Preconditions.checkState(context == mContext);
- Preconditions.checkState(callList == mCallList);
- Preconditions.checkState(audioModeProvider == mAudioModeProvider);
- return;
- }
-
- Preconditions.checkNotNull(context);
- mContext = context;
-
- mContactInfoCache = contactInfoCache;
-
- mStatusBarNotifier = statusBarNotifier;
- mExternalCallNotifier = externalCallNotifier;
- addListener(mStatusBarNotifier);
-
- mAudioModeProvider = audioModeProvider;
-
- mProximitySensor = proximitySensor;
- addListener(mProximitySensor);
-
- addIncomingCallListener(mAnswerPresenter);
- addInCallUiListener(mAnswerPresenter);
-
- mCallList = callList;
- mExternalCallList = externalCallList;
- externalCallList.addExternalCallListener(mExternalCallNotifier);
-
- // This only gets called by the service so this is okay.
- mServiceConnected = true;
-
- // The final thing we do in this set up is add ourselves as a listener to CallList. This
- // will kick off an update and the whole process can start.
- mCallList.addListener(this);
-
- // Create spam call list listener and add it to the list of listeners
- mSpamCallListListener = new SpamCallListListener(context);
- mCallList.addListener(mSpamCallListListener);
-
- VideoPauseController.getInstance().setUp(this);
- InCallVideoCallCallbackNotifier.getInstance().addSessionModificationListener(this);
-
- mFilteredQueryHandler = new FilteredNumberAsyncQueryHandler(context.getContentResolver());
- mTelephonyManager = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
- mTelephonyManager.listen(mPhoneStateListener, PhoneStateListener.LISTEN_CALL_STATE);
- mCallList.setExtendedCallInfoService(
- com.android.dialerbind.ObjectFactory.newExtendedCallInfoService(context));
-
- Log.d(this, "Finished InCallPresenter.setUp");
- }
-
- /**
- * Called when the telephony service has disconnected from us. This will happen when there are
- * no more active calls. However, we may still want to continue showing the UI for
- * certain cases like showing "Call Ended".
- * What we really want is to wait for the activity and the service to both disconnect before we
- * tear things down. This method sets a serviceConnected boolean and calls a secondary method
- * that performs the aforementioned logic.
- */
- public void tearDown() {
- Log.d(this, "tearDown");
- mCallList.clearOnDisconnect();
-
- mServiceConnected = false;
- attemptCleanup();
-
- mTelephonyManager.listen(mPhoneStateListener, PhoneStateListener.LISTEN_NONE);
- VideoPauseController.getInstance().tearDown();
- InCallVideoCallCallbackNotifier.getInstance().removeSessionModificationListener(this);
- }
-
- private void attemptFinishActivity() {
- final boolean doFinish = (mInCallActivity != null && isActivityStarted());
- Log.i(this, "Hide in call UI: " + doFinish);
- if (doFinish) {
- mInCallActivity.setExcludeFromRecents(true);
- mInCallActivity.finish();
-
- if (mAccountSelectionCancelled) {
- // This finish is a result of account selection cancellation
- // do not include activity ending transition
- mInCallActivity.overridePendingTransition(0, 0);
- }
- }
- }
-
- /**
- * Called when the UI begins, and starts the callstate callbacks if necessary.
- */
- public void setActivity(InCallActivity inCallActivity) {
- if (inCallActivity == null) {
- throw new IllegalArgumentException("registerActivity cannot be called with null");
- }
- if (mInCallActivity != null && mInCallActivity != inCallActivity) {
- Log.w(this, "Setting a second activity before destroying the first.");
- }
- updateActivity(inCallActivity);
- }
-
- /**
- * Called when the UI ends. Attempts to tear down everything if necessary. See
- * {@link #tearDown()} for more insight on the tear-down process.
- */
- public void unsetActivity(InCallActivity inCallActivity) {
- if (inCallActivity == null) {
- throw new IllegalArgumentException("unregisterActivity cannot be called with null");
- }
- if (mInCallActivity == null) {
- Log.i(this, "No InCallActivity currently set, no need to unset.");
- return;
- }
- if (mInCallActivity != inCallActivity) {
- Log.w(this, "Second instance of InCallActivity is trying to unregister when another"
- + " instance is active. Ignoring.");
- return;
- }
- updateActivity(null);
- }
-
- /**
- * Updates the current instance of {@link InCallActivity} with the provided one. If a
- * {@code null} activity is provided, it means that the activity was finished and we should
- * attempt to cleanup.
- */
- private void updateActivity(InCallActivity inCallActivity) {
- boolean updateListeners = false;
- boolean doAttemptCleanup = false;
-
- if (inCallActivity != null) {
- if (mInCallActivity == null) {
- updateListeners = true;
- Log.i(this, "UI Initialized");
- } else {
- // since setActivity is called onStart(), it can be called multiple times.
- // This is fine and ignorable, but we do not want to update the world every time
- // this happens (like going to/from background) so we do not set updateListeners.
- }
-
- mInCallActivity = inCallActivity;
- mInCallActivity.setExcludeFromRecents(false);
-
- // By the time the UI finally comes up, the call may already be disconnected.
- // If that's the case, we may need to show an error dialog.
- if (mCallList != null && mCallList.getDisconnectedCall() != null) {
- maybeShowErrorDialogOnDisconnect(mCallList.getDisconnectedCall());
- }
-
- // When the UI comes up, we need to first check the in-call state.
- // If we are showing NO_CALLS, that means that a call probably connected and
- // then immediately disconnected before the UI was able to come up.
- // If we dont have any calls, start tearing down the UI instead.
- // NOTE: This code relies on {@link #mInCallActivity} being set so we run it after
- // it has been set.
- if (mInCallState == InCallState.NO_CALLS) {
- Log.i(this, "UI Initialized, but no calls left. shut down.");
- attemptFinishActivity();
- return;
- }
- } else {
- Log.i(this, "UI Destroyed");
- updateListeners = true;
- mInCallActivity = null;
-
- // We attempt cleanup for the destroy case but only after we recalculate the state
- // to see if we need to come back up or stay shut down. This is why we do the
- // cleanup after the call to onCallListChange() instead of directly here.
- doAttemptCleanup = true;
- }
-
- // Messages can come from the telephony layer while the activity is coming up
- // and while the activity is going down. So in both cases we need to recalculate what
- // state we should be in after they complete.
- // Examples: (1) A new incoming call could come in and then get disconnected before
- // the activity is created.
- // (2) All calls could disconnect and then get a new incoming call before the
- // activity is destroyed.
- //
- // b/1122139 - We previously had a check for mServiceConnected here as well, but there are
- // cases where we need to recalculate the current state even if the service in not
- // connected. In particular the case where startOrFinish() is called while the app is
- // already finish()ing. In that case, we skip updating the state with the knowledge that
- // we will check again once the activity has finished. That means we have to recalculate the
- // state here even if the service is disconnected since we may not have finished a state
- // transition while finish()ing.
- if (updateListeners) {
- onCallListChange(mCallList);
- }
-
- if (doAttemptCleanup) {
- attemptCleanup();
- }
- }
-
- private boolean mAwaitingCallListUpdate = false;
-
- public void onBringToForeground(boolean showDialpad) {
- Log.i(this, "Bringing UI to foreground.");
- bringToForeground(showDialpad);
- }
-
- public void onCallAdded(final android.telecom.Call call) {
- LatencyReport latencyReport = new LatencyReport(call);
- if (shouldAttemptBlocking(call)) {
- maybeBlockCall(call, latencyReport);
- } else {
- latencyReport.onCallBlockingDone();
- if (call.getDetails()
- .hasProperty(CallSdkCompat.Details.PROPERTY_IS_EXTERNAL_CALL)) {
- mExternalCallList.onCallAdded(call);
- } else {
- mCallList.onCallAdded(call, latencyReport);
- }
- }
-
- // Since a call has been added we are no longer waiting for Telecom to send us a call.
- setBoundAndWaitingForOutgoingCall(false, null);
- call.registerCallback(mCallCallback);
- }
-
- private boolean shouldAttemptBlocking(android.telecom.Call call) {
- if (call.getState() != android.telecom.Call.STATE_RINGING) {
- return false;
- }
- if (TelecomCallUtil.isEmergencyCall(call)) {
- Log.i(this, "Not attempting to block incoming emergency call");
- return false;
- }
- if (FilteredNumbersUtil.hasRecentEmergencyCall(mContext)) {
- Log.i(this, "Not attempting to block incoming call due to recent emergency call");
- return false;
- }
- if (call.getDetails().hasProperty(CallSdkCompat.Details.PROPERTY_IS_EXTERNAL_CALL)) {
- return false;
- }
-
- return true;
- }
-
- /**
- * Checks whether a call should be blocked, and blocks it if so. Otherwise, it adds the call
- * to the CallList so it can proceed as normal. There is a timeout, so if the function for
- * checking whether a function is blocked does not return in a reasonable time, we proceed
- * with adding the call anyways.
- */
- private void maybeBlockCall(final android.telecom.Call call,
- final LatencyReport latencyReport) {
- final String countryIso = GeoUtil.getCurrentCountryIso(mContext);
- final String number = TelecomCallUtil.getNumber(call);
- final long timeAdded = System.currentTimeMillis();
-
- // Though AtomicBoolean's can be scary, don't fear, as in this case it is only used on the
- // main UI thread. It is needed so we can change its value within different scopes, since
- // that cannot be done with a final boolean.
- final AtomicBoolean hasTimedOut = new AtomicBoolean(false);
-
- final Handler handler = new Handler();
-
- // Proceed if the query is slow; the call may still be blocked after the query returns.
- final Runnable runnable = new Runnable() {
- public void run() {
- hasTimedOut.set(true);
- latencyReport.onCallBlockingDone();
- mCallList.onCallAdded(call, latencyReport);
- }
- };
- handler.postDelayed(runnable, BLOCK_QUERY_TIMEOUT_MS);
-
- OnCheckBlockedListener onCheckBlockedListener = new OnCheckBlockedListener() {
- @Override
- public void onCheckComplete(final Integer id) {
- if (!hasTimedOut.get()) {
- handler.removeCallbacks(runnable);
- }
- if (id == null) {
- if (!hasTimedOut.get()) {
- latencyReport.onCallBlockingDone();
- mCallList.onCallAdded(call, latencyReport);
- }
- } else {
- Log.i(this, "Rejecting incoming call from blocked number");
- call.reject(false, null);
- Logger.logInteraction(InteractionEvent.CALL_BLOCKED);
-
- mFilteredQueryHandler.incrementFilteredCount(id);
-
- // Register observer to update the call log.
- // BlockedNumberContentObserver will unregister after successful log or timeout.
- BlockedNumberContentObserver contentObserver =
- new BlockedNumberContentObserver(new Handler(), number, timeAdded);
- contentObserver.register();
- }
- }
- };
-
- final boolean success = mFilteredQueryHandler.isBlockedNumber(
- onCheckBlockedListener, number, countryIso);
- if (!success) {
- Log.d(this, "checkForBlockedCall: invalid number, skipping block checking");
- if (!hasTimedOut.get()) {
- handler.removeCallbacks(runnable);
-
- latencyReport.onCallBlockingDone();
- mCallList.onCallAdded(call, latencyReport);
- }
- }
- }
-
- public void onCallRemoved(android.telecom.Call call) {
- if (call.getDetails()
- .hasProperty(CallSdkCompat.Details.PROPERTY_IS_EXTERNAL_CALL)) {
- mExternalCallList.onCallRemoved(call);
- } else {
- mCallList.onCallRemoved(call);
- call.unregisterCallback(mCallCallback);
- }
- }
-
- public void onCanAddCallChanged(boolean canAddCall) {
- for (CanAddCallListener listener : mCanAddCallListeners) {
- listener.onCanAddCallChanged(canAddCall);
- }
- }
-
- /**
- * Called when there is a change to the call list.
- * Sets the In-Call state for the entire in-call app based on the information it gets from
- * CallList. Dispatches the in-call state to all listeners. Can trigger the creation or
- * destruction of the UI based on the states that is calculates.
- */
- @Override
- public void onCallListChange(CallList callList) {
- if (mInCallActivity != null && mInCallActivity.getCallCardFragment() != null &&
- mInCallActivity.getCallCardFragment().isAnimating()) {
- mAwaitingCallListUpdate = true;
- return;
- }
- if (callList == null) {
- return;
- }
-
- mAwaitingCallListUpdate = false;
-
- InCallState newState = getPotentialStateFromCallList(callList);
- InCallState oldState = mInCallState;
- Log.d(this, "onCallListChange oldState= " + oldState + " newState=" + newState);
- newState = startOrFinishUi(newState);
- Log.d(this, "onCallListChange newState changed to " + newState);
-
- // Set the new state before announcing it to the world
- Log.i(this, "Phone switching state: " + oldState + " -> " + newState);
- mInCallState = newState;
-
- // notify listeners of new state
- for (InCallStateListener listener : mListeners) {
- Log.d(this, "Notify " + listener + " of state " + mInCallState.toString());
- listener.onStateChange(oldState, mInCallState, callList);
- }
-
- if (isActivityStarted()) {
- final boolean hasCall = callList.getActiveOrBackgroundCall() != null ||
- callList.getOutgoingCall() != null;
- mInCallActivity.dismissKeyguard(hasCall);
- }
- }
-
- /**
- * Called when there is a new incoming call.
- *
- * @param call
- */
- @Override
- public void onIncomingCall(Call call) {
- InCallState newState = startOrFinishUi(InCallState.INCOMING);
- InCallState oldState = mInCallState;
-
- Log.i(this, "Phone switching state: " + oldState + " -> " + newState);
- mInCallState = newState;
-
- for (IncomingCallListener listener : mIncomingCallListeners) {
- listener.onIncomingCall(oldState, mInCallState, call);
- }
- }
-
- @Override
- public void onUpgradeToVideo(Call call) {
- //NO-OP
- }
- /**
- * Called when a call becomes disconnected. Called everytime an existing call
- * changes from being connected (incoming/outgoing/active) to disconnected.
- */
- @Override
- public void onDisconnect(Call call) {
- maybeShowErrorDialogOnDisconnect(call);
-
- // We need to do the run the same code as onCallListChange.
- onCallListChange(mCallList);
-
- if (isActivityStarted()) {
- mInCallActivity.dismissKeyguard(false);
- }
-
- if (call.isEmergencyCall()) {
- FilteredNumbersUtil.recordLastEmergencyCallTime(mContext);
- }
- }
-
- @Override
- public void onUpgradeToVideoRequest(Call call, int videoState) {
- Log.d(this, "onUpgradeToVideoRequest call = " + call + " video state = " + videoState);
-
- if (call == null) {
- return;
- }
-
- call.setRequestedVideoState(videoState);
- }
-
- /**
- * Given the call list, return the state in which the in-call screen should be.
- */
- public InCallState getPotentialStateFromCallList(CallList callList) {
-
- InCallState newState = InCallState.NO_CALLS;
-
- if (callList == null) {
- return newState;
- }
- if (callList.getIncomingCall() != null) {
- newState = InCallState.INCOMING;
- } else if (callList.getWaitingForAccountCall() != null) {
- newState = InCallState.WAITING_FOR_ACCOUNT;
- } else if (callList.getPendingOutgoingCall() != null) {
- newState = InCallState.PENDING_OUTGOING;
- } else if (callList.getOutgoingCall() != null) {
- newState = InCallState.OUTGOING;
- } else if (callList.getActiveCall() != null ||
- callList.getBackgroundCall() != null ||
- callList.getDisconnectedCall() != null ||
- callList.getDisconnectingCall() != null) {
- newState = InCallState.INCALL;
- }
-
- if (newState == InCallState.NO_CALLS) {
- if (mBoundAndWaitingForOutgoingCall) {
- return InCallState.OUTGOING;
- }
- }
-
- return newState;
- }
-
- public boolean isBoundAndWaitingForOutgoingCall() {
- return mBoundAndWaitingForOutgoingCall;
- }
-
- public void setBoundAndWaitingForOutgoingCall(boolean isBound, PhoneAccountHandle handle) {
- // NOTE: It is possible for there to be a race and have handle become null before
- // the circular reveal starts. This should not cause any problems because CallCardFragment
- // should fallback to the actual call in the CallList at that point in time to determine
- // the theme color.
- Log.i(this, "setBoundAndWaitingForOutgoingCall: " + isBound);
- mBoundAndWaitingForOutgoingCall = isBound;
- mPendingPhoneAccountHandle = handle;
- if (isBound && mInCallState == InCallState.NO_CALLS) {
- mInCallState = InCallState.OUTGOING;
- }
- }
-
- @Override
- public void onCircularRevealComplete(FragmentManager fm) {
- if (mInCallActivity != null) {
- mInCallActivity.showCallCardFragment(true);
- mInCallActivity.getCallCardFragment().animateForNewOutgoingCall();
- CircularRevealFragment.endCircularReveal(mInCallActivity.getFragmentManager());
- }
- }
-
- public void onShrinkAnimationComplete() {
- if (mAwaitingCallListUpdate) {
- onCallListChange(mCallList);
- }
- }
-
- public void addIncomingCallListener(IncomingCallListener listener) {
- Preconditions.checkNotNull(listener);
- mIncomingCallListeners.add(listener);
- }
-
- public void removeIncomingCallListener(IncomingCallListener listener) {
- if (listener != null) {
- mIncomingCallListeners.remove(listener);
- }
- }
-
- public void addListener(InCallStateListener listener) {
- Preconditions.checkNotNull(listener);
- mListeners.add(listener);
- }
-
- public void removeListener(InCallStateListener listener) {
- if (listener != null) {
- mListeners.remove(listener);
- }
- }
-
- public void addDetailsListener(InCallDetailsListener listener) {
- Preconditions.checkNotNull(listener);
- mDetailsListeners.add(listener);
- }
-
- public void removeDetailsListener(InCallDetailsListener listener) {
- if (listener != null) {
- mDetailsListeners.remove(listener);
- }
- }
-
- public void addCanAddCallListener(CanAddCallListener listener) {
- Preconditions.checkNotNull(listener);
- mCanAddCallListeners.add(listener);
- }
-
- public void removeCanAddCallListener(CanAddCallListener listener) {
- if (listener != null) {
- mCanAddCallListeners.remove(listener);
- }
- }
-
- public void addOrientationListener(InCallOrientationListener listener) {
- Preconditions.checkNotNull(listener);
- mOrientationListeners.add(listener);
- }
-
- public void removeOrientationListener(InCallOrientationListener listener) {
- if (listener != null) {
- mOrientationListeners.remove(listener);
- }
- }
-
- public void addInCallEventListener(InCallEventListener listener) {
- Preconditions.checkNotNull(listener);
- mInCallEventListeners.add(listener);
- }
-
- public void removeInCallEventListener(InCallEventListener listener) {
- if (listener != null) {
- mInCallEventListeners.remove(listener);
- }
- }
-
- public ProximitySensor getProximitySensor() {
- return mProximitySensor;
- }
-
- public void handleAccountSelection(PhoneAccountHandle accountHandle, boolean setDefault) {
- if (mCallList != null) {
- Call call = mCallList.getWaitingForAccountCall();
- if (call != null) {
- String callId = call.getId();
- TelecomAdapter.getInstance().phoneAccountSelected(callId, accountHandle, setDefault);
- }
- }
- }
-
- public void cancelAccountSelection() {
- mAccountSelectionCancelled = true;
- if (mCallList != null) {
- Call call = mCallList.getWaitingForAccountCall();
- if (call != null) {
- String callId = call.getId();
- TelecomAdapter.getInstance().disconnectCall(callId);
- }
- }
- }
-
- /**
- * Hangs up any active or outgoing calls.
- */
- public void hangUpOngoingCall(Context context) {
- // By the time we receive this intent, we could be shut down and call list
- // could be null. Bail in those cases.
- if (mCallList == null) {
- if (mStatusBarNotifier == null) {
- // The In Call UI has crashed but the notification still stayed up. We should not
- // come to this stage.
- StatusBarNotifier.clearAllCallNotifications(context);
- }
- return;
- }
-
- Call call = mCallList.getOutgoingCall();
- if (call == null) {
- call = mCallList.getActiveOrBackgroundCall();
- }
-
- if (call != null) {
- TelecomAdapter.getInstance().disconnectCall(call.getId());
- call.setState(Call.State.DISCONNECTING);
- mCallList.onUpdate(call);
- }
- }
-
- /**
- * Answers any incoming call.
- */
- public void answerIncomingCall(Context context, int videoState) {
- // By the time we receive this intent, we could be shut down and call list
- // could be null. Bail in those cases.
- if (mCallList == null) {
- StatusBarNotifier.clearAllCallNotifications(context);
- return;
- }
-
- Call call = mCallList.getIncomingCall();
- if (call != null) {
- TelecomAdapter.getInstance().answerCall(call.getId(), videoState);
- showInCall(false, false/* newOutgoingCall */);
- }
- }
-
- /**
- * Declines any incoming call.
- */
- public void declineIncomingCall(Context context) {
- // By the time we receive this intent, we could be shut down and call list
- // could be null. Bail in those cases.
- if (mCallList == null) {
- StatusBarNotifier.clearAllCallNotifications(context);
- return;
- }
-
- Call call = mCallList.getIncomingCall();
- if (call != null) {
- TelecomAdapter.getInstance().rejectCall(call.getId(), false, null);
- }
- }
-
- public void acceptUpgradeRequest(int videoState, Context context) {
- Log.d(this, " acceptUpgradeRequest videoState " + videoState);
- // Bail if we have been shut down and the call list is null.
- if (mCallList == null) {
- StatusBarNotifier.clearAllCallNotifications(context);
- Log.e(this, " acceptUpgradeRequest mCallList is empty so returning");
- return;
- }
-
- Call call = mCallList.getVideoUpgradeRequestCall();
- if (call != null) {
- VideoProfile videoProfile = new VideoProfile(videoState);
- call.getVideoCall().sendSessionModifyResponse(videoProfile);
- call.setSessionModificationState(Call.SessionModificationState.NO_REQUEST);
- }
- }
-
- public void declineUpgradeRequest(Context context) {
- Log.d(this, " declineUpgradeRequest");
- // Bail if we have been shut down and the call list is null.
- if (mCallList == null) {
- StatusBarNotifier.clearAllCallNotifications(context);
- Log.e(this, " declineUpgradeRequest mCallList is empty so returning");
- return;
- }
-
- Call call = mCallList.getVideoUpgradeRequestCall();
- if (call != null) {
- VideoProfile videoProfile =
- new VideoProfile(call.getVideoState());
- call.getVideoCall().sendSessionModifyResponse(videoProfile);
- call.setSessionModificationState(Call.SessionModificationState.NO_REQUEST);
- }
- }
-
- /*package*/
- void declineUpgradeRequest() {
- // Pass mContext if InCallActivity is destroyed.
- // Ex: When user pressed back key while in active call and
- // then modify request is received followed by MT call.
- declineUpgradeRequest(mInCallActivity != null ? mInCallActivity : mContext);
- }
-
- /**
- * Returns true if the incall app is the foreground application.
- */
- public boolean isShowingInCallUi() {
- return (isActivityStarted() && mInCallActivity.isVisible());
- }
-
- /**
- * Returns true if the activity has been created and is running.
- * Returns true as long as activity is not destroyed or finishing. This ensures that we return
- * true even if the activity is paused (not in foreground).
- */
- public boolean isActivityStarted() {
- return (mInCallActivity != null &&
- !mInCallActivity.isDestroyed() &&
- !mInCallActivity.isFinishing());
- }
-
- public boolean isActivityPreviouslyStarted() {
- return mIsActivityPreviouslyStarted;
- }
-
- /**
- * Determines if the In-Call app is currently changing configuration.
- *
- * @return {@code true} if the In-Call app is changing configuration.
- */
- public boolean isChangingConfigurations() {
- return mIsChangingConfigurations;
- }
-
- /**
- * Tracks whether the In-Call app is currently in the process of changing configuration (i.e.
- * screen orientation).
- */
- /*package*/
- void updateIsChangingConfigurations() {
- mIsChangingConfigurations = false;
- if (mInCallActivity != null) {
- mIsChangingConfigurations = mInCallActivity.isChangingConfigurations();
- }
- Log.v(this, "updateIsChangingConfigurations = " + mIsChangingConfigurations);
- }
-
-
- /**
- * Called when the activity goes in/out of the foreground.
- */
- public void onUiShowing(boolean showing) {
- // We need to update the notification bar when we leave the UI because that
- // could trigger it to show again.
- if (mStatusBarNotifier != null) {
- mStatusBarNotifier.updateNotification(mInCallState, mCallList);
- }
-
- if (mProximitySensor != null) {
- mProximitySensor.onInCallShowing(showing);
- }
-
- Intent broadcastIntent = ObjectFactory.getUiReadyBroadcastIntent(mContext);
- if (broadcastIntent != null) {
- broadcastIntent.putExtra(EXTRA_FIRST_TIME_SHOWN, !mIsActivityPreviouslyStarted);
-
- if (showing) {
- Log.d(this, "Sending sticky broadcast: ", broadcastIntent);
- mContext.sendStickyBroadcast(broadcastIntent);
- } else {
- Log.d(this, "Removing sticky broadcast: ", broadcastIntent);
- mContext.removeStickyBroadcast(broadcastIntent);
- }
- }
-
- if (showing) {
- mIsActivityPreviouslyStarted = true;
- } else {
- updateIsChangingConfigurations();
- }
-
- for (InCallUiListener listener : mInCallUiListeners) {
- listener.onUiShowing(showing);
- }
- }
-
- public void addInCallUiListener(InCallUiListener listener) {
- mInCallUiListeners.add(listener);
- }
-
- public boolean removeInCallUiListener(InCallUiListener listener) {
- return mInCallUiListeners.remove(listener);
- }
-
- /*package*/
- void onActivityStarted() {
- Log.d(this, "onActivityStarted");
- notifyVideoPauseController(true);
- }
-
- /*package*/
- void onActivityStopped() {
- Log.d(this, "onActivityStopped");
- notifyVideoPauseController(false);
- }
-
- private void notifyVideoPauseController(boolean showing) {
- Log.d(this, "notifyVideoPauseController: mIsChangingConfigurations=" +
- mIsChangingConfigurations);
- if (!mIsChangingConfigurations) {
- VideoPauseController.getInstance().onUiShowing(showing);
- }
- }
-
- /**
- * Brings the app into the foreground if possible.
- */
- public void bringToForeground(boolean showDialpad) {
- // Before we bring the incall UI to the foreground, we check to see if:
- // 1. It is not currently in the foreground
- // 2. We are in a state where we want to show the incall ui (i.e. there are calls to
- // be displayed)
- // If the activity hadn't actually been started previously, yet there are still calls
- // present (e.g. a call was accepted by a bluetooth or wired headset), we want to
- // bring it up the UI regardless.
- if (!isShowingInCallUi() && mInCallState != InCallState.NO_CALLS) {
- showInCall(showDialpad, false /* newOutgoingCall */);
- }
- }
-
- public void onPostDialCharWait(String callId, String chars) {
- if (isActivityStarted()) {
- mInCallActivity.showPostCharWaitDialog(callId, chars);
- }
- }
-
- /**
- * Handles the green CALL key while in-call.
- * @return true if we consumed the event.
- */
- public boolean handleCallKey() {
- Log.v(this, "handleCallKey");
-
- // The green CALL button means either "Answer", "Unhold", or
- // "Swap calls", or can be a no-op, depending on the current state
- // of the Phone.
-
- /**
- * INCOMING CALL
- */
- final CallList calls = mCallList;
- final Call incomingCall = calls.getIncomingCall();
- Log.v(this, "incomingCall: " + incomingCall);
-
- // (1) Attempt to answer a call
- if (incomingCall != null) {
- TelecomAdapter.getInstance().answerCall(
- incomingCall.getId(), VideoProfile.STATE_AUDIO_ONLY);
- return true;
- }
-
- /**
- * STATE_ACTIVE CALL
- */
- final Call activeCall = calls.getActiveCall();
- if (activeCall != null) {
- // TODO: This logic is repeated from CallButtonPresenter.java. We should
- // consolidate this logic.
- final boolean canMerge = activeCall.can(
- android.telecom.Call.Details.CAPABILITY_MERGE_CONFERENCE);
- final boolean canSwap = activeCall.can(
- android.telecom.Call.Details.CAPABILITY_SWAP_CONFERENCE);
-
- Log.v(this, "activeCall: " + activeCall + ", canMerge: " + canMerge +
- ", canSwap: " + canSwap);
-
- // (2) Attempt actions on conference calls
- if (canMerge) {
- TelecomAdapter.getInstance().merge(activeCall.getId());
- return true;
- } else if (canSwap) {
- TelecomAdapter.getInstance().swap(activeCall.getId());
- return true;
- }
- }
-
- /**
- * BACKGROUND CALL
- */
- final Call heldCall = calls.getBackgroundCall();
- if (heldCall != null) {
- // We have a hold call so presumeable it will always support HOLD...but
- // there is no harm in double checking.
- final boolean canHold = heldCall.can(android.telecom.Call.Details.CAPABILITY_HOLD);
-
- Log.v(this, "heldCall: " + heldCall + ", canHold: " + canHold);
-
- // (4) unhold call
- if (heldCall.getState() == Call.State.ONHOLD && canHold) {
- TelecomAdapter.getInstance().unholdCall(heldCall.getId());
- return true;
- }
- }
-
- // Always consume hard keys
- return true;
- }
-
- /**
- * A dialog could have prevented in-call screen from being previously finished.
- * This function checks to see if there should be any UI left and if not attempts
- * to tear down the UI.
- */
- public void onDismissDialog() {
- Log.i(this, "Dialog dismissed");
- if (mInCallState == InCallState.NO_CALLS) {
- attemptFinishActivity();
- attemptCleanup();
- }
- }
-
- /**
- * Toggles whether the application is in fullscreen mode or not.
- *
- * @return {@code true} if in-call is now in fullscreen mode.
- */
- public boolean toggleFullscreenMode() {
- boolean isFullScreen = !mIsFullScreen;
- Log.v(this, "toggleFullscreenMode = " + isFullScreen);
- setFullScreen(isFullScreen);
- return mIsFullScreen;
- }
-
- /**
- * Clears the previous fullscreen state.
- */
- public void clearFullscreen() {
- mIsFullScreen = false;
- }
-
- /**
- * Changes the fullscreen mode of the in-call UI.
- *
- * @param isFullScreen {@code true} if in-call should be in fullscreen mode, {@code false}
- * otherwise.
- */
- public void setFullScreen(boolean isFullScreen) {
- setFullScreen(isFullScreen, false /* force */);
- }
-
- /**
- * Changes the fullscreen mode of the in-call UI.
- *
- * @param isFullScreen {@code true} if in-call should be in fullscreen mode, {@code false}
- * otherwise.
- * @param force {@code true} if fullscreen mode should be set regardless of its current state.
- */
- public void setFullScreen(boolean isFullScreen, boolean force) {
- Log.v(this, "setFullScreen = " + isFullScreen);
-
- // As a safeguard, ensure we cannot enter fullscreen if the dialpad is shown.
- if (isDialpadVisible()) {
- isFullScreen = false;
- Log.v(this, "setFullScreen overridden as dialpad is shown = " + isFullScreen);
- }
-
- if (mIsFullScreen == isFullScreen && !force) {
- Log.v(this, "setFullScreen ignored as already in that state.");
- return;
- }
- mIsFullScreen = isFullScreen;
- notifyFullscreenModeChange(mIsFullScreen);
- }
-
- /**
- * @return {@code true} if the in-call ui is currently in fullscreen mode, {@code false}
- * otherwise.
- */
- public boolean isFullscreen() {
- return mIsFullScreen;
- }
-
-
- /**
- * Called by the {@link VideoCallPresenter} to inform of a change in full screen video status.
- *
- * @param isFullscreenMode {@code True} if entering full screen mode.
- */
- public void notifyFullscreenModeChange(boolean isFullscreenMode) {
- for (InCallEventListener listener : mInCallEventListeners) {
- listener.onFullscreenModeChanged(isFullscreenMode);
- }
- }
-
- /**
- * Called by the {@link CallCardPresenter} to inform of a change in visibility of the secondary
- * caller info bar.
- *
- * @param isVisible {@code true} if the secondary caller info is visible, {@code false}
- * otherwise.
- * @param height the height of the secondary caller info bar.
- */
- public void notifySecondaryCallerInfoVisibilityChanged(boolean isVisible, int height) {
- for (InCallEventListener listener : mInCallEventListeners) {
- listener.onSecondaryCallerInfoVisibilityChanged(isVisible, height);
- }
- }
-
-
- /**
- * For some disconnected causes, we show a dialog. This calls into the activity to show
- * the dialog if appropriate for the call.
- */
- private void maybeShowErrorDialogOnDisconnect(Call call) {
- // For newly disconnected calls, we may want to show a dialog on specific error conditions
- if (isActivityStarted() && call.getState() == Call.State.DISCONNECTED) {
- if (call.getAccountHandle() == null && !call.isConferenceCall()) {
- setDisconnectCauseForMissingAccounts(call);
- }
- mInCallActivity.maybeShowErrorDialogOnDisconnect(call.getDisconnectCause());
- }
- }
-
- /**
- * When the state of in-call changes, this is the first method to get called. It determines if
- * the UI needs to be started or finished depending on the new state and does it.
- */
- private InCallState startOrFinishUi(InCallState newState) {
- Log.d(this, "startOrFinishUi: " + mInCallState + " -> " + newState);
-
- // TODO: Consider a proper state machine implementation
-
- // If the state isn't changing we have already done any starting/stopping of activities in
- // a previous pass...so lets cut out early
- if (newState == mInCallState) {
- return newState;
- }
-
- // A new Incoming call means that the user needs to be notified of the the call (since
- // it wasn't them who initiated it). We do this through full screen notifications and
- // happens indirectly through {@link StatusBarNotifier}.
- //
- // The process for incoming calls is as follows:
- //
- // 1) CallList - Announces existence of new INCOMING call
- // 2) InCallPresenter - Gets announcement and calculates that the new InCallState
- // - should be set to INCOMING.
- // 3) InCallPresenter - This method is called to see if we need to start or finish
- // the app given the new state.
- // 4) StatusBarNotifier - Listens to InCallState changes. InCallPresenter calls
- // StatusBarNotifier explicitly to issue a FullScreen Notification
- // that will either start the InCallActivity or show the user a
- // top-level notification dialog if the user is in an immersive app.
- // That notification can also start the InCallActivity.
- // 5) InCallActivity - Main activity starts up and at the end of its onCreate will
- // call InCallPresenter::setActivity() to let the presenter
- // know that start-up is complete.
- //
- // [ AND NOW YOU'RE IN THE CALL. voila! ]
- //
- // Our app is started using a fullScreen notification. We need to do this whenever
- // we get an incoming call. Depending on the current context of the device, either a
- // incoming call HUN or the actual InCallActivity will be shown.
- final boolean startIncomingCallSequence = (InCallState.INCOMING == newState);
-
- // A dialog to show on top of the InCallUI to select a PhoneAccount
- final boolean showAccountPicker = (InCallState.WAITING_FOR_ACCOUNT == newState);
-
- // A new outgoing call indicates that the user just now dialed a number and when that
- // happens we need to display the screen immediately or show an account picker dialog if
- // no default is set. However, if the main InCallUI is already visible, we do not want to
- // re-initiate the start-up animation, so we do not need to do anything here.
- //
- // It is also possible to go into an intermediate state where the call has been initiated
- // but Telecom has not yet returned with the details of the call (handle, gateway, etc.).
- // This pending outgoing state can also launch the call screen.
- //
- // This is different from the incoming call sequence because we do not need to shock the
- // user with a top-level notification. Just show the call UI normally.
- final boolean mainUiNotVisible = !isShowingInCallUi() || !getCallCardFragmentVisible();
- boolean showCallUi = InCallState.OUTGOING == newState && mainUiNotVisible;
-
- // Direct transition from PENDING_OUTGOING -> INCALL means that there was an error in the
- // outgoing call process, so the UI should be brought up to show an error dialog.
- showCallUi |= (InCallState.PENDING_OUTGOING == mInCallState
- && InCallState.INCALL == newState && !isShowingInCallUi());
-
- // Another exception - InCallActivity is in charge of disconnecting a call with no
- // valid accounts set. Bring the UI up if this is true for the current pending outgoing
- // call so that:
- // 1) The call can be disconnected correctly
- // 2) The UI comes up and correctly displays the error dialog.
- // TODO: Remove these special case conditions by making InCallPresenter a true state
- // machine. Telecom should also be the component responsible for disconnecting a call
- // with no valid accounts.
- showCallUi |= InCallState.PENDING_OUTGOING == newState && mainUiNotVisible
- && isCallWithNoValidAccounts(mCallList.getPendingOutgoingCall());
-
- // The only time that we have an instance of mInCallActivity and it isn't started is
- // when it is being destroyed. In that case, lets avoid bringing up another instance of
- // the activity. When it is finally destroyed, we double check if we should bring it back
- // up so we aren't going to lose anything by avoiding a second startup here.
- boolean activityIsFinishing = mInCallActivity != null && !isActivityStarted();
- if (activityIsFinishing) {
- Log.i(this, "Undo the state change: " + newState + " -> " + mInCallState);
- return mInCallState;
- }
-
- if (showCallUi || showAccountPicker) {
- Log.i(this, "Start in call UI");
- showInCall(false /* showDialpad */, !showAccountPicker /* newOutgoingCall */);
- } else if (startIncomingCallSequence) {
- Log.i(this, "Start Full Screen in call UI");
-
- // We're about the bring up the in-call UI for an incoming call. If we still have
- // dialogs up, we need to clear them out before showing incoming screen.
- if (isActivityStarted()) {
- mInCallActivity.dismissPendingDialogs();
- }
- if (!startUi(newState)) {
- // startUI refused to start the UI. This indicates that it needed to restart the
- // activity. When it finally restarts, it will call us back, so we do not actually
- // change the state yet (we return mInCallState instead of newState).
- return mInCallState;
- }
- } else if (newState == InCallState.NO_CALLS) {
- // The new state is the no calls state. Tear everything down.
- attemptFinishActivity();
- attemptCleanup();
- }
-
- return newState;
- }
-
- /**
- * Determines whether or not a call has no valid phone accounts that can be used to make the
- * call with. Emergency calls do not require a phone account.
- *
- * @param call to check accounts for.
- * @return {@code true} if the call has no call capable phone accounts set, {@code false} if
- * the call contains a phone account that could be used to initiate it with, or is an emergency
- * call.
- */
- public static boolean isCallWithNoValidAccounts(Call call) {
- if (call != null && !call.isEmergencyCall()) {
- Bundle extras = call.getIntentExtras();
-
- if (extras == null) {
- extras = EMPTY_EXTRAS;
- }
-
- final List phoneAccountHandles = extras
- .getParcelableArrayList(android.telecom.Call.AVAILABLE_PHONE_ACCOUNTS);
-
- if ((call.getAccountHandle() == null &&
- (phoneAccountHandles == null || phoneAccountHandles.isEmpty()))) {
- Log.i(InCallPresenter.getInstance(), "No valid accounts for call " + call);
- return true;
- }
- }
- return false;
- }
-
- /**
- * Sets the DisconnectCause for a call that was disconnected because it was missing a
- * PhoneAccount or PhoneAccounts to select from.
- * @param call
- */
- private void setDisconnectCauseForMissingAccounts(Call call) {
- android.telecom.Call telecomCall = call.getTelecomCall();
-
- Bundle extras = telecomCall.getDetails().getIntentExtras();
- // Initialize the extras bundle to avoid NPE
- if (extras == null) {
- extras = new Bundle();
- }
-
- final List phoneAccountHandles = extras.getParcelableArrayList(
- android.telecom.Call.AVAILABLE_PHONE_ACCOUNTS);
-
- if (phoneAccountHandles == null || phoneAccountHandles.isEmpty()) {
- String scheme = telecomCall.getDetails().getHandle().getScheme();
- final String errorMsg = PhoneAccount.SCHEME_TEL.equals(scheme) ?
- mContext.getString(R.string.callFailed_simError) :
- mContext.getString(R.string.incall_error_supp_service_unknown);
- DisconnectCause disconnectCause =
- new DisconnectCause(DisconnectCause.ERROR, null, errorMsg, errorMsg);
- call.setDisconnectCause(disconnectCause);
- }
- }
-
- private boolean startUi(InCallState inCallState) {
- boolean isCallWaiting = mCallList.getActiveCall() != null &&
- mCallList.getIncomingCall() != null;
-
- // If the screen is off, we need to make sure it gets turned on for incoming calls.
- // This normally works just fine thanks to FLAG_TURN_SCREEN_ON but that only works
- // when the activity is first created. Therefore, to ensure the screen is turned on
- // for the call waiting case, we finish() the current activity and start a new one.
- // There should be no jank from this since the screen is already off and will remain so
- // until our new activity is up.
-
- if (isCallWaiting) {
- if (mProximitySensor.isScreenReallyOff() && isActivityStarted()) {
- Log.i(this, "Restarting InCallActivity to turn screen on for call waiting");
- mInCallActivity.finish();
- // When the activity actually finishes, we will start it again if there are
- // any active calls, so we do not need to start it explicitly here. Note, we
- // actually get called back on this function to restart it.
-
- // We return false to indicate that we did not actually start the UI.
- return false;
- } else {
- showInCall(false, false);
- }
- } else {
- mStatusBarNotifier.updateNotification(inCallState, mCallList);
- }
- return true;
- }
-
- /**
- * Checks to see if both the UI is gone and the service is disconnected. If so, tear it all
- * down.
- */
- private void attemptCleanup() {
- boolean shouldCleanup = (mInCallActivity == null && !mServiceConnected &&
- mInCallState == InCallState.NO_CALLS);
- Log.i(this, "attemptCleanup? " + shouldCleanup);
-
- if (shouldCleanup) {
- mIsActivityPreviouslyStarted = false;
- mIsChangingConfigurations = false;
-
- // blow away stale contact info so that we get fresh data on
- // the next set of calls
- if (mContactInfoCache != null) {
- mContactInfoCache.clearCache();
- }
- mContactInfoCache = null;
-
- if (mProximitySensor != null) {
- removeListener(mProximitySensor);
- mProximitySensor.tearDown();
- }
- mProximitySensor = null;
-
- mAudioModeProvider = null;
-
- if (mStatusBarNotifier != null) {
- removeListener(mStatusBarNotifier);
- }
- if (mExternalCallNotifier != null && mExternalCallList != null) {
- mExternalCallList.removeExternalCallListener(mExternalCallNotifier);
- }
- mStatusBarNotifier = null;
-
- if (mCallList != null) {
- mCallList.removeListener(this);
- mCallList.removeListener(mSpamCallListListener);
- }
- mCallList = null;
-
- mContext = null;
- mInCallActivity = null;
-
- mListeners.clear();
- mIncomingCallListeners.clear();
- mDetailsListeners.clear();
- mCanAddCallListeners.clear();
- mOrientationListeners.clear();
- mInCallEventListeners.clear();
-
- Log.d(this, "Finished InCallPresenter.CleanUp");
- }
- }
-
- public void showInCall(final boolean showDialpad, final boolean newOutgoingCall) {
- Log.i(this, "Showing InCallActivity");
- mContext.startActivity(getInCallIntent(showDialpad, newOutgoingCall));
- }
-
- public void onServiceBind() {
- mServiceBound = true;
- }
-
- public void onServiceUnbind() {
- InCallPresenter.getInstance().setBoundAndWaitingForOutgoingCall(false, null);
- mServiceBound = false;
- }
-
- public boolean isServiceBound() {
- return mServiceBound;
- }
-
- public void maybeStartRevealAnimation(Intent intent) {
- if (intent == null || mInCallActivity != null) {
- return;
- }
- final Bundle extras = intent.getBundleExtra(TelecomManager.EXTRA_OUTGOING_CALL_EXTRAS);
- if (extras == null) {
- // Incoming call, just show the in-call UI directly.
- return;
- }
-
- if (extras.containsKey(android.telecom.Call.AVAILABLE_PHONE_ACCOUNTS)) {
- // Account selection dialog will show up so don't show the animation.
- return;
- }
-
- final PhoneAccountHandle accountHandle =
- intent.getParcelableExtra(TelecomManager.EXTRA_PHONE_ACCOUNT_HANDLE);
- final Point touchPoint = extras.getParcelable(TouchPointManager.TOUCH_POINT);
-
- InCallPresenter.getInstance().setBoundAndWaitingForOutgoingCall(true, accountHandle);
-
- final Intent incallIntent = getInCallIntent(false, true);
- incallIntent.putExtra(TouchPointManager.TOUCH_POINT, touchPoint);
- mContext.startActivity(incallIntent);
- }
-
- public Intent getInCallIntent(boolean showDialpad, boolean newOutgoingCall) {
- final Intent intent = new Intent(Intent.ACTION_MAIN, null);
- intent.setFlags(Intent.FLAG_ACTIVITY_NO_USER_ACTION | Intent.FLAG_ACTIVITY_NEW_TASK);
-
- intent.setClass(mContext, InCallActivity.class);
- if (showDialpad) {
- intent.putExtra(InCallActivity.SHOW_DIALPAD_EXTRA, true);
- }
- intent.putExtra(InCallActivity.NEW_OUTGOING_CALL_EXTRA, newOutgoingCall);
- return intent;
- }
-
- /**
- * Retrieves the current in-call camera manager instance, creating if necessary.
- *
- * @return The {@link InCallCameraManager}.
- */
- public InCallCameraManager getInCallCameraManager() {
- synchronized(this) {
- if (mInCallCameraManager == null) {
- mInCallCameraManager = new InCallCameraManager(mContext);
- }
-
- return mInCallCameraManager;
- }
- }
-
- /**
- * Notifies listeners of changes in orientation and notify calls of rotation angle change.
- *
- * @param orientation The screen orientation of the device (one of:
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_0},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_90},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_180},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_270}).
- */
- public void onDeviceOrientationChange(int orientation) {
- Log.d(this, "onDeviceOrientationChange: orientation= " + orientation);
-
- if (mCallList != null) {
- mCallList.notifyCallsOfDeviceRotation(orientation);
- } else {
- Log.w(this, "onDeviceOrientationChange: CallList is null.");
- }
-
- // Notify listeners of device orientation changed.
- for (InCallOrientationListener listener : mOrientationListeners) {
- listener.onDeviceOrientationChanged(orientation);
- }
- }
-
- /**
- * Configures the in-call UI activity so it can change orientations or not. Enables the
- * orientation event listener if allowOrientationChange is true, disables it if false.
- *
- * @param allowOrientationChange {@code True} if the in-call UI can change between portrait
- * and landscape. {@Code False} if the in-call UI should be locked in portrait.
- */
- public void setInCallAllowsOrientationChange(boolean allowOrientationChange) {
- if (mInCallActivity == null) {
- Log.e(this, "InCallActivity is null. Can't set requested orientation.");
- return;
- }
-
- if (!allowOrientationChange) {
- mInCallActivity.setRequestedOrientation(
- InCallOrientationEventListener.NO_SENSOR_SCREEN_ORIENTATION);
- } else {
- // Using SCREEN_ORIENTATION_FULL_SENSOR allows for reverse-portrait orientation, where
- // SCREEN_ORIENTATION_SENSOR does not.
- mInCallActivity.setRequestedOrientation(
- InCallOrientationEventListener.FULL_SENSOR_SCREEN_ORIENTATION);
- }
- mInCallActivity.enableInCallOrientationEventListener(allowOrientationChange);
- }
-
- public void enableScreenTimeout(boolean enable) {
- Log.v(this, "enableScreenTimeout: value=" + enable);
- if (mInCallActivity == null) {
- Log.e(this, "enableScreenTimeout: InCallActivity is null.");
- return;
- }
-
- final Window window = mInCallActivity.getWindow();
- if (enable) {
- window.clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
- } else {
- window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
- }
- }
-
- /**
- * Returns the space available beside the call card.
- *
- * @return The space beside the call card.
- */
- public float getSpaceBesideCallCard() {
- if (mInCallActivity != null && mInCallActivity.getCallCardFragment() != null) {
- return mInCallActivity.getCallCardFragment().getSpaceBesideCallCard();
- }
- return 0;
- }
-
- /**
- * Returns whether the call card fragment is currently visible.
- *
- * @return True if the call card fragment is visible.
- */
- public boolean getCallCardFragmentVisible() {
- if (mInCallActivity != null && mInCallActivity.getCallCardFragment() != null) {
- return mInCallActivity.getCallCardFragment().isVisible();
- }
- return false;
- }
-
- /**
- * Hides or shows the conference manager fragment.
- *
- * @param show {@code true} if the conference manager should be shown, {@code false} if it
- * should be hidden.
- */
- public void showConferenceCallManager(boolean show) {
- if (mInCallActivity == null) {
- return;
- }
-
- mInCallActivity.showConferenceFragment(show);
- }
-
- /**
- * Determines if the dialpad is visible.
- *
- * @return {@code true} if the dialpad is visible, {@code false} otherwise.
- */
- public boolean isDialpadVisible() {
- if (mInCallActivity == null) {
- return false;
- }
- return mInCallActivity.isDialpadVisible();
- }
-
- /**
- * @return True if the application is currently running in a right-to-left locale.
- */
- public static boolean isRtl() {
- return TextUtils.getLayoutDirectionFromLocale(Locale.getDefault()) ==
- View.LAYOUT_DIRECTION_RTL;
- }
-
- /**
- * Extract background color from call object. The theme colors will include a primary color
- * and a secondary color.
- */
- public void setThemeColors() {
- // This method will set the background to default if the color is PhoneAccount.NO_COLOR.
- mThemeColors = getColorsFromCall(mCallList.getFirstCall());
-
- if (mInCallActivity == null) {
- return;
- }
-
- final Resources resources = mInCallActivity.getResources();
- final int color;
- if (resources.getBoolean(R.bool.is_layout_landscape)) {
- // TODO use ResourcesCompat.getColor(Resources, int, Resources.Theme) when available
- // {@link Resources#getColor(int)} used for compatibility
- color = resources.getColor(R.color.statusbar_background_color);
- } else {
- color = mThemeColors.mSecondaryColor;
- }
-
- mInCallActivity.getWindow().setStatusBarColor(color);
- final TaskDescription td = new TaskDescription(
- resources.getString(R.string.notification_ongoing_call), null, color);
- mInCallActivity.setTaskDescription(td);
- }
-
- /**
- * @return A palette for colors to display in the UI.
- */
- public MaterialPalette getThemeColors() {
- return mThemeColors;
- }
-
- private MaterialPalette getColorsFromCall(Call call) {
- if (call == null) {
- return getColorsFromPhoneAccountHandle(mPendingPhoneAccountHandle);
- } else {
- if (call.isSpam()) {
- Resources resources = mContext.getResources();
- return new InCallUIMaterialColorMapUtils(
- resources).calculatePrimaryAndSecondaryColor(
- resources.getColor(R.color.incall_call_spam_background_color));
- } else {
- return getColorsFromPhoneAccountHandle(call.getAccountHandle());
- }
- }
- }
-
- private MaterialPalette getColorsFromPhoneAccountHandle(PhoneAccountHandle phoneAccountHandle) {
- int highlightColor = PhoneAccount.NO_HIGHLIGHT_COLOR;
- if (phoneAccountHandle != null) {
- final TelecomManager tm = getTelecomManager();
-
- if (tm != null) {
- final PhoneAccount account =
- TelecomManagerCompat.getPhoneAccount(tm, phoneAccountHandle);
- // For single-sim devices, there will be no selected highlight color, so the phone
- // account will default to NO_HIGHLIGHT_COLOR.
- if (account != null && CompatUtils.isLollipopMr1Compatible()) {
- highlightColor = account.getHighlightColor();
- }
- }
- }
- return new InCallUIMaterialColorMapUtils(
- mContext.getResources()).calculatePrimaryAndSecondaryColor(highlightColor);
- }
-
- /**
- * @return An instance of TelecomManager.
- */
- public TelecomManager getTelecomManager() {
- if (mTelecomManager == null) {
- mTelecomManager = (TelecomManager)
- mContext.getSystemService(Context.TELECOM_SERVICE);
- }
- return mTelecomManager;
- }
-
- /**
- * @return An instance of TelephonyManager
- */
- public TelephonyManager getTelephonyManager() {
- return mTelephonyManager;
- }
-
- InCallActivity getActivity() {
- return mInCallActivity;
- }
-
- AnswerPresenter getAnswerPresenter() {
- return mAnswerPresenter;
- }
-
- ExternalCallNotifier getExternalCallNotifier() {
- return mExternalCallNotifier;
- }
-
- /**
- * Private constructor. Must use getInstance() to get this singleton.
- */
- private InCallPresenter() {
- }
-
- /**
- * All the main states of InCallActivity.
- */
- public enum InCallState {
- // InCall Screen is off and there are no calls
- NO_CALLS,
-
- // Incoming-call screen is up
- INCOMING,
-
- // In-call experience is showing
- INCALL,
-
- // Waiting for user input before placing outgoing call
- WAITING_FOR_ACCOUNT,
-
- // UI is starting up but no call has been initiated yet.
- // The UI is waiting for Telecom to respond.
- PENDING_OUTGOING,
-
- // User is dialing out
- OUTGOING;
-
- public boolean isIncoming() {
- return (this == INCOMING);
- }
-
- public boolean isConnectingOrConnected() {
- return (this == INCOMING ||
- this == OUTGOING ||
- this == INCALL);
- }
- }
-
- /**
- * Interface implemented by classes that need to know about the InCall State.
- */
- public interface InCallStateListener {
- // TODO: Enhance state to contain the call objects instead of passing CallList
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList);
- }
-
- public interface IncomingCallListener {
- public void onIncomingCall(InCallState oldState, InCallState newState, Call call);
- }
-
- public interface CanAddCallListener {
- public void onCanAddCallChanged(boolean canAddCall);
- }
-
- public interface InCallDetailsListener {
- public void onDetailsChanged(Call call, android.telecom.Call.Details details);
- }
-
- public interface InCallOrientationListener {
- public void onDeviceOrientationChanged(int orientation);
- }
-
- /**
- * Interface implemented by classes that need to know about events which occur within the
- * In-Call UI. Used as a means of communicating between fragments that make up the UI.
- */
- public interface InCallEventListener {
- public void onFullscreenModeChanged(boolean isFullscreenMode);
- public void onSecondaryCallerInfoVisibilityChanged(boolean isVisible, int height);
- }
-
- public interface InCallUiListener {
- void onUiShowing(boolean showing);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallServiceImpl.java b/InCallUI/src/com/android/incallui/InCallServiceImpl.java
deleted file mode 100644
index 1414bc51de1200aaa16b77904394fb56f7417773..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallServiceImpl.java
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.content.Intent;
-import android.os.IBinder;
-import android.telecom.Call;
-import android.telecom.CallAudioState;
-import android.telecom.InCallService;
-
-/**
- * Used to receive updates about calls from the Telecom component. This service is bound to
- * Telecom while there exist calls which potentially require UI. This includes ringing (incoming),
- * dialing (outgoing), and active calls. When the last call is disconnected, Telecom will unbind to
- * the service triggering InCallActivity (via CallList) to finish soon after.
- */
-public class InCallServiceImpl extends InCallService {
-
- @Override
- public void onCallAudioStateChanged(CallAudioState audioState) {
- AudioModeProvider.getInstance().onAudioStateChanged(audioState.isMuted(),
- audioState.getRoute(), audioState.getSupportedRouteMask());
- }
-
- @Override
- public void onBringToForeground(boolean showDialpad) {
- InCallPresenter.getInstance().onBringToForeground(showDialpad);
- }
-
- @Override
- public void onCallAdded(Call call) {
- InCallPresenter.getInstance().onCallAdded(call);
- }
-
- @Override
- public void onCallRemoved(Call call) {
- InCallPresenter.getInstance().onCallRemoved(call);
- }
-
- @Override
- public void onCanAddCallChanged(boolean canAddCall) {
- InCallPresenter.getInstance().onCanAddCallChanged(canAddCall);
- }
-
- @Override
- public IBinder onBind(Intent intent) {
- final Context context = getApplicationContext();
- final ContactInfoCache contactInfoCache = ContactInfoCache.getInstance(context);
- InCallPresenter.getInstance().setUp(
- getApplicationContext(),
- CallList.getInstance(),
- new ExternalCallList(),
- AudioModeProvider.getInstance(),
- new StatusBarNotifier(context, contactInfoCache),
- new ExternalCallNotifier(context, contactInfoCache),
- contactInfoCache,
- new ProximitySensor(
- context,
- AudioModeProvider.getInstance(),
- new AccelerometerListener(context))
- );
- InCallPresenter.getInstance().onServiceBind();
- InCallPresenter.getInstance().maybeStartRevealAnimation(intent);
- TelecomAdapter.getInstance().setInCallService(this);
-
- return super.onBind(intent);
- }
-
- @Override
- public boolean onUnbind(Intent intent) {
- super.onUnbind(intent);
-
- InCallPresenter.getInstance().onServiceUnbind();
- tearDown();
-
- return false;
- }
-
- private void tearDown() {
- Log.v(this, "tearDown");
- // Tear down the InCall system
- TelecomAdapter.getInstance().clearInCallService();
- InCallPresenter.getInstance().tearDown();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallServiceListener.java b/InCallUI/src/com/android/incallui/InCallServiceListener.java
deleted file mode 100644
index 11a5b08ef9b44efb1d98841464167935d1dc5bde..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallServiceListener.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.telecom.InCallService;
-
-/**
- * Interface implemented by In-Call components that maintain a reference to the Telecom API
- * {@code InCallService} object. Clarifies the expectations associated with the relevant method
- * calls.
- */
-public interface InCallServiceListener {
-
- /**
- * Called once at {@code InCallService} startup time with a valid instance. At
- * that time, there will be no existing {@code Call}s.
- *
- * @param inCallService The {@code InCallService} object.
- */
- void setInCallService(InCallService inCallService);
-
- /**
- * Called once at {@code InCallService} shutdown time. At that time, any {@code Call}s
- * will have transitioned through the disconnected state and will no longer exist.
- */
- void clearInCallService();
-}
diff --git a/InCallUI/src/com/android/incallui/InCallUIMaterialColorMapUtils.java b/InCallUI/src/com/android/incallui/InCallUIMaterialColorMapUtils.java
deleted file mode 100644
index 9c108b8557f1fd69f3fc073f953018bcf3b9aceb..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallUIMaterialColorMapUtils.java
+++ /dev/null
@@ -1,55 +0,0 @@
-package com.android.incallui;
-
-import android.content.res.Resources;
-import android.content.res.TypedArray;
-import android.telecom.PhoneAccount;
-
-import com.android.contacts.common.util.MaterialColorMapUtils;
-import com.android.contacts.common.util.MaterialColorMapUtils.MaterialPalette;
-import com.android.dialer.R;
-
-public class InCallUIMaterialColorMapUtils extends MaterialColorMapUtils {
- private final TypedArray sPrimaryColors;
- private final TypedArray sSecondaryColors;
- private final Resources mResources;
-
- public InCallUIMaterialColorMapUtils(Resources resources) {
- super(resources);
- sPrimaryColors = resources.obtainTypedArray(R.array.background_colors);
- sSecondaryColors = resources.obtainTypedArray(R.array.background_colors_dark);
- mResources = resources;
- }
-
- /**
- * Currently the InCallUI color will only vary by SIM color which is a list of colors
- * defined in the background_colors array, so first search the list for the matching color and
- * fall back to the closest matching color if an exact match does not exist.
- */
- @Override
- public MaterialPalette calculatePrimaryAndSecondaryColor(int color) {
- if (color == PhoneAccount.NO_HIGHLIGHT_COLOR) {
- return getDefaultPrimaryAndSecondaryColors(mResources);
- }
-
- for (int i = 0; i < sPrimaryColors.length(); i++) {
- if (sPrimaryColors.getColor(i, 0) == color) {
- return new MaterialPalette(
- sPrimaryColors.getColor(i, 0),
- sSecondaryColors.getColor(i, 0));
- }
- }
-
- // The color isn't in the list, so use the superclass to find an approximate color.
- return super.calculatePrimaryAndSecondaryColor(color);
- }
-
- /**
- * {@link Resources#getColor(int) used for compatibility
- */
- @SuppressWarnings("deprecation")
- public static MaterialPalette getDefaultPrimaryAndSecondaryColors(Resources resources) {
- final int primaryColor = resources.getColor(R.color.dialer_theme_color);
- final int secondaryColor = resources.getColor(R.color.dialer_theme_color_dark);
- return new MaterialPalette(primaryColor, secondaryColor);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallVideoCallCallback.java b/InCallUI/src/com/android/incallui/InCallVideoCallCallback.java
deleted file mode 100644
index 99e6d5129bd54b6e3f342acd5bd13addf70e0f68..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallVideoCallCallback.java
+++ /dev/null
@@ -1,156 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.telecom.Connection;
-import android.telecom.Connection.VideoProvider;
-import android.telecom.InCallService.VideoCall;
-import android.telecom.VideoProfile;
-import android.telecom.VideoProfile.CameraCapabilities;
-
-/**
- * Implements the InCallUI VideoCall Callback.
- */
-public class InCallVideoCallCallback extends VideoCall.Callback {
-
- /**
- * The call associated with this {@link InCallVideoCallCallback}.
- */
- private Call mCall;
-
- /**
- * Creates an instance of the call video client, specifying the call it is related to.
- *
- * @param call The call.
- */
- public InCallVideoCallCallback(Call call) {
- mCall = call;
- }
-
- /**
- * Handles an incoming session modification request.
- *
- * @param videoProfile The requested video call profile.
- */
- @Override
- public void onSessionModifyRequestReceived(VideoProfile videoProfile) {
- Log.d(this, " onSessionModifyRequestReceived videoProfile=" + videoProfile);
- int previousVideoState = VideoUtils.getUnPausedVideoState(mCall.getVideoState());
- int newVideoState = VideoUtils.getUnPausedVideoState(videoProfile.getVideoState());
-
- boolean wasVideoCall = VideoUtils.isVideoCall(previousVideoState);
- boolean isVideoCall = VideoUtils.isVideoCall(newVideoState);
-
- // Check for upgrades to video.
- if (!wasVideoCall && isVideoCall && previousVideoState != newVideoState) {
- InCallVideoCallCallbackNotifier.getInstance().upgradeToVideoRequest(mCall,
- newVideoState);
- }
- }
-
- /**
- * Handles a session modification response.
- *
- * @param status Status of the session modify request. Valid values are
- * {@link Connection.VideoProvider#SESSION_MODIFY_REQUEST_SUCCESS},
- * {@link Connection.VideoProvider#SESSION_MODIFY_REQUEST_FAIL},
- * {@link Connection.VideoProvider#SESSION_MODIFY_REQUEST_INVALID}
- * @param requestedProfile
- * @param responseProfile The actual profile changes made by the peer device.
- */
- @Override
- public void onSessionModifyResponseReceived(int status, VideoProfile requestedProfile,
- VideoProfile responseProfile) {
- Log.d(this, "onSessionModifyResponseReceived status=" + status + " requestedProfile="
- + requestedProfile + " responseProfile=" + responseProfile);
- if (status != VideoProvider.SESSION_MODIFY_REQUEST_SUCCESS) {
- // Report the reason the upgrade failed as the new session modification state.
- if (status == VideoProvider.SESSION_MODIFY_REQUEST_TIMED_OUT) {
- mCall.setSessionModificationState(
- Call.SessionModificationState.UPGRADE_TO_VIDEO_REQUEST_TIMED_OUT);
- } else {
- if (status == VideoProvider.SESSION_MODIFY_REQUEST_REJECTED_BY_REMOTE) {
- mCall.setSessionModificationState(
- Call.SessionModificationState.REQUEST_REJECTED);
- } else {
- mCall.setSessionModificationState(
- Call.SessionModificationState.REQUEST_FAILED);
- }
- }
- }
-
- // Finally clear the outstanding request.
- mCall.setSessionModificationState(Call.SessionModificationState.NO_REQUEST);
- }
-
- /**
- * Handles a call session event.
- *
- * @param event The event.
- */
- @Override
- public void onCallSessionEvent(int event) {
- InCallVideoCallCallbackNotifier.getInstance().callSessionEvent(event);
- }
-
- /**
- * Handles a change to the peer video dimensions.
- *
- * @param width The updated peer video width.
- * @param height The updated peer video height.
- */
- @Override
- public void onPeerDimensionsChanged(int width, int height) {
- InCallVideoCallCallbackNotifier.getInstance().peerDimensionsChanged(mCall, width, height);
- }
-
- /**
- * Handles a change to the video quality of the call.
- *
- * @param videoQuality The updated video call quality.
- */
- @Override
- public void onVideoQualityChanged(int videoQuality) {
- InCallVideoCallCallbackNotifier.getInstance().videoQualityChanged(mCall, videoQuality);
- }
-
- /**
- * Handles a change to the call data usage. No implementation as the in-call UI does not
- * display data usage.
- *
- * @param dataUsage The updated data usage.
- */
- @Override
- public void onCallDataUsageChanged(long dataUsage) {
- Log.d(this, "onCallDataUsageChanged: dataUsage = " + dataUsage);
- InCallVideoCallCallbackNotifier.getInstance().callDataUsageChanged(dataUsage);
- }
-
- /**
- * Handles changes to the camera capabilities. No implementation as the in-call UI does not
- * make use of camera capabilities.
- *
- * @param cameraCapabilities The changed camera capabilities.
- */
- @Override
- public void onCameraCapabilitiesChanged(CameraCapabilities cameraCapabilities) {
- if (cameraCapabilities != null) {
- InCallVideoCallCallbackNotifier.getInstance().cameraDimensionsChanged(
- mCall, cameraCapabilities.getWidth(), cameraCapabilities.getHeight());
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/InCallVideoCallCallbackNotifier.java b/InCallUI/src/com/android/incallui/InCallVideoCallCallbackNotifier.java
deleted file mode 100644
index bb7529205a7a483dbc57cdf747f774556fba122f..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/InCallVideoCallCallbackNotifier.java
+++ /dev/null
@@ -1,284 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import java.util.Collections;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * Class used by {@link InCallService.VideoCallCallback} to notify interested parties of incoming
- * events.
- */
-public class InCallVideoCallCallbackNotifier {
- /**
- * Singleton instance of this class.
- */
- private static InCallVideoCallCallbackNotifier sInstance =
- new InCallVideoCallCallbackNotifier();
-
- /**
- * ConcurrentHashMap constructor params: 8 is initial table size, 0.9f is
- * load factor before resizing, 1 means we only expect a single thread to
- * access the map so make only a single shard
- */
- private final Set mSessionModificationListeners =
- Collections.newSetFromMap(new ConcurrentHashMap
- (8, 0.9f, 1));
- private final Set mVideoEventListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
- private final Set mSurfaceChangeListeners = Collections.newSetFromMap(
- new ConcurrentHashMap(8, 0.9f, 1));
-
- /**
- * Static singleton accessor method.
- */
- public static InCallVideoCallCallbackNotifier getInstance() {
- return sInstance;
- }
-
- /**
- * Private constructor. Instance should only be acquired through getInstance().
- */
- private InCallVideoCallCallbackNotifier() {
- }
-
- /**
- * Adds a new {@link SessionModificationListener}.
- *
- * @param listener The listener.
- */
- public void addSessionModificationListener(SessionModificationListener listener) {
- Preconditions.checkNotNull(listener);
- mSessionModificationListeners.add(listener);
- }
-
- /**
- * Remove a {@link SessionModificationListener}.
- *
- * @param listener The listener.
- */
- public void removeSessionModificationListener(SessionModificationListener listener) {
- if (listener != null) {
- mSessionModificationListeners.remove(listener);
- }
- }
-
- /**
- * Adds a new {@link VideoEventListener}.
- *
- * @param listener The listener.
- */
- public void addVideoEventListener(VideoEventListener listener) {
- Preconditions.checkNotNull(listener);
- mVideoEventListeners.add(listener);
- }
-
- /**
- * Remove a {@link VideoEventListener}.
- *
- * @param listener The listener.
- */
- public void removeVideoEventListener(VideoEventListener listener) {
- if (listener != null) {
- mVideoEventListeners.remove(listener);
- }
- }
-
- /**
- * Adds a new {@link SurfaceChangeListener}.
- *
- * @param listener The listener.
- */
- public void addSurfaceChangeListener(SurfaceChangeListener listener) {
- Preconditions.checkNotNull(listener);
- mSurfaceChangeListeners.add(listener);
- }
-
- /**
- * Remove a {@link SurfaceChangeListener}.
- *
- * @param listener The listener.
- */
- public void removeSurfaceChangeListener(SurfaceChangeListener listener) {
- if (listener != null) {
- mSurfaceChangeListeners.remove(listener);
- }
- }
-
- /**
- * Inform listeners of an upgrade to video request for a call.
- * @param call The call.
- * @param videoState The video state we want to upgrade to.
- */
- public void upgradeToVideoRequest(Call call, int videoState) {
- Log.d(this, "upgradeToVideoRequest call = " + call + " new video state = " + videoState);
- for (SessionModificationListener listener : mSessionModificationListeners) {
- listener.onUpgradeToVideoRequest(call, videoState);
- }
- }
-
- /**
- * Inform listeners of a call session event.
- *
- * @param event The call session event.
- */
- public void callSessionEvent(int event) {
- for (VideoEventListener listener : mVideoEventListeners) {
- listener.onCallSessionEvent(event);
- }
- }
-
- /**
- * Inform listeners of a downgrade to audio.
- *
- * @param call The call.
- * @param paused The paused state.
- */
- public void peerPausedStateChanged(Call call, boolean paused) {
- for (VideoEventListener listener : mVideoEventListeners) {
- listener.onPeerPauseStateChanged(call, paused);
- }
- }
-
- /**
- * Inform listeners of any change in the video quality of the call
- *
- * @param call The call.
- * @param videoQuality The updated video quality of the call.
- */
- public void videoQualityChanged(Call call, int videoQuality) {
- for (VideoEventListener listener : mVideoEventListeners) {
- listener.onVideoQualityChanged(call, videoQuality);
- }
- }
-
- /**
- * Inform listeners of a change to peer dimensions.
- *
- * @param call The call.
- * @param width New peer width.
- * @param height New peer height.
- */
- public void peerDimensionsChanged(Call call, int width, int height) {
- for (SurfaceChangeListener listener : mSurfaceChangeListeners) {
- listener.onUpdatePeerDimensions(call, width, height);
- }
- }
-
- /**
- * Inform listeners of a change to camera dimensions.
- *
- * @param call The call.
- * @param width The new camera video width.
- * @param height The new camera video height.
- */
- public void cameraDimensionsChanged(Call call, int width, int height) {
- for (SurfaceChangeListener listener : mSurfaceChangeListeners) {
- listener.onCameraDimensionsChange(call, width, height);
- }
- }
-
- /**
- * Inform listeners of a change to call data usage.
- *
- * @param dataUsage data usage value
- */
- public void callDataUsageChanged(long dataUsage) {
- for (VideoEventListener listener : mVideoEventListeners) {
- listener.onCallDataUsageChange(dataUsage);
- }
- }
-
- /**
- * Listener interface for any class that wants to be notified of upgrade to video request.
- */
- public interface SessionModificationListener {
- /**
- * Called when a peer request is received to upgrade an audio-only call to a video call.
- *
- * @param call The call the request was received for.
- * @param videoState The requested video state.
- */
- public void onUpgradeToVideoRequest(Call call, int videoState);
- }
-
- /**
- * Listener interface for any class that wants to be notified of video events, including pause
- * and un-pause of peer video, video quality changes.
- */
- public interface VideoEventListener {
- /**
- * Called when the peer pauses or un-pauses video transmission.
- *
- * @param call The call which paused or un-paused video transmission.
- * @param paused {@code True} when the video transmission is paused, {@code false}
- * otherwise.
- */
- public void onPeerPauseStateChanged(Call call, boolean paused);
-
- /**
- * Called when the video quality changes.
- *
- * @param call The call whose video quality changes.
- * @param videoCallQuality - values are QUALITY_HIGH, MEDIUM, LOW and UNKNOWN.
- */
- public void onVideoQualityChanged(Call call, int videoCallQuality);
-
- /*
- * Called when call data usage value is requested or when call data usage value is updated
- * because of a call state change
- *
- * @param dataUsage call data usage value
- */
- public void onCallDataUsageChange(long dataUsage);
-
- /**
- * Called when call session event is raised.
- *
- * @param event The call session event.
- */
- public void onCallSessionEvent(int event);
- }
-
- /**
- * Listener interface for any class that wants to be notified of changes to the video surfaces.
- */
- public interface SurfaceChangeListener {
- /**
- * Called when the peer video feed changes dimensions. This can occur when the peer rotates
- * their device, changing the aspect ratio of the video signal.
- *
- * @param call The call which experienced a peer video
- * @param width
- * @param height
- */
- public void onUpdatePeerDimensions(Call call, int width, int height);
-
- /**
- * Called when the local camera changes dimensions. This occurs when a change in camera
- * occurs.
- *
- * @param call The call which experienced the camera dimension change.
- * @param width The new camera video width.
- * @param height The new camera video height.
- */
- public void onCameraDimensionsChange(Call call, int width, int height);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/LatencyReport.java b/InCallUI/src/com/android/incallui/LatencyReport.java
deleted file mode 100644
index 655372a8f949f2beb077d9759795343e87d29969..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/LatencyReport.java
+++ /dev/null
@@ -1,145 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.os.Bundle;
-import android.os.SystemClock;
-
-import com.android.incalluibind.ObjectFactory;
-
-/**
- * Tracks latency information for a call.
- */
-public class LatencyReport {
- // The following are hidden constants from android.telecom.TelecomManager.
- private static final String EXTRA_CALL_CREATED_TIME_MILLIS =
- "android.telecom.extra.CALL_CREATED_TIME_MILLIS";
- private static final String EXTRA_CALL_TELECOM_ROUTING_START_TIME_MILLIS =
- "android.telecom.extra.CALL_TELECOM_ROUTING_START_TIME_MILLIS";
- private static final String EXTRA_CALL_TELECOM_ROUTING_END_TIME_MILLIS =
- "android.telecom.extra.CALL_TELECOM_ROUTING_END_TIME_MILLIS";
-
- public static final long INVALID_TIME = -1;
-
- private final boolean mWasIncoming;
-
- // Time elapsed since boot when the call was created by the connection service.
- private final long mCreatedTimeMillis;
-
- // Time elapsed since boot when telecom began processing the call.
- private final long mTelecomRoutingStartTimeMillis;
-
- // Time elapsed since boot when telecom finished processing the call. This includes things like
- // looking up contact info and call blocking but before showing any UI.
- private final long mTelecomRoutingEndTimeMillis;
-
- // Time elapsed since boot when the call was added to the InCallUi.
- private final long mCallAddedTimeMillis;
-
- // Time elapsed since boot when the call was added and call blocking evaluation was completed.
- private long mCallBlockingTimeMillis = INVALID_TIME;
-
- // Time elapsed since boot when the call notification was shown.
- private long mCallNotificationTimeMillis = INVALID_TIME;
-
- // Time elapsed since boot when the InCallUI was shown.
- private long mInCallUiShownTimeMillis = INVALID_TIME;
-
- // Whether the call was shown to the user as a heads up notification instead of a full screen
- // UI.
- private boolean mDidDisplayHeadsUpNotification;
-
- public LatencyReport() {
- mWasIncoming = false;
- mCreatedTimeMillis = INVALID_TIME;
- mTelecomRoutingStartTimeMillis = INVALID_TIME;
- mTelecomRoutingEndTimeMillis = INVALID_TIME;
- mCallAddedTimeMillis = SystemClock.elapsedRealtime();
- }
-
- public LatencyReport(android.telecom.Call telecomCall) {
- mWasIncoming = telecomCall.getState() == android.telecom.Call.STATE_RINGING;
- Bundle extras = telecomCall.getDetails().getIntentExtras();
- if (extras == null) {
- mCreatedTimeMillis = INVALID_TIME;
- mTelecomRoutingStartTimeMillis = INVALID_TIME;
- mTelecomRoutingEndTimeMillis = INVALID_TIME;
- } else {
- mCreatedTimeMillis = extras.getLong(EXTRA_CALL_CREATED_TIME_MILLIS, INVALID_TIME);
- mTelecomRoutingStartTimeMillis = extras.getLong(
- EXTRA_CALL_TELECOM_ROUTING_START_TIME_MILLIS, INVALID_TIME);
- mTelecomRoutingEndTimeMillis = extras.getLong(
- EXTRA_CALL_TELECOM_ROUTING_END_TIME_MILLIS, INVALID_TIME);
- }
- mCallAddedTimeMillis = SystemClock.elapsedRealtime();
- }
-
- public boolean getWasIncoming() {
- return mWasIncoming;
- }
-
- public long getCreatedTimeMillis() {
- return mCreatedTimeMillis;
- }
-
- public long getTelecomRoutingStartTimeMillis() {
- return mTelecomRoutingStartTimeMillis;
- }
-
- public long getTelecomRoutingEndTimeMillis() {
- return mTelecomRoutingEndTimeMillis;
- }
-
- public long getCallAddedTimeMillis() {
- return mCallAddedTimeMillis;
- }
-
- public long getCallBlockingTimeMillis() {
- return mCallBlockingTimeMillis;
- }
-
- public void onCallBlockingDone() {
- if (mCallBlockingTimeMillis == INVALID_TIME) {
- mCallBlockingTimeMillis = SystemClock.elapsedRealtime();
- }
- }
-
- public long getCallNotificationTimeMillis() {
- return mCallNotificationTimeMillis;
- }
-
- public void onNotificationShown() {
- if (mCallNotificationTimeMillis == INVALID_TIME) {
- mCallNotificationTimeMillis = SystemClock.elapsedRealtime();
- }
- }
-
- public long getInCallUiShownTimeMillis() {
- return mInCallUiShownTimeMillis;
- }
-
- public void onInCallUiShown(boolean forFullScreenIntent) {
- if (mInCallUiShownTimeMillis == INVALID_TIME) {
- mInCallUiShownTimeMillis = SystemClock.elapsedRealtime();
- mDidDisplayHeadsUpNotification = mWasIncoming && !forFullScreenIntent;
- }
- }
-
- public boolean getDidDisplayHeadsUpNotification() {
- return mDidDisplayHeadsUpNotification;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/Log.java b/InCallUI/src/com/android/incallui/Log.java
deleted file mode 100644
index 07a0e61ca7e65094193d2dc6c5a72020b93f8008..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/Log.java
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.net.Uri;
-import android.telecom.PhoneAccount;
-import android.telephony.PhoneNumberUtils;
-
-import java.security.MessageDigest;
-import java.security.NoSuchAlgorithmException;
-
-/**
- * Manages logging for the entire class.
- */
-public class Log {
-
- // Generic tag for all In Call logging
- public static final String TAG = "InCall";
-
- public static final boolean FORCE_DEBUG = false; /* STOPSHIP if true */
- public static final boolean DEBUG = FORCE_DEBUG ||
- android.util.Log.isLoggable(TAG, android.util.Log.DEBUG);
- public static final boolean VERBOSE = FORCE_DEBUG ||
- android.util.Log.isLoggable(TAG, android.util.Log.VERBOSE);
- public static final String TAG_DELIMETER = " - ";
-
- public static void d(String tag, String msg) {
- if (DEBUG) {
- android.util.Log.d(TAG, delimit(tag) + msg);
- }
- }
-
- public static void d(Object obj, String msg) {
- if (DEBUG) {
- android.util.Log.d(TAG, getPrefix(obj) + msg);
- }
- }
-
- public static void d(Object obj, String str1, Object str2) {
- if (DEBUG) {
- android.util.Log.d(TAG, getPrefix(obj) + str1 + str2);
- }
- }
-
- public static void v(Object obj, String msg) {
- if (VERBOSE) {
- android.util.Log.v(TAG, getPrefix(obj) + msg);
- }
- }
-
- public static void v(Object obj, String str1, Object str2) {
- if (VERBOSE) {
- android.util.Log.d(TAG, getPrefix(obj) + str1 + str2);
- }
- }
-
- public static void e(String tag, String msg, Exception e) {
- android.util.Log.e(TAG, delimit(tag) + msg, e);
- }
-
- public static void e(String tag, String msg) {
- android.util.Log.e(TAG, delimit(tag) + msg);
- }
-
- public static void e(Object obj, String msg, Exception e) {
- android.util.Log.e(TAG, getPrefix(obj) + msg, e);
- }
-
- public static void e(Object obj, String msg) {
- android.util.Log.e(TAG, getPrefix(obj) + msg);
- }
-
- public static void i(String tag, String msg) {
- android.util.Log.i(TAG, delimit(tag) + msg);
- }
-
- public static void i(Object obj, String msg) {
- android.util.Log.i(TAG, getPrefix(obj) + msg);
- }
-
- public static void w(Object obj, String msg) {
- android.util.Log.w(TAG, getPrefix(obj) + msg);
- }
-
- public static void wtf(Object obj, String msg) {
- android.util.Log.wtf(TAG, getPrefix(obj) + msg);
- }
-
- public static String piiHandle(Object pii) {
- if (pii == null || VERBOSE) {
- return String.valueOf(pii);
- }
-
- if (pii instanceof Uri) {
- Uri uri = (Uri) pii;
-
- // All Uri's which are not "tel" go through normal pii() method.
- if (!PhoneAccount.SCHEME_TEL.equals(uri.getScheme())) {
- return pii(pii);
- } else {
- pii = uri.getSchemeSpecificPart();
- }
- }
-
- String originalString = String.valueOf(pii);
- StringBuilder stringBuilder = new StringBuilder(originalString.length());
- for (char c : originalString.toCharArray()) {
- if (PhoneNumberUtils.isDialable(c)) {
- stringBuilder.append('*');
- } else {
- stringBuilder.append(c);
- }
- }
- return stringBuilder.toString();
- }
-
- /**
- * Redact personally identifiable information for production users.
- * If we are running in verbose mode, return the original string, otherwise
- * return a SHA-1 hash of the input string.
- */
- public static String pii(Object pii) {
- if (pii == null || VERBOSE) {
- return String.valueOf(pii);
- }
- return "[" + secureHash(String.valueOf(pii).getBytes()) + "]";
- }
-
- private static String secureHash(byte[] input) {
- MessageDigest messageDigest;
- try {
- messageDigest = MessageDigest.getInstance("SHA-1");
- } catch (NoSuchAlgorithmException e) {
- return null;
- }
- messageDigest.update(input);
- byte[] result = messageDigest.digest();
- return encodeHex(result);
- }
-
- private static String encodeHex(byte[] bytes) {
- StringBuffer hex = new StringBuffer(bytes.length * 2);
-
- for (int i = 0; i < bytes.length; i++) {
- int byteIntValue = bytes[i] & 0xff;
- if (byteIntValue < 0x10) {
- hex.append("0");
- }
- hex.append(Integer.toString(byteIntValue, 16));
- }
-
- return hex.toString();
- }
-
- private static String getPrefix(Object obj) {
- return (obj == null ? "" : (obj.getClass().getSimpleName() + TAG_DELIMETER));
- }
-
- private static String delimit(String tag) {
- return tag + TAG_DELIMETER;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/NeededForReflection.java b/InCallUI/src/com/android/incallui/NeededForReflection.java
deleted file mode 100644
index 363a0a548cc8213f617ad7a4ec47a998aa7f3b97..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/NeededForReflection.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-/**
- * Denotes that the class, constructor, method or field is used for reflection and therefore cannot
- * be removed by tools like ProGuard.
- */
-@Retention(RetentionPolicy.CLASS)
-@Target({ElementType.TYPE, ElementType.CONSTRUCTOR, ElementType.METHOD, ElementType.FIELD})
-public @interface NeededForReflection {}
diff --git a/InCallUI/src/com/android/incallui/NotificationBroadcastReceiver.java b/InCallUI/src/com/android/incallui/NotificationBroadcastReceiver.java
deleted file mode 100644
index 27f71159d0f0922dfec174ac730063f407d58776..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/NotificationBroadcastReceiver.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.telecom.VideoProfile;
-
-/**
- * Accepts broadcast Intents which will be prepared by {@link StatusBarNotifier} and thus
- * sent from the notification manager.
- * This should be visible from outside, but shouldn't be exported.
- */
-public class NotificationBroadcastReceiver extends BroadcastReceiver {
-
- /**
- * Intent Action used for hanging up the current call from Notification bar. This will
- * choose first ringing call, first active call, or first background call (typically in
- * STATE_HOLDING state).
- */
- public static final String ACTION_DECLINE_INCOMING_CALL =
- "com.android.incallui.ACTION_DECLINE_INCOMING_CALL";
- public static final String ACTION_HANG_UP_ONGOING_CALL =
- "com.android.incallui.ACTION_HANG_UP_ONGOING_CALL";
- public static final String ACTION_ANSWER_VIDEO_INCOMING_CALL =
- "com.android.incallui.ACTION_ANSWER_VIDEO_INCOMING_CALL";
- public static final String ACTION_ANSWER_VOICE_INCOMING_CALL =
- "com.android.incallui.ACTION_ANSWER_VOICE_INCOMING_CALL";
- public static final String ACTION_ACCEPT_VIDEO_UPGRADE_REQUEST =
- "com.android.incallui.ACTION_ACCEPT_VIDEO_UPGRADE_REQUEST";
- public static final String ACTION_DECLINE_VIDEO_UPGRADE_REQUEST =
- "com.android.incallui.ACTION_DECLINE_VIDEO_UPGRADE_REQUEST";
- public static final String ACTION_PULL_EXTERNAL_CALL =
- "com.android.incallui.ACTION_PULL_EXTERNAL_CALL";
- public static final String EXTRA_NOTIFICATION_ID =
- "com.android.incallui.extra.EXTRA_NOTIFICATION_ID";
-
- @Override
- public void onReceive(Context context, Intent intent) {
- final String action = intent.getAction();
- Log.i(this, "Broadcast from Notification: " + action);
-
- // TODO: Commands of this nature should exist in the CallList.
- if (action.equals(ACTION_ANSWER_VIDEO_INCOMING_CALL)) {
- InCallPresenter.getInstance().answerIncomingCall(
- context, VideoProfile.STATE_BIDIRECTIONAL);
- } else if (action.equals(ACTION_ANSWER_VOICE_INCOMING_CALL)) {
- InCallPresenter.getInstance().answerIncomingCall(
- context, VideoProfile.STATE_AUDIO_ONLY);
- } else if (action.equals(ACTION_DECLINE_INCOMING_CALL)) {
- InCallPresenter.getInstance().declineIncomingCall(context);
- } else if (action.equals(ACTION_HANG_UP_ONGOING_CALL)) {
- InCallPresenter.getInstance().hangUpOngoingCall(context);
- } else if (action.equals(ACTION_ACCEPT_VIDEO_UPGRADE_REQUEST)) {
- //TODO: Change calltype after adding support for TX and RX
- InCallPresenter.getInstance().acceptUpgradeRequest(
- VideoProfile.STATE_BIDIRECTIONAL, context);
- } else if (action.equals(ACTION_DECLINE_VIDEO_UPGRADE_REQUEST)) {
- InCallPresenter.getInstance().declineUpgradeRequest(context);
- } else if (action.equals(ACTION_PULL_EXTERNAL_CALL)) {
- int notificationId = intent.getIntExtra(EXTRA_NOTIFICATION_ID, -1);
- InCallPresenter.getInstance().getExternalCallNotifier()
- .pullExternalCall(notificationId);
- }
- }
-
-}
diff --git a/InCallUI/src/com/android/incallui/PostCharDialogFragment.java b/InCallUI/src/com/android/incallui/PostCharDialogFragment.java
deleted file mode 100644
index 6f904ad9e5ab22f673fb86017e61502f4aeaffe2..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/PostCharDialogFragment.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import android.app.AlertDialog;
-import android.app.Dialog;
-import android.app.DialogFragment;
-import android.content.DialogInterface;
-import android.os.Bundle;
-import android.view.WindowManager;
-
-import com.android.dialer.R;
-
-/**
- * Pop up an alert dialog with OK and Cancel buttons to allow user to Accept or Reject the WAIT
- * inserted as part of the Dial string.
- */
-public class PostCharDialogFragment extends DialogFragment {
-
- private static final String STATE_CALL_ID = "CALL_ID";
- private static final String STATE_POST_CHARS = "POST_CHARS";
-
- private String mCallId;
- private String mPostDialStr;
-
- public PostCharDialogFragment() {
- }
-
- public PostCharDialogFragment(String callId, String postDialStr) {
- mCallId = callId;
- mPostDialStr = postDialStr;
- }
-
- @Override
- public Dialog onCreateDialog(Bundle savedInstanceState) {
- super.onCreateDialog(savedInstanceState);
-
- if (mPostDialStr == null && savedInstanceState != null) {
- mCallId = savedInstanceState.getString(STATE_CALL_ID);
- mPostDialStr = savedInstanceState.getString(STATE_POST_CHARS);
- }
-
- final StringBuilder buf = new StringBuilder();
- buf.append(getResources().getText(R.string.wait_prompt_str));
- buf.append(mPostDialStr);
-
- final AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
- builder.setMessage(buf.toString());
-
- builder.setPositiveButton(R.string.pause_prompt_yes, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int whichButton) {
- TelecomAdapter.getInstance().postDialContinue(mCallId, true);
- }
- });
- builder.setNegativeButton(R.string.pause_prompt_no, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int whichButton) {
- dialog.cancel();
- }
- });
-
- final AlertDialog dialog = builder.create();
- return dialog;
- }
-
- @Override
- public void onCancel(DialogInterface dialog) {
- super.onCancel(dialog);
-
- TelecomAdapter.getInstance().postDialContinue(mCallId, false);
- }
-
- @Override
- public void onSaveInstanceState(Bundle outState) {
- super.onSaveInstanceState(outState);
-
- outState.putString(STATE_CALL_ID, mCallId);
- outState.putString(STATE_POST_CHARS, mPostDialStr);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/Presenter.java b/InCallUI/src/com/android/incallui/Presenter.java
deleted file mode 100644
index 4e1fa978d76c88a0a9673ee5c553fbaee3780288..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/Presenter.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.os.Bundle;
-
-/**
- * Base class for Presenters.
- */
-public abstract class Presenter {
-
- private U mUi;
-
- /**
- * Called after the UI view has been created. That is when fragment.onViewCreated() is called.
- *
- * @param ui The Ui implementation that is now ready to be used.
- */
- public void onUiReady(U ui) {
- mUi = ui;
- }
-
- /**
- * Called when the UI view is destroyed in Fragment.onDestroyView().
- */
- public final void onUiDestroy(U ui) {
- onUiUnready(ui);
- mUi = null;
- }
-
- /**
- * To be overriden by Presenter implementations. Called when the fragment is being
- * destroyed but before ui is set to null.
- */
- public void onUiUnready(U ui) {
- }
-
- public void onSaveInstanceState(Bundle outState) {}
-
- public void onRestoreInstanceState(Bundle savedInstanceState) {}
-
- public U getUi() {
- return mUi;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ProximitySensor.java b/InCallUI/src/com/android/incallui/ProximitySensor.java
deleted file mode 100644
index 3c9fd937019e31cf171fad48225d952283a0bfb9..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ProximitySensor.java
+++ /dev/null
@@ -1,317 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Objects;
-
-import android.content.Context;
-import android.content.res.Configuration;
-import android.hardware.display.DisplayManager;
-import android.hardware.display.DisplayManager.DisplayListener;
-import android.os.PowerManager;
-import android.telecom.CallAudioState;
-import android.view.Display;
-
-import com.android.incallui.AudioModeProvider.AudioModeListener;
-import com.android.incallui.InCallPresenter.InCallState;
-import com.android.incallui.InCallPresenter.InCallStateListener;
-
-/**
- * Class manages the proximity sensor for the in-call UI.
- * We enable the proximity sensor while the user in a phone call. The Proximity sensor turns off
- * the touchscreen and display when the user is close to the screen to prevent user's cheek from
- * causing touch events.
- * The class requires special knowledge of the activity and device state to know when the proximity
- * sensor should be enabled and disabled. Most of that state is fed into this class through
- * public methods.
- */
-public class ProximitySensor implements AccelerometerListener.OrientationListener,
- InCallStateListener, AudioModeListener {
- private static final String TAG = ProximitySensor.class.getSimpleName();
-
- private final PowerManager mPowerManager;
- private final PowerManager.WakeLock mProximityWakeLock;
- private final AudioModeProvider mAudioModeProvider;
- private final AccelerometerListener mAccelerometerListener;
- private final ProximityDisplayListener mDisplayListener;
- private int mOrientation = AccelerometerListener.ORIENTATION_UNKNOWN;
- private boolean mUiShowing = false;
- private boolean mIsPhoneOffhook = false;
- private boolean mDialpadVisible;
-
- // True if the keyboard is currently *not* hidden
- // Gets updated whenever there is a Configuration change
- private boolean mIsHardKeyboardOpen;
-
- public ProximitySensor(Context context, AudioModeProvider audioModeProvider,
- AccelerometerListener accelerometerListener) {
- mPowerManager = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
- if (mPowerManager.isWakeLockLevelSupported(PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK)) {
- mProximityWakeLock = mPowerManager.newWakeLock(
- PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK, TAG);
- } else {
- Log.w(TAG, "Device does not support proximity wake lock.");
- mProximityWakeLock = null;
- }
- mAccelerometerListener = accelerometerListener;
- mAccelerometerListener.setListener(this);
-
- mDisplayListener = new ProximityDisplayListener(
- (DisplayManager) context.getSystemService(Context.DISPLAY_SERVICE));
- mDisplayListener.register();
-
- mAudioModeProvider = audioModeProvider;
- mAudioModeProvider.addListener(this);
- }
-
- public void tearDown() {
- mAudioModeProvider.removeListener(this);
-
- mAccelerometerListener.enable(false);
- mDisplayListener.unregister();
-
- turnOffProximitySensor(true);
- }
-
- /**
- * Called to identify when the device is laid down flat.
- */
- @Override
- public void orientationChanged(int orientation) {
- mOrientation = orientation;
- updateProximitySensorMode();
- }
-
- /**
- * Called to keep track of the overall UI state.
- */
- @Override
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList) {
- // We ignore incoming state because we do not want to enable proximity
- // sensor during incoming call screen. We check hasLiveCall() because a disconnected call
- // can also put the in-call screen in the INCALL state.
- boolean hasOngoingCall = InCallState.INCALL == newState && callList.hasLiveCall();
- boolean isOffhook = (InCallState.OUTGOING == newState) || hasOngoingCall;
-
- if (isOffhook != mIsPhoneOffhook) {
- mIsPhoneOffhook = isOffhook;
-
- mOrientation = AccelerometerListener.ORIENTATION_UNKNOWN;
- mAccelerometerListener.enable(mIsPhoneOffhook);
-
- updateProximitySensorMode();
- }
- }
-
- @Override
- public void onSupportedAudioMode(int modeMask) {
- }
-
- @Override
- public void onMute(boolean muted) {
- }
-
- /**
- * Called when the audio mode changes during a call.
- */
- @Override
- public void onAudioMode(int mode) {
- updateProximitySensorMode();
- }
-
- public void onDialpadVisible(boolean visible) {
- mDialpadVisible = visible;
- updateProximitySensorMode();
- }
-
- /**
- * Called by InCallActivity to listen for hard keyboard events.
- */
- public void onConfigurationChanged(Configuration newConfig) {
- mIsHardKeyboardOpen = newConfig.hardKeyboardHidden == Configuration.HARDKEYBOARDHIDDEN_NO;
-
- // Update the Proximity sensor based on keyboard state
- updateProximitySensorMode();
- }
-
- /**
- * Used to save when the UI goes in and out of the foreground.
- */
- public void onInCallShowing(boolean showing) {
- if (showing) {
- mUiShowing = true;
-
- // We only consider the UI not showing for instances where another app took the foreground.
- // If we stopped showing because the screen is off, we still consider that showing.
- } else if (mPowerManager.isScreenOn()) {
- mUiShowing = false;
- }
- updateProximitySensorMode();
- }
-
- void onDisplayStateChanged(boolean isDisplayOn) {
- Log.i(this, "isDisplayOn: " + isDisplayOn);
- mAccelerometerListener.enable(isDisplayOn);
- }
-
- /**
- * TODO: There is no way to determine if a screen is off due to proximity or if it is
- * legitimately off, but if ever we can do that in the future, it would be useful here.
- * Until then, this function will simply return true of the screen is off.
- * TODO: Investigate whether this can be replaced with the ProximityDisplayListener.
- */
- public boolean isScreenReallyOff() {
- return !mPowerManager.isScreenOn();
- }
-
- private void turnOnProximitySensor() {
- if (mProximityWakeLock != null) {
- if (!mProximityWakeLock.isHeld()) {
- Log.i(this, "Acquiring proximity wake lock");
- mProximityWakeLock.acquire();
- } else {
- Log.i(this, "Proximity wake lock already acquired");
- }
- }
- }
-
- private void turnOffProximitySensor(boolean screenOnImmediately) {
- if (mProximityWakeLock != null) {
- if (mProximityWakeLock.isHeld()) {
- Log.i(this, "Releasing proximity wake lock");
- int flags =
- (screenOnImmediately ? 0 : PowerManager.RELEASE_FLAG_WAIT_FOR_NO_PROXIMITY);
- mProximityWakeLock.release(flags);
- } else {
- Log.i(this, "Proximity wake lock already released");
- }
- }
- }
-
- /**
- * Updates the wake lock used to control proximity sensor behavior,
- * based on the current state of the phone.
- *
- * On devices that have a proximity sensor, to avoid false touches
- * during a call, we hold a PROXIMITY_SCREEN_OFF_WAKE_LOCK wake lock
- * whenever the phone is off hook. (When held, that wake lock causes
- * the screen to turn off automatically when the sensor detects an
- * object close to the screen.)
- *
- * This method is a no-op for devices that don't have a proximity
- * sensor.
- *
- * Proximity wake lock will *not* be held if any one of the
- * conditions is true while on a call:
- * 1) If the audio is routed via Bluetooth
- * 2) If a wired headset is connected
- * 3) if the speaker is ON
- * 4) If the slider is open(i.e. the hardkeyboard is *not* hidden)
- */
- private synchronized void updateProximitySensorMode() {
- final int audioMode = mAudioModeProvider.getAudioMode();
-
- // turn proximity sensor off and turn screen on immediately if
- // we are using a headset, the keyboard is open, or the device
- // is being held in a horizontal position.
- boolean screenOnImmediately = (CallAudioState.ROUTE_WIRED_HEADSET == audioMode
- || CallAudioState.ROUTE_SPEAKER == audioMode
- || CallAudioState.ROUTE_BLUETOOTH == audioMode
- || mIsHardKeyboardOpen);
-
- // We do not keep the screen off when the user is outside in-call screen and we are
- // horizontal, but we do not force it on when we become horizontal until the
- // proximity sensor goes negative.
- final boolean horizontal =
- (mOrientation == AccelerometerListener.ORIENTATION_HORIZONTAL);
- screenOnImmediately |= !mUiShowing && horizontal;
-
- // We do not keep the screen off when dialpad is visible, we are horizontal, and
- // the in-call screen is being shown.
- // At that moment we're pretty sure users want to use it, instead of letting the
- // proximity sensor turn off the screen by their hands.
- screenOnImmediately |= mDialpadVisible && horizontal;
-
- Log.v(this, "screenonImmediately: ", screenOnImmediately);
-
- Log.i(this, Objects.toStringHelper(this)
- .add("keybrd", mIsHardKeyboardOpen ? 1 : 0)
- .add("dpad", mDialpadVisible ? 1 : 0)
- .add("offhook", mIsPhoneOffhook ? 1 : 0)
- .add("hor", horizontal ? 1 : 0)
- .add("ui", mUiShowing ? 1 : 0)
- .add("aud", CallAudioState.audioRouteToString(audioMode))
- .toString());
-
- if (mIsPhoneOffhook && !screenOnImmediately) {
- Log.d(this, "Turning on proximity sensor");
- // Phone is in use! Arrange for the screen to turn off
- // automatically when the sensor detects a close object.
- turnOnProximitySensor();
- } else {
- Log.d(this, "Turning off proximity sensor");
- // Phone is either idle, or ringing. We don't want any special proximity sensor
- // behavior in either case.
- turnOffProximitySensor(screenOnImmediately);
- }
- }
-
- /**
- * Implementation of a {@link DisplayListener} that maintains a binary state:
- * Screen on vs screen off. Used by the proximity sensor manager to decide whether or not
- * it needs to listen to accelerometer events.
- */
- public class ProximityDisplayListener implements DisplayListener {
- private DisplayManager mDisplayManager;
- private boolean mIsDisplayOn = true;
-
- ProximityDisplayListener(DisplayManager displayManager) {
- mDisplayManager = displayManager;
- }
-
- void register() {
- mDisplayManager.registerDisplayListener(this, null);
- }
-
- void unregister() {
- mDisplayManager.unregisterDisplayListener(this);
- }
-
- @Override
- public void onDisplayRemoved(int displayId) {
- }
-
- @Override
- public void onDisplayChanged(int displayId) {
- if (displayId == Display.DEFAULT_DISPLAY) {
- final Display display = mDisplayManager.getDisplay(displayId);
-
- final boolean isDisplayOn = display.getState() != Display.STATE_OFF;
- // For call purposes, we assume that as long as the screen is not truly off, it is
- // considered on, even if it is in an unknown or low power idle state.
- if (isDisplayOn != mIsDisplayOn) {
- mIsDisplayOn = isDisplayOn;
- onDisplayStateChanged(mIsDisplayOn);
- }
- }
- }
-
- @Override
- public void onDisplayAdded(int displayId) {
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/StatusBarNotifier.java b/InCallUI/src/com/android/incallui/StatusBarNotifier.java
deleted file mode 100644
index cc87dd414e9ec0bfbb72772bf17ed59faf63dd61..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/StatusBarNotifier.java
+++ /dev/null
@@ -1,793 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui;
-
-import static com.android.contacts.common.compat.CallSdkCompat.Details.PROPERTY_ENTERPRISE_CALL;
-import static com.android.incallui.NotificationBroadcastReceiver.ACTION_ACCEPT_VIDEO_UPGRADE_REQUEST;
-import static com.android.incallui.NotificationBroadcastReceiver.ACTION_ANSWER_VIDEO_INCOMING_CALL;
-import static com.android.incallui.NotificationBroadcastReceiver.ACTION_ANSWER_VOICE_INCOMING_CALL;
-import static com.android.incallui.NotificationBroadcastReceiver.ACTION_DECLINE_INCOMING_CALL;
-import static com.android.incallui.NotificationBroadcastReceiver.ACTION_DECLINE_VIDEO_UPGRADE_REQUEST;
-import static com.android.incallui.NotificationBroadcastReceiver.ACTION_HANG_UP_ONGOING_CALL;
-
-import com.google.common.base.Preconditions;
-
-import android.app.Notification;
-import android.app.NotificationManager;
-import android.app.PendingIntent;
-import android.content.Context;
-import android.content.Intent;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.media.AudioAttributes;
-import android.net.Uri;
-import android.provider.ContactsContract.Contacts;
-import android.support.annotation.Nullable;
-import android.telecom.Call.Details;
-import android.telecom.PhoneAccount;
-import android.telecom.TelecomManager;
-import android.text.BidiFormatter;
-import android.text.TextDirectionHeuristics;
-import android.text.TextUtils;
-
-import com.android.contacts.common.ContactsUtils;
-import com.android.contacts.common.ContactsUtils.UserType;
-import com.android.contacts.common.preference.ContactsPreferences;
-import com.android.contacts.common.testing.NeededForTesting;
-import com.android.contacts.common.util.BitmapUtil;
-import com.android.contacts.common.util.ContactDisplayUtils;
-import com.android.dialer.R;
-import com.android.dialer.service.ExtendedCallInfoService;
-import com.android.incallui.ContactInfoCache.ContactCacheEntry;
-import com.android.incallui.ContactInfoCache.ContactInfoCacheCallback;
-import com.android.incallui.InCallPresenter.InCallState;
-import com.android.incallui.async.PausableExecutorImpl;
-import com.android.incallui.ringtone.DialerRingtoneManager;
-import com.android.incallui.ringtone.InCallTonePlayer;
-import com.android.incallui.ringtone.ToneGeneratorFactory;
-
-import java.util.Objects;
-
-/**
- * This class adds Notifications to the status bar for the in-call experience.
- */
-public class StatusBarNotifier implements InCallPresenter.InCallStateListener,
- CallList.CallUpdateListener {
-
- // Notification types
- // Indicates that no notification is currently showing.
- private static final int NOTIFICATION_NONE = 0;
- // Notification for an active call. This is non-interruptive, but cannot be dismissed.
- private static final int NOTIFICATION_IN_CALL = 1;
- // Notification for incoming calls. This is interruptive and will show up as a HUN.
- private static final int NOTIFICATION_INCOMING_CALL = 2;
-
- private static final int PENDING_INTENT_REQUEST_CODE_NON_FULL_SCREEN = 0;
- private static final int PENDING_INTENT_REQUEST_CODE_FULL_SCREEN = 1;
-
- private static final long[] VIBRATE_PATTERN = new long[] {0, 1000, 1000};
-
- private final Context mContext;
- @Nullable private ContactsPreferences mContactsPreferences;
- private final ContactInfoCache mContactInfoCache;
- private final NotificationManager mNotificationManager;
- private final DialerRingtoneManager mDialerRingtoneManager;
- private int mCurrentNotification = NOTIFICATION_NONE;
- private int mCallState = Call.State.INVALID;
- private int mSavedIcon = 0;
- private String mSavedContent = null;
- private Bitmap mSavedLargeIcon;
- private String mSavedContentTitle;
- private String mCallId = null;
- private InCallState mInCallState;
- private Uri mRingtone;
-
- public StatusBarNotifier(Context context, ContactInfoCache contactInfoCache) {
- Preconditions.checkNotNull(context);
- mContext = context;
- mContactsPreferences = ContactsPreferencesFactory.newContactsPreferences(mContext);
- mContactInfoCache = contactInfoCache;
- mNotificationManager =
- (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
- mDialerRingtoneManager = new DialerRingtoneManager(
- new InCallTonePlayer(new ToneGeneratorFactory(), new PausableExecutorImpl()),
- CallList.getInstance());
- mCurrentNotification = NOTIFICATION_NONE;
- }
-
- /**
- * Creates notifications according to the state we receive from {@link InCallPresenter}.
- */
- @Override
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList) {
- Log.d(this, "onStateChange");
- mInCallState = newState;
- updateNotification(newState, callList);
- }
-
- /**
- * Updates the phone app's status bar notification *and* launches the
- * incoming call UI in response to a new incoming call.
- *
- * If an incoming call is ringing (or call-waiting), the notification
- * will also include a "fullScreenIntent" that will cause the
- * InCallScreen to be launched, unless the current foreground activity
- * is marked as "immersive".
- *
- * (This is the mechanism that actually brings up the incoming call UI
- * when we receive a "new ringing connection" event from the telephony
- * layer.)
- *
- * Also note that this method is safe to call even if the phone isn't
- * actually ringing (or, more likely, if an incoming call *was*
- * ringing briefly but then disconnected). In that case, we'll simply
- * update or cancel the in-call notification based on the current
- * phone state.
- *
- * @see #updateInCallNotification(InCallState,CallList)
- */
- public void updateNotification(InCallState state, CallList callList) {
- updateInCallNotification(state, callList);
- }
-
- /**
- * Take down the in-call notification.
- * @see #updateInCallNotification(InCallState,CallList)
- */
- private void cancelNotification() {
- if (!TextUtils.isEmpty(mCallId)) {
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- mCallId = null;
- }
- if (mCurrentNotification != NOTIFICATION_NONE) {
- Log.d(this, "cancelInCall()...");
- mNotificationManager.cancel(mCurrentNotification);
- }
- mCurrentNotification = NOTIFICATION_NONE;
- }
-
- /**
- * Should only be called from a irrecoverable state where it is necessary to dismiss all
- * notifications.
- */
- static void clearAllCallNotifications(Context backupContext) {
- Log.i(StatusBarNotifier.class.getSimpleName(),
- "Something terrible happened. Clear all InCall notifications");
-
- NotificationManager notificationManager =
- (NotificationManager) backupContext.getSystemService(Context.NOTIFICATION_SERVICE);
- notificationManager.cancel(NOTIFICATION_IN_CALL);
- notificationManager.cancel(NOTIFICATION_INCOMING_CALL);
- }
-
- /**
- * Helper method for updateInCallNotification() and
- * updateNotification(): Update the phone app's
- * status bar notification based on the current telephony state, or
- * cancels the notification if the phone is totally idle.
- */
- private void updateInCallNotification(final InCallState state, CallList callList) {
- Log.d(this, "updateInCallNotification...");
-
- final Call call = getCallToShow(callList);
-
- if (call != null) {
- showNotification(call);
- } else {
- cancelNotification();
- }
- }
-
- private void showNotification(final Call call) {
- final boolean isIncoming = (call.getState() == Call.State.INCOMING ||
- call.getState() == Call.State.CALL_WAITING);
- if (!TextUtils.isEmpty(mCallId)) {
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- }
- mCallId = call.getId();
- CallList.getInstance().addCallUpdateListener(call.getId(), this);
-
- // we make a call to the contact info cache to query for supplemental data to what the
- // call provides. This includes the contact name and photo.
- // This callback will always get called immediately and synchronously with whatever data
- // it has available, and may make a subsequent call later (same thread) if it had to
- // call into the contacts provider for more data.
- mContactInfoCache.findInfo(call, isIncoming, new ContactInfoCacheCallback() {
- @Override
- public void onContactInfoComplete(String callId, ContactCacheEntry entry) {
- Call call = CallList.getInstance().getCallById(callId);
- if (call != null) {
- call.getLogState().contactLookupResult = entry.contactLookupResult;
- buildAndSendNotification(call, entry);
- }
- }
-
- @Override
- public void onImageLoadComplete(String callId, ContactCacheEntry entry) {
- Call call = CallList.getInstance().getCallById(callId);
- if (call != null) {
- buildAndSendNotification(call, entry);
- }
- }
-
- @Override
- public void onContactInteractionsInfoComplete(String callId, ContactCacheEntry entry) {}
- });
- }
-
- /**
- * Sets up the main Ui for the notification
- */
- private void buildAndSendNotification(Call originalCall, ContactCacheEntry contactInfo) {
- // This can get called to update an existing notification after contact information has come
- // back. However, it can happen much later. Before we continue, we need to make sure that
- // the call being passed in is still the one we want to show in the notification.
- final Call call = getCallToShow(CallList.getInstance());
- if (call == null || !call.getId().equals(originalCall.getId())) {
- return;
- }
-
- final int callState = call.getState();
- // Dont' show as spam if the number is in local contact.
- if (contactInfo.contactLookupResult == Call.LogState.LOOKUP_LOCAL_CONTACT) {
- call.setSpam(false);
- }
-
- // Check if data has changed; if nothing is different, don't issue another notification.
- final int iconResId = getIconToDisplay(call);
- Bitmap largeIcon = getLargeIconToDisplay(contactInfo, call);
- final String content =
- getContentString(call, contactInfo.userType);
- final String contentTitle = getContentTitle(contactInfo, call);
-
- final boolean isVideoUpgradeRequest = call.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST;
- final int notificationType;
- if (callState == Call.State.INCOMING || callState == Call.State.CALL_WAITING
- || isVideoUpgradeRequest) {
- notificationType = NOTIFICATION_INCOMING_CALL;
- } else {
- notificationType = NOTIFICATION_IN_CALL;
- }
-
- if (!checkForChangeAndSaveData(iconResId, content, largeIcon, contentTitle, callState,
- notificationType, contactInfo.contactRingtoneUri)) {
- return;
- }
-
- if (largeIcon != null) {
- largeIcon = getRoundedIcon(largeIcon);
- }
-
- /*
- * This builder is used for the notification shown when the device is locked and the user
- * has set their notification settings to 'hide sensitive content'
- * {@see Notification.Builder#setPublicVersion}.
- */
- Notification.Builder publicBuilder = new Notification.Builder(mContext);
- publicBuilder.setSmallIcon(iconResId)
- .setColor(mContext.getResources().getColor(R.color.dialer_theme_color))
- // Hide work call state for the lock screen notification
- .setContentTitle(getContentString(call, ContactsUtils.USER_TYPE_CURRENT));
- setNotificationWhen(call, callState, publicBuilder);
-
- /*
- * Builder for the notification shown when the device is unlocked or the user has set their
- * notification settings to 'show all notification content'.
- */
- final Notification.Builder builder = getNotificationBuilder();
- builder.setPublicVersion(publicBuilder.build());
-
- // Set up the main intent to send the user to the in-call screen
- builder.setContentIntent(createLaunchPendingIntent(false /* isFullScreen */));
-
- // Set the intent as a full screen intent as well if a call is incoming
- if (notificationType == NOTIFICATION_INCOMING_CALL
- && !InCallPresenter.getInstance().isShowingInCallUi()) {
- configureFullScreenIntent(
- builder, createLaunchPendingIntent(true /* isFullScreen */), call);
- // Set the notification category for incoming calls
- builder.setCategory(Notification.CATEGORY_CALL);
- }
-
- // Set the content
- builder.setContentText(content);
- builder.setSmallIcon(iconResId);
- builder.setContentTitle(contentTitle);
- builder.setLargeIcon(largeIcon);
- builder.setColor(mContext.getResources().getColor(R.color.dialer_theme_color));
-
- if (isVideoUpgradeRequest) {
- builder.setUsesChronometer(false);
- addDismissUpgradeRequestAction(builder);
- addAcceptUpgradeRequestAction(builder);
- } else {
- createIncomingCallNotification(call, callState, builder);
- }
-
- addPersonReference(builder, contactInfo, call);
-
- /*
- * Fire off the notification
- */
- Notification notification = builder.build();
-
- if (mDialerRingtoneManager.shouldPlayRingtone(callState, contactInfo.contactRingtoneUri)) {
- notification.flags |= Notification.FLAG_INSISTENT;
- notification.sound = contactInfo.contactRingtoneUri;
- AudioAttributes.Builder audioAttributes = new AudioAttributes.Builder();
- audioAttributes.setContentType(AudioAttributes.CONTENT_TYPE_MUSIC);
- audioAttributes.setUsage(AudioAttributes.USAGE_NOTIFICATION_RINGTONE);
- notification.audioAttributes = audioAttributes.build();
- if (mDialerRingtoneManager.shouldVibrate(mContext.getContentResolver())) {
- notification.vibrate = VIBRATE_PATTERN;
- }
- }
- if (mDialerRingtoneManager.shouldPlayCallWaitingTone(callState)) {
- Log.v(this, "Playing call waiting tone");
- mDialerRingtoneManager.playCallWaitingTone();
- }
- if (mCurrentNotification != notificationType && mCurrentNotification != NOTIFICATION_NONE) {
- Log.i(this, "Previous notification already showing - cancelling "
- + mCurrentNotification);
- mNotificationManager.cancel(mCurrentNotification);
- }
-
- Log.i(this, "Displaying notification for " + notificationType);
- mNotificationManager.notify(notificationType, notification);
- call.getLatencyReport().onNotificationShown();
- mCurrentNotification = notificationType;
- }
-
- private void createIncomingCallNotification(
- Call call, int state, Notification.Builder builder) {
- setNotificationWhen(call, state, builder);
-
- // Add hang up option for any active calls (active | onhold), outgoing calls (dialing).
- if (state == Call.State.ACTIVE ||
- state == Call.State.ONHOLD ||
- Call.State.isDialing(state)) {
- addHangupAction(builder);
- } else if (state == Call.State.INCOMING || state == Call.State.CALL_WAITING) {
- addDismissAction(builder);
- if (call.isVideoCall(mContext)) {
- addVoiceAction(builder);
- addVideoCallAction(builder);
- } else {
- addAnswerAction(builder);
- }
- }
- }
-
- /*
- * Sets the notification's when section as needed. For active calls, this is explicitly set as
- * the duration of the call. For all other states, the notification will automatically show the
- * time at which the notification was created.
- */
- private void setNotificationWhen(Call call, int state, Notification.Builder builder) {
- if (state == Call.State.ACTIVE) {
- builder.setUsesChronometer(true);
- builder.setWhen(call.getConnectTimeMillis());
- } else {
- builder.setUsesChronometer(false);
- }
- }
-
- /**
- * Checks the new notification data and compares it against any notification that we
- * are already displaying. If the data is exactly the same, we return false so that
- * we do not issue a new notification for the exact same data.
- */
- private boolean checkForChangeAndSaveData(int icon, String content, Bitmap largeIcon,
- String contentTitle, int state, int notificationType, Uri ringtone) {
-
- // The two are different:
- // if new title is not null, it should be different from saved version OR
- // if new title is null, the saved version should not be null
- final boolean contentTitleChanged =
- (contentTitle != null && !contentTitle.equals(mSavedContentTitle)) ||
- (contentTitle == null && mSavedContentTitle != null);
-
- // any change means we are definitely updating
- boolean retval = (mSavedIcon != icon) || !Objects.equals(mSavedContent, content)
- || (mCallState != state) || (mSavedLargeIcon != largeIcon)
- || contentTitleChanged || !Objects.equals(mRingtone, ringtone);
-
- // If we aren't showing a notification right now or the notification type is changing,
- // definitely do an update.
- if (mCurrentNotification != notificationType) {
- if (mCurrentNotification == NOTIFICATION_NONE) {
- Log.d(this, "Showing notification for first time.");
- }
- retval = true;
- }
-
- mSavedIcon = icon;
- mSavedContent = content;
- mCallState = state;
- mSavedLargeIcon = largeIcon;
- mSavedContentTitle = contentTitle;
- mRingtone = ringtone;
-
- if (retval) {
- Log.d(this, "Data changed. Showing notification");
- }
-
- return retval;
- }
-
- /**
- * Returns the main string to use in the notification.
- */
- @NeededForTesting
- String getContentTitle(ContactCacheEntry contactInfo, Call call) {
- if (call.isConferenceCall() && !call.hasProperty(Details.PROPERTY_GENERIC_CONFERENCE)) {
- return mContext.getResources().getString(R.string.card_title_conf_call);
- }
-
- String preferredName = ContactDisplayUtils.getPreferredDisplayName(contactInfo.namePrimary,
- contactInfo.nameAlternative, mContactsPreferences);
- if (TextUtils.isEmpty(preferredName)) {
- return TextUtils.isEmpty(contactInfo.number) ? null : BidiFormatter.getInstance()
- .unicodeWrap(contactInfo.number, TextDirectionHeuristics.LTR);
- }
- return preferredName;
- }
-
- private void addPersonReference(Notification.Builder builder, ContactCacheEntry contactInfo,
- Call call) {
- // Query {@link Contacts#CONTENT_LOOKUP_URI} directly with work lookup key is not allowed.
- // So, do not pass {@link Contacts#CONTENT_LOOKUP_URI} to NotificationManager to avoid
- // NotificationManager using it.
- if (contactInfo.lookupUri != null && contactInfo.userType != ContactsUtils.USER_TYPE_WORK) {
- builder.addPerson(contactInfo.lookupUri.toString());
- } else if (!TextUtils.isEmpty(call.getNumber())) {
- builder.addPerson(Uri.fromParts(PhoneAccount.SCHEME_TEL,
- call.getNumber(), null).toString());
- }
- }
-
- /**
- * Gets a large icon from the contact info object to display in the notification.
- */
- private Bitmap getLargeIconToDisplay(ContactCacheEntry contactInfo, Call call) {
- Bitmap largeIcon = null;
- if (call.isConferenceCall() && !call.hasProperty(Details.PROPERTY_GENERIC_CONFERENCE)) {
- largeIcon = BitmapFactory.decodeResource(mContext.getResources(),
- R.drawable.img_conference);
- }
- if (contactInfo.photo != null && (contactInfo.photo instanceof BitmapDrawable)) {
- largeIcon = ((BitmapDrawable) contactInfo.photo).getBitmap();
- }
- if (call.isSpam()) {
- Drawable drawable = mContext.getResources().getDrawable(R.drawable.blocked_contact);
- largeIcon = CallCardFragment.drawableToBitmap(drawable);
- }
- return largeIcon;
- }
-
- private Bitmap getRoundedIcon(Bitmap bitmap) {
- if (bitmap == null) {
- return null;
- }
- final int height = (int) mContext.getResources().getDimension(
- android.R.dimen.notification_large_icon_height);
- final int width = (int) mContext.getResources().getDimension(
- android.R.dimen.notification_large_icon_width);
- return BitmapUtil.getRoundedBitmap(bitmap, width, height);
- }
-
- /**
- * Returns the appropriate icon res Id to display based on the call for which
- * we want to display information.
- */
- private int getIconToDisplay(Call call) {
- // Even if both lines are in use, we only show a single item in
- // the expanded Notifications UI. It's labeled "Ongoing call"
- // (or "On hold" if there's only one call, and it's on hold.)
- // Also, we don't have room to display caller-id info from two
- // different calls. So if both lines are in use, display info
- // from the foreground call. And if there's a ringing call,
- // display that regardless of the state of the other calls.
- if (call.getState() == Call.State.ONHOLD) {
- return R.drawable.ic_phone_paused_white_24dp;
- } else if (call.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- return R.drawable.ic_videocam;
- }
- return R.drawable.ic_call_white_24dp;
- }
-
- /**
- * Returns the message to use with the notification.
- */
- private String getContentString(Call call, @UserType long userType) {
- boolean isIncomingOrWaiting = call.getState() == Call.State.INCOMING ||
- call.getState() == Call.State.CALL_WAITING;
-
- if (isIncomingOrWaiting &&
- call.getNumberPresentation() == TelecomManager.PRESENTATION_ALLOWED) {
-
- if (!TextUtils.isEmpty(call.getChildNumber())) {
- return mContext.getString(R.string.child_number, call.getChildNumber());
- } else if (!TextUtils.isEmpty(call.getCallSubject()) && call.isCallSubjectSupported()) {
- return call.getCallSubject();
- }
- }
-
- int resId = R.string.notification_ongoing_call;
- if (call.hasProperty(Details.PROPERTY_WIFI)) {
- resId = R.string.notification_ongoing_call_wifi;
- }
-
- if (isIncomingOrWaiting) {
- if (call.hasProperty(Details.PROPERTY_WIFI)) {
- resId = R.string.notification_incoming_call_wifi;
- } else {
- if (call.isSpam()) {
- resId = R.string.notification_incoming_spam_call;
- } else {
- resId = R.string.notification_incoming_call;
- }
- }
- } else if (call.getState() == Call.State.ONHOLD) {
- resId = R.string.notification_on_hold;
- } else if (Call.State.isDialing(call.getState())) {
- resId = R.string.notification_dialing;
- } else if (call.getSessionModificationState()
- == Call.SessionModificationState.RECEIVED_UPGRADE_TO_VIDEO_REQUEST) {
- resId = R.string.notification_requesting_video_call;
- }
-
- // Is the call placed through work connection service.
- boolean isWorkCall = call.hasProperty(PROPERTY_ENTERPRISE_CALL);
- if(userType == ContactsUtils.USER_TYPE_WORK || isWorkCall) {
- resId = getWorkStringFromPersonalString(resId);
- }
-
- return mContext.getString(resId);
- }
-
- private static int getWorkStringFromPersonalString(int resId) {
- if (resId == R.string.notification_ongoing_call) {
- return R.string.notification_ongoing_work_call;
- } else if (resId == R.string.notification_ongoing_call_wifi) {
- return R.string.notification_ongoing_work_call_wifi;
- } else if (resId == R.string.notification_incoming_call_wifi) {
- return R.string.notification_incoming_work_call_wifi;
- } else if (resId == R.string.notification_incoming_call) {
- return R.string.notification_incoming_work_call;
- } else {
- return resId;
- }
- }
-
- /**
- * Gets the most relevant call to display in the notification.
- */
- private Call getCallToShow(CallList callList) {
- if (callList == null) {
- return null;
- }
- Call call = callList.getIncomingCall();
- if (call == null) {
- call = callList.getOutgoingCall();
- }
- if (call == null) {
- call = callList.getVideoUpgradeRequestCall();
- }
- if (call == null) {
- call = callList.getActiveOrBackgroundCall();
- }
- return call;
- }
-
- private void addAnswerAction(Notification.Builder builder) {
- Log.d(this, "Will show \"answer\" action in the incoming call Notification");
-
- PendingIntent answerVoicePendingIntent = createNotificationPendingIntent(
- mContext, ACTION_ANSWER_VOICE_INCOMING_CALL);
- builder.addAction(R.drawable.ic_call_white_24dp,
- mContext.getText(R.string.notification_action_answer),
- answerVoicePendingIntent);
- }
-
- private void addDismissAction(Notification.Builder builder) {
- Log.d(this, "Will show \"dismiss\" action in the incoming call Notification");
-
- PendingIntent declinePendingIntent =
- createNotificationPendingIntent(mContext, ACTION_DECLINE_INCOMING_CALL);
- builder.addAction(R.drawable.ic_close_dk,
- mContext.getText(R.string.notification_action_dismiss),
- declinePendingIntent);
- }
-
- private void addHangupAction(Notification.Builder builder) {
- Log.d(this, "Will show \"hang-up\" action in the ongoing active call Notification");
-
- PendingIntent hangupPendingIntent =
- createNotificationPendingIntent(mContext, ACTION_HANG_UP_ONGOING_CALL);
- builder.addAction(R.drawable.ic_call_end_white_24dp,
- mContext.getText(R.string.notification_action_end_call),
- hangupPendingIntent);
- }
-
- private void addVideoCallAction(Notification.Builder builder) {
- Log.i(this, "Will show \"video\" action in the incoming call Notification");
-
- PendingIntent answerVideoPendingIntent = createNotificationPendingIntent(
- mContext, ACTION_ANSWER_VIDEO_INCOMING_CALL);
- builder.addAction(R.drawable.ic_videocam,
- mContext.getText(R.string.notification_action_answer_video),
- answerVideoPendingIntent);
- }
-
- private void addVoiceAction(Notification.Builder builder) {
- Log.d(this, "Will show \"voice\" action in the incoming call Notification");
-
- PendingIntent answerVoicePendingIntent = createNotificationPendingIntent(
- mContext, ACTION_ANSWER_VOICE_INCOMING_CALL);
- builder.addAction(R.drawable.ic_call_white_24dp,
- mContext.getText(R.string.notification_action_answer_voice),
- answerVoicePendingIntent);
- }
-
- private void addAcceptUpgradeRequestAction(Notification.Builder builder) {
- Log.i(this, "Will show \"accept upgrade\" action in the incoming call Notification");
-
- PendingIntent acceptVideoPendingIntent = createNotificationPendingIntent(
- mContext, ACTION_ACCEPT_VIDEO_UPGRADE_REQUEST);
- builder.addAction(0, mContext.getText(R.string.notification_action_accept),
- acceptVideoPendingIntent);
- }
-
- private void addDismissUpgradeRequestAction(Notification.Builder builder) {
- Log.i(this, "Will show \"dismiss upgrade\" action in the incoming call Notification");
-
- PendingIntent declineVideoPendingIntent = createNotificationPendingIntent(
- mContext, ACTION_DECLINE_VIDEO_UPGRADE_REQUEST);
- builder.addAction(0, mContext.getText(R.string.notification_action_dismiss),
- declineVideoPendingIntent);
- }
-
- /**
- * Adds fullscreen intent to the builder.
- */
- private void configureFullScreenIntent(Notification.Builder builder, PendingIntent intent,
- Call call) {
- // Ok, we actually want to launch the incoming call
- // UI at this point (in addition to simply posting a notification
- // to the status bar). Setting fullScreenIntent will cause
- // the InCallScreen to be launched immediately *unless* the
- // current foreground activity is marked as "immersive".
- Log.d(this, "- Setting fullScreenIntent: " + intent);
- builder.setFullScreenIntent(intent, true);
-
- // Ugly hack alert:
- //
- // The NotificationManager has the (undocumented) behavior
- // that it will *ignore* the fullScreenIntent field if you
- // post a new Notification that matches the ID of one that's
- // already active. Unfortunately this is exactly what happens
- // when you get an incoming call-waiting call: the
- // "ongoing call" notification is already visible, so the
- // InCallScreen won't get launched in this case!
- // (The result: if you bail out of the in-call UI while on a
- // call and then get a call-waiting call, the incoming call UI
- // won't come up automatically.)
- //
- // The workaround is to just notice this exact case (this is a
- // call-waiting call *and* the InCallScreen is not in the
- // foreground) and manually cancel the in-call notification
- // before (re)posting it.
- //
- // TODO: there should be a cleaner way of avoiding this
- // problem (see discussion in bug 3184149.)
-
- // If a call is onhold during an incoming call, the call actually comes in as
- // INCOMING. For that case *and* traditional call-waiting, we want to
- // cancel the notification.
- boolean isCallWaiting = (call.getState() == Call.State.CALL_WAITING ||
- (call.getState() == Call.State.INCOMING &&
- CallList.getInstance().getBackgroundCall() != null));
-
- if (isCallWaiting) {
- Log.i(this, "updateInCallNotification: call-waiting! force relaunch...");
- // Cancel the IN_CALL_NOTIFICATION immediately before
- // (re)posting it; this seems to force the
- // NotificationManager to launch the fullScreenIntent.
- mNotificationManager.cancel(NOTIFICATION_IN_CALL);
- }
- }
-
- private Notification.Builder getNotificationBuilder() {
- final Notification.Builder builder = new Notification.Builder(mContext);
- builder.setOngoing(true);
-
- // Make the notification prioritized over the other normal notifications.
- builder.setPriority(Notification.PRIORITY_HIGH);
-
- return builder;
- }
-
- private PendingIntent createLaunchPendingIntent(boolean isFullScreen) {
- Intent intent = InCallPresenter.getInstance().getInCallIntent(
- false /* showDialpad */, false /* newOutgoingCall */);
-
- int requestCode = PENDING_INTENT_REQUEST_CODE_NON_FULL_SCREEN;
- if (isFullScreen) {
- intent.putExtra(InCallActivity.FOR_FULL_SCREEN_INTENT, true);
- // Use a unique request code so that the pending intent isn't clobbered by the
- // non-full screen pending intent.
- requestCode = PENDING_INTENT_REQUEST_CODE_FULL_SCREEN;
- }
-
- // PendingIntent that can be used to launch the InCallActivity. The
- // system fires off this intent if the user pulls down the windowshade
- // and clicks the notification's expanded view. It's also used to
- // launch the InCallActivity immediately when when there's an incoming
- // call (see the "fullScreenIntent" field below).
- return PendingIntent.getActivity(mContext, requestCode, intent, 0);
- }
-
- /**
- * Returns PendingIntent for answering a phone call. This will typically be used from
- * Notification context.
- */
- private static PendingIntent createNotificationPendingIntent(Context context, String action) {
- final Intent intent = new Intent(action, null,
- context, NotificationBroadcastReceiver.class);
- return PendingIntent.getBroadcast(context, 0, intent, 0);
- }
-
- @Override
- public void onCallChanged(Call call) {
- if (CallList.getInstance().getIncomingCall() == null) {
- mDialerRingtoneManager.stopCallWaitingTone();
- }
- }
-
- /**
- * Responds to changes in the session modification state for the call by dismissing the
- * status bar notification as required.
- *
- * @param sessionModificationState The new session modification state.
- */
- @Override
- public void onSessionModificationStateChange(int sessionModificationState) {
- if (sessionModificationState == Call.SessionModificationState.NO_REQUEST) {
- if (mCallId != null) {
- CallList.getInstance().removeCallUpdateListener(mCallId, this);
- }
-
- updateNotification(mInCallState, CallList.getInstance());
- }
- }
-
- @Override
- public void onLastForwardedNumberChange() {
- // no-op
- }
-
- @Override
- public void onChildNumberChange() {
- // no-op
- }
-}
diff --git a/InCallUI/src/com/android/incallui/TelecomAdapter.java b/InCallUI/src/com/android/incallui/TelecomAdapter.java
deleted file mode 100644
index f172270ddfc07a937da435a3d437a8b938a6c291..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/TelecomAdapter.java
+++ /dev/null
@@ -1,226 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.google.common.base.Preconditions;
-
-import android.content.ActivityNotFoundException;
-import android.content.Intent;
-import android.os.Looper;
-import android.telecom.InCallService;
-import android.telecom.PhoneAccountHandle;
-
-import java.util.List;
-
-final class TelecomAdapter implements InCallServiceListener {
- private static final String ADD_CALL_MODE_KEY = "add_call_mode";
-
- private static TelecomAdapter sInstance;
- private InCallService mInCallService;
-
- static TelecomAdapter getInstance() {
- Preconditions.checkState(Looper.getMainLooper().getThread() == Thread.currentThread());
- if (sInstance == null) {
- sInstance = new TelecomAdapter();
- }
- return sInstance;
- }
-
- private TelecomAdapter() {
- }
-
- @Override
- public void setInCallService(InCallService inCallService) {
- mInCallService = inCallService;
- }
-
- @Override
- public void clearInCallService() {
- mInCallService = null;
- }
-
- private android.telecom.Call getTelecomCallById(String callId) {
- Call call = CallList.getInstance().getCallById(callId);
- return call == null ? null : call.getTelecomCall();
- }
-
- void answerCall(String callId, int videoState) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.answer(videoState);
- } else {
- Log.e(this, "error answerCall, call not in call list: " + callId);
- }
- }
-
- void rejectCall(String callId, boolean rejectWithMessage, String message) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.reject(rejectWithMessage, message);
- } else {
- Log.e(this, "error rejectCall, call not in call list: " + callId);
- }
- }
-
- void disconnectCall(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.disconnect();
- } else {
- Log.e(this, "error disconnectCall, call not in call list " + callId);
- }
- }
-
- void holdCall(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.hold();
- } else {
- Log.e(this, "error holdCall, call not in call list " + callId);
- }
- }
-
- void unholdCall(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.unhold();
- } else {
- Log.e(this, "error unholdCall, call not in call list " + callId);
- }
- }
-
- void mute(boolean shouldMute) {
- if (mInCallService != null) {
- mInCallService.setMuted(shouldMute);
- } else {
- Log.e(this, "error mute, mInCallService is null");
- }
- }
-
- void setAudioRoute(int route) {
- if (mInCallService != null) {
- mInCallService.setAudioRoute(route);
- } else {
- Log.e(this, "error setAudioRoute, mInCallService is null");
- }
- }
-
- void separateCall(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.splitFromConference();
- } else {
- Log.e(this, "error separateCall, call not in call list " + callId);
- }
- }
-
- void merge(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- List conferenceable = call.getConferenceableCalls();
- if (!conferenceable.isEmpty()) {
- call.conference(conferenceable.get(0));
- } else {
- if (call.getDetails().can(android.telecom.Call.Details.CAPABILITY_MERGE_CONFERENCE)) {
- call.mergeConference();
- }
- }
- } else {
- Log.e(this, "error merge, call not in call list " + callId);
- }
- }
-
- void swap(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- if (call.getDetails().can(android.telecom.Call.Details.CAPABILITY_SWAP_CONFERENCE)) {
- call.swapConference();
- }
- } else {
- Log.e(this, "error swap, call not in call list " + callId);
- }
- }
-
- void addCall() {
- if (mInCallService != null) {
- Intent intent = new Intent(Intent.ACTION_DIAL);
- intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-
- // when we request the dialer come up, we also want to inform
- // it that we're going through the "add call" option from the
- // InCallScreen / PhoneUtils.
- intent.putExtra(ADD_CALL_MODE_KEY, true);
- try {
- Log.d(this, "Sending the add Call intent");
- mInCallService.startActivity(intent);
- } catch (ActivityNotFoundException e) {
- // This is rather rare but possible.
- // Note: this method is used even when the phone is encrypted. At that moment
- // the system may not find any Activity which can accept this Intent.
- Log.e(this, "Activity for adding calls isn't found.", e);
- }
- }
- }
-
- void playDtmfTone(String callId, char digit) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.playDtmfTone(digit);
- } else {
- Log.e(this, "error playDtmfTone, call not in call list " + callId);
- }
- }
-
- void stopDtmfTone(String callId) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.stopDtmfTone();
- } else {
- Log.e(this, "error stopDtmfTone, call not in call list " + callId);
- }
- }
-
- void postDialContinue(String callId, boolean proceed) {
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.postDialContinue(proceed);
- } else {
- Log.e(this, "error postDialContinue, call not in call list " + callId);
- }
- }
-
- void phoneAccountSelected(String callId, PhoneAccountHandle accountHandle, boolean setDefault) {
- if (accountHandle == null) {
- Log.e(this, "error phoneAccountSelected, accountHandle is null");
- // TODO: Do we really want to send null accountHandle?
- }
-
- android.telecom.Call call = getTelecomCallById(callId);
- if (call != null) {
- call.phoneAccountSelected(accountHandle, setDefault);
- } else {
- Log.e(this, "error phoneAccountSelected, call not in call list " + callId);
- }
- }
-
- boolean canAddCall() {
- if (mInCallService != null) {
- return mInCallService.canAddCall();
- }
- return false;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/VideoCallFragment.java b/InCallUI/src/com/android/incallui/VideoCallFragment.java
deleted file mode 100644
index 6a46a423d3668d0522fe9317035cc43ca2e3f004..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/VideoCallFragment.java
+++ /dev/null
@@ -1,901 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.graphics.Matrix;
-import android.graphics.Point;
-import android.graphics.SurfaceTexture;
-import android.os.Bundle;
-import android.view.Display;
-import android.view.LayoutInflater;
-import android.view.Surface;
-import android.view.TextureView;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewStub;
-import android.view.ViewTreeObserver;
-import android.widget.FrameLayout;
-import android.widget.ImageView;
-
-import com.android.dialer.R;
-import com.android.phone.common.animation.AnimUtils;
-import com.google.common.base.Objects;
-
-/**
- * Fragment containing video calling surfaces.
- */
-public class VideoCallFragment extends BaseFragment implements VideoCallPresenter.VideoCallUi {
- private static final String TAG = VideoCallFragment.class.getSimpleName();
- private static final boolean DEBUG = false;
-
- /**
- * Used to indicate that the surface dimensions are not set.
- */
- private static final int DIMENSIONS_NOT_SET = -1;
-
- /**
- * Surface ID for the display surface.
- */
- public static final int SURFACE_DISPLAY = 1;
-
- /**
- * Surface ID for the preview surface.
- */
- public static final int SURFACE_PREVIEW = 2;
-
- /**
- * Used to indicate that the UI rotation is unknown.
- */
- public static final int ORIENTATION_UNKNOWN = -1;
-
- // Static storage used to retain the video surfaces across Activity restart.
- // TextureViews are not parcelable, so it is not possible to store them in the saved state.
- private static boolean sVideoSurfacesInUse = false;
- private static VideoCallSurface sPreviewSurface = null;
- private static VideoCallSurface sDisplaySurface = null;
- private static Point sDisplaySize = null;
-
- /**
- * {@link ViewStub} holding the video call surfaces. This is the parent for the
- * {@link VideoCallFragment}. Used to ensure that the video surfaces are only inflated when
- * required.
- */
- private ViewStub mVideoViewsStub;
-
- /**
- * Inflated view containing the video call surfaces represented by the {@link ViewStub}.
- */
- private View mVideoViews;
-
- /**
- * The {@link FrameLayout} containing the preview surface.
- */
- private View mPreviewVideoContainer;
-
- /**
- * Icon shown to indicate that the outgoing camera has been turned off.
- */
- private View mCameraOff;
-
- /**
- * {@link ImageView} containing the user's profile photo.
- */
- private ImageView mPreviewPhoto;
-
- /**
- * {@code True} when the layout of the activity has been completed.
- */
- private boolean mIsLayoutComplete = false;
-
- /**
- * {@code True} if in landscape mode.
- */
- private boolean mIsLandscape;
-
- private int mAnimationDuration;
-
- /**
- * Inner-class representing a {@link TextureView} and its associated {@link SurfaceTexture} and
- * {@link Surface}. Used to manage the lifecycle of these objects across device orientation
- * changes.
- */
- private static class VideoCallSurface implements TextureView.SurfaceTextureListener,
- View.OnClickListener, View.OnAttachStateChangeListener {
- private int mSurfaceId;
- private VideoCallPresenter mPresenter;
- private TextureView mTextureView;
- private SurfaceTexture mSavedSurfaceTexture;
- private Surface mSavedSurface;
- private boolean mIsDoneWithSurface;
- private int mWidth = DIMENSIONS_NOT_SET;
- private int mHeight = DIMENSIONS_NOT_SET;
-
- /**
- * Creates an instance of a {@link VideoCallSurface}.
- *
- * @param surfaceId The surface ID of the surface.
- * @param textureView The {@link TextureView} for the surface.
- */
- public VideoCallSurface(VideoCallPresenter presenter, int surfaceId,
- TextureView textureView) {
- this(presenter, surfaceId, textureView, DIMENSIONS_NOT_SET, DIMENSIONS_NOT_SET);
- }
-
- /**
- * Creates an instance of a {@link VideoCallSurface}.
- *
- * @param surfaceId The surface ID of the surface.
- * @param textureView The {@link TextureView} for the surface.
- * @param width The width of the surface.
- * @param height The height of the surface.
- */
- public VideoCallSurface(VideoCallPresenter presenter,int surfaceId, TextureView textureView,
- int width, int height) {
- Log.d(this, "VideoCallSurface: surfaceId=" + surfaceId +
- " width=" + width + " height=" + height);
- mPresenter = presenter;
- mWidth = width;
- mHeight = height;
- mSurfaceId = surfaceId;
-
- recreateView(textureView);
- }
-
- /**
- * Recreates a {@link VideoCallSurface} after a device orientation change. Re-applies the
- * saved {@link SurfaceTexture} to the
- *
- * @param view The {@link TextureView}.
- */
- public void recreateView(TextureView view) {
- if (DEBUG) {
- Log.i(TAG, "recreateView: " + view);
- }
-
- if (mTextureView == view) {
- return;
- }
-
- mTextureView = view;
- mTextureView.setSurfaceTextureListener(this);
- mTextureView.setOnClickListener(this);
-
- final boolean areSameSurfaces =
- Objects.equal(mSavedSurfaceTexture, mTextureView.getSurfaceTexture());
- Log.d(this, "recreateView: SavedSurfaceTexture=" + mSavedSurfaceTexture
- + " areSameSurfaces=" + areSameSurfaces);
- if (mSavedSurfaceTexture != null && !areSameSurfaces) {
- mTextureView.setSurfaceTexture(mSavedSurfaceTexture);
- if (createSurface(mWidth, mHeight)) {
- onSurfaceCreated();
- }
- }
- mIsDoneWithSurface = false;
- }
-
- public void resetPresenter(VideoCallPresenter presenter) {
- Log.d(this, "resetPresenter: CurrentPresenter=" + mPresenter + " NewPresenter="
- + presenter);
- mPresenter = presenter;
- }
-
- /**
- * Handles {@link SurfaceTexture} callback to indicate that a {@link SurfaceTexture} has
- * been successfully created.
- *
- * @param surfaceTexture The {@link SurfaceTexture} which has been created.
- * @param width The width of the {@link SurfaceTexture}.
- * @param height The height of the {@link SurfaceTexture}.
- */
- @Override
- public void onSurfaceTextureAvailable(SurfaceTexture surfaceTexture, int width,
- int height) {
- boolean surfaceCreated;
- if (DEBUG) {
- Log.i(TAG, "onSurfaceTextureAvailable: " + surfaceTexture);
- }
- // Where there is no saved {@link SurfaceTexture} available, use the newly created one.
- // If a saved {@link SurfaceTexture} is available, we are re-creating after an
- // orientation change.
- Log.d(this, " onSurfaceTextureAvailable mSurfaceId=" + mSurfaceId + " surfaceTexture="
- + surfaceTexture + " width=" + width
- + " height=" + height + " mSavedSurfaceTexture=" + mSavedSurfaceTexture);
- Log.d(this, " onSurfaceTextureAvailable VideoCallPresenter=" + mPresenter);
- if (mSavedSurfaceTexture == null) {
- mSavedSurfaceTexture = surfaceTexture;
- surfaceCreated = createSurface(width, height);
- } else {
- // A saved SurfaceTexture was found.
- Log.d(this, " onSurfaceTextureAvailable: Replacing with cached surface...");
- mTextureView.setSurfaceTexture(mSavedSurfaceTexture);
- surfaceCreated = true;
- }
-
- // Inform presenter that the surface is available.
- if (surfaceCreated) {
- onSurfaceCreated();
- }
- }
-
- private void onSurfaceCreated() {
- if (mPresenter != null) {
- mPresenter.onSurfaceCreated(mSurfaceId);
- } else {
- Log.e(this, "onSurfaceTextureAvailable: Presenter is null");
- }
- }
-
- /**
- * Handles a change in the {@link SurfaceTexture}'s size.
- *
- * @param surfaceTexture The {@link SurfaceTexture}.
- * @param width The new width.
- * @param height The new height.
- */
- @Override
- public void onSurfaceTextureSizeChanged(SurfaceTexture surfaceTexture, int width,
- int height) {
- // Not handled
- }
-
- /**
- * Handles {@link SurfaceTexture} destruct callback, indicating that it has been destroyed.
- *
- * @param surfaceTexture The {@link SurfaceTexture}.
- * @return {@code True} if the {@link TextureView} can release the {@link SurfaceTexture}.
- */
- @Override
- public boolean onSurfaceTextureDestroyed(SurfaceTexture surfaceTexture) {
- /**
- * Destroying the surface texture; inform the presenter so it can null the surfaces.
- */
- Log.d(this, " onSurfaceTextureDestroyed mSurfaceId=" + mSurfaceId + " surfaceTexture="
- + surfaceTexture + " SavedSurfaceTexture=" + mSavedSurfaceTexture
- + " SavedSurface=" + mSavedSurface);
- Log.d(this, " onSurfaceTextureDestroyed VideoCallPresenter=" + mPresenter);
-
- // Notify presenter if it is not null.
- onSurfaceDestroyed();
-
- if (mIsDoneWithSurface) {
- onSurfaceReleased();
- if (mSavedSurface != null) {
- mSavedSurface.release();
- mSavedSurface = null;
- }
- }
- return mIsDoneWithSurface;
- }
-
- private void onSurfaceDestroyed() {
- if (mPresenter != null) {
- mPresenter.onSurfaceDestroyed(mSurfaceId);
- } else {
- Log.e(this, "onSurfaceTextureDestroyed: Presenter is null.");
- }
- }
-
- /**
- * Handles {@link SurfaceTexture} update callback.
- * @param surface
- */
- @Override
- public void onSurfaceTextureUpdated(SurfaceTexture surface) {
- // Not Handled
- }
-
- @Override
- public void onViewAttachedToWindow(View v) {
- if (DEBUG) {
- Log.i(TAG, "OnViewAttachedToWindow");
- }
- if (mSavedSurfaceTexture != null) {
- mTextureView.setSurfaceTexture(mSavedSurfaceTexture);
- }
- }
-
- @Override
- public void onViewDetachedFromWindow(View v) {}
-
- /**
- * Retrieves the current {@link TextureView}.
- *
- * @return The {@link TextureView}.
- */
- public TextureView getTextureView() {
- return mTextureView;
- }
-
- /**
- * Called by the user presenter to indicate that the surface is no longer required due to a
- * change in video state. Releases and clears out the saved surface and surface textures.
- */
- public void setDoneWithSurface() {
- Log.d(this, "setDoneWithSurface: SavedSurface=" + mSavedSurface
- + " SavedSurfaceTexture=" + mSavedSurfaceTexture);
- mIsDoneWithSurface = true;
- if (mTextureView != null && mTextureView.isAvailable()) {
- return;
- }
-
- if (mSavedSurface != null) {
- onSurfaceReleased();
- mSavedSurface.release();
- mSavedSurface = null;
- }
- if (mSavedSurfaceTexture != null) {
- mSavedSurfaceTexture.release();
- mSavedSurfaceTexture = null;
- }
- }
-
- private void onSurfaceReleased() {
- if (mPresenter != null) {
- mPresenter.onSurfaceReleased(mSurfaceId);
- } else {
- Log.d(this, "setDoneWithSurface: Presenter is null.");
- }
- }
-
- /**
- * Retrieves the saved surface instance.
- *
- * @return The surface.
- */
- public Surface getSurface() {
- return mSavedSurface;
- }
-
- /**
- * Sets the dimensions of the surface.
- *
- * @param width The width of the surface, in pixels.
- * @param height The height of the surface, in pixels.
- */
- public void setSurfaceDimensions(int width, int height) {
- Log.d(this, "setSurfaceDimensions, width=" + width + " height=" + height);
- mWidth = width;
- mHeight = height;
-
- if (width != DIMENSIONS_NOT_SET && height != DIMENSIONS_NOT_SET
- && mSavedSurfaceTexture != null) {
- Log.d(this, "setSurfaceDimensions, mSavedSurfaceTexture is NOT equal to null.");
- mSavedSurfaceTexture.setDefaultBufferSize(width, height);
- }
- }
-
- /**
- * Creates the {@link Surface}, adjusting the {@link SurfaceTexture} buffer size.
- * @param width The width of the surface to create.
- * @param height The height of the surface to create.
- */
- private boolean createSurface(int width, int height) {
- Log.d(this, "createSurface mSavedSurfaceTexture=" + mSavedSurfaceTexture
- + " mSurfaceId =" + mSurfaceId + " mWidth " + width + " mHeight=" + height);
- if (width != DIMENSIONS_NOT_SET && height != DIMENSIONS_NOT_SET
- && mSavedSurfaceTexture != null) {
- mSavedSurfaceTexture.setDefaultBufferSize(width, height);
- mSavedSurface = new Surface(mSavedSurfaceTexture);
- return true;
- }
- return false;
- }
-
- /**
- * Handles a user clicking the surface, which is the trigger to toggle the full screen
- * Video UI.
- *
- * @param view The view receiving the click.
- */
- @Override
- public void onClick(View view) {
- if (mPresenter != null) {
- mPresenter.onSurfaceClick(mSurfaceId);
- } else {
- Log.e(this, "onClick: Presenter is null.");
- }
- }
-
- /**
- * Returns the dimensions of the surface.
- *
- * @return The dimensions of the surface.
- */
- public Point getSurfaceDimensions() {
- return new Point(mWidth, mHeight);
- }
- };
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- mAnimationDuration = getResources().getInteger(R.integer.video_animation_duration);
- }
-
- /**
- * Handles creation of the activity and initialization of the presenter.
- *
- * @param savedInstanceState The saved instance state.
- */
- @Override
- public void onActivityCreated(Bundle savedInstanceState) {
- mIsLandscape = getResources().getBoolean(R.bool.is_layout_landscape);
- Log.d(this, "onActivityCreated: IsLandscape=" + mIsLandscape);
- getPresenter().init(getActivity());
-
- super.onActivityCreated(savedInstanceState);
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- super.onCreateView(inflater, container, savedInstanceState);
-
- final View view = inflater.inflate(R.layout.video_call_fragment, container, false);
-
- return view;
- }
-
- /**
- * Centers the display view vertically for portrait orientations. The view is centered within
- * the available space not occupied by the call card. This is a no-op for landscape mode.
- *
- * @param displayVideo The video view to center.
- */
- private void centerDisplayView(View displayVideo) {
- if (!mIsLandscape) {
- ViewGroup.LayoutParams p = displayVideo.getLayoutParams();
- int height = p.height;
-
- float spaceBesideCallCard = InCallPresenter.getInstance().getSpaceBesideCallCard();
- // If space beside call card is zeo, layout hasn't happened yet so there is no point
- // in attempting to center the view.
- if (Math.abs(spaceBesideCallCard - 0.0f) < 0.0001) {
- return;
- }
- float videoViewTranslation = height / 2 - spaceBesideCallCard / 2;
- displayVideo.setTranslationY(videoViewTranslation);
- }
- }
-
- /**
- * After creation of the fragment view, retrieves the required views.
- *
- * @param view The fragment view.
- * @param savedInstanceState The saved instance state.
- */
- @Override
- public void onViewCreated(View view, Bundle savedInstanceState) {
- super.onViewCreated(view, savedInstanceState);
- Log.d(this, "onViewCreated: VideoSurfacesInUse=" + sVideoSurfacesInUse);
-
- mVideoViewsStub = (ViewStub) view.findViewById(R.id.videoCallViewsStub);
- }
-
- @Override
- public void onStop() {
- super.onStop();
- Log.d(this, "onStop:");
- }
-
- @Override
- public void onPause() {
- super.onPause();
- Log.d(this, "onPause:");
- getPresenter().cancelAutoFullScreen();
- }
-
- @Override
- public void onDestroyView() {
- super.onDestroyView();
- Log.d(this, "onDestroyView:");
- }
-
- /**
- * Creates the presenter for the {@link VideoCallFragment}.
- * @return The presenter instance.
- */
- @Override
- public VideoCallPresenter createPresenter() {
- Log.d(this, "createPresenter");
- VideoCallPresenter presenter = new VideoCallPresenter();
- onPresenterChanged(presenter);
- return presenter;
- }
-
- /**
- * @return The user interface for the presenter, which is this fragment.
- */
- @Override
- public VideoCallPresenter.VideoCallUi getUi() {
- return this;
- }
-
- /**
- * Inflate video surfaces.
- *
- * @param show {@code True} if the video surfaces should be shown.
- */
- private void inflateVideoUi(boolean show) {
- int visibility = show ? View.VISIBLE : View.GONE;
- getView().setVisibility(visibility);
-
- if (show) {
- inflateVideoCallViews();
- }
-
- if (mVideoViews != null) {
- mVideoViews.setVisibility(visibility);
- }
- }
-
- /**
- * Hides and shows the incoming video view and changes the outgoing video view's state based on
- * whether outgoing view is enabled or not.
- */
- @Override
- public void showVideoViews(boolean previewPaused, boolean showIncoming) {
- inflateVideoUi(true);
-
- View incomingVideoView = mVideoViews.findViewById(R.id.incomingVideo);
- if (incomingVideoView != null) {
- incomingVideoView.setVisibility(showIncoming ? View.VISIBLE : View.INVISIBLE);
- }
- if (mCameraOff != null) {
- mCameraOff.setVisibility(!previewPaused ? View.VISIBLE : View.INVISIBLE);
- }
- if (mPreviewPhoto != null) {
- mPreviewPhoto.setVisibility(!previewPaused ? View.VISIBLE : View.INVISIBLE);
- }
- }
-
- /**
- * Hide all video views.
- */
- @Override
- public void hideVideoUi() {
- inflateVideoUi(false);
- }
-
- /**
- * Cleans up the video telephony surfaces. Used when the presenter indicates a change to an
- * audio-only state. Since the surfaces are static, it is important to ensure they are cleaned
- * up promptly.
- */
- @Override
- public void cleanupSurfaces() {
- Log.d(this, "cleanupSurfaces");
- if (sDisplaySurface != null) {
- sDisplaySurface.setDoneWithSurface();
- sDisplaySurface = null;
- }
- if (sPreviewSurface != null) {
- sPreviewSurface.setDoneWithSurface();
- sPreviewSurface = null;
- }
- sVideoSurfacesInUse = false;
- }
-
- @Override
- public ImageView getPreviewPhotoView() {
- return mPreviewPhoto;
- }
-
- /**
- * Adjusts the location of the video preview view by the specified offset.
- *
- * @param shiftUp {@code true} if the preview should shift up, {@code false} if it should shift
- * down.
- * @param offset The offset.
- */
- @Override
- public void adjustPreviewLocation(boolean shiftUp, int offset) {
- if (sPreviewSurface == null || mPreviewVideoContainer == null) {
- return;
- }
-
- // Set the position of the secondary call info card to its starting location.
- mPreviewVideoContainer.setTranslationY(shiftUp ? 0 : -offset);
-
- // Animate the secondary card info slide up/down as it appears and disappears.
- mPreviewVideoContainer.animate()
- .setInterpolator(AnimUtils.EASE_OUT_EASE_IN)
- .setDuration(mAnimationDuration)
- .translationY(shiftUp ? -offset : 0)
- .start();
- }
-
- private void onPresenterChanged(VideoCallPresenter presenter) {
- Log.d(this, "onPresenterChanged: Presenter=" + presenter);
- if (sDisplaySurface != null) {
- sDisplaySurface.resetPresenter(presenter);;
- }
- if (sPreviewSurface != null) {
- sPreviewSurface.resetPresenter(presenter);
- }
- }
-
- /**
- * @return {@code True} if the display video surface has been created.
- */
- @Override
- public boolean isDisplayVideoSurfaceCreated() {
- boolean ret = sDisplaySurface != null && sDisplaySurface.getSurface() != null;
- Log.d(this, " isDisplayVideoSurfaceCreated returns " + ret);
- return ret;
- }
-
- /**
- * @return {@code True} if the preview video surface has been created.
- */
- @Override
- public boolean isPreviewVideoSurfaceCreated() {
- boolean ret = sPreviewSurface != null && sPreviewSurface.getSurface() != null;
- Log.d(this, " isPreviewVideoSurfaceCreated returns " + ret);
- return ret;
- }
-
- /**
- * {@link android.view.Surface} on which incoming video for a video call is displayed.
- * {@code Null} until the video views {@link android.view.ViewStub} is inflated.
- */
- @Override
- public Surface getDisplayVideoSurface() {
- return sDisplaySurface == null ? null : sDisplaySurface.getSurface();
- }
-
- /**
- * {@link android.view.Surface} on which a preview of the outgoing video for a video call is
- * displayed. {@code Null} until the video views {@link android.view.ViewStub} is inflated.
- */
- @Override
- public Surface getPreviewVideoSurface() {
- return sPreviewSurface == null ? null : sPreviewSurface.getSurface();
- }
-
- /**
- * Changes the dimensions of the preview surface. Called when the dimensions change due to a
- * device orientation change.
- *
- * @param width The new width.
- * @param height The new height.
- */
- @Override
- public void setPreviewSize(int width, int height) {
- Log.d(this, "setPreviewSize: width=" + width + " height=" + height);
- if (sPreviewSurface != null) {
- TextureView preview = sPreviewSurface.getTextureView();
-
- if (preview == null ) {
- return;
- }
-
- // Set the dimensions of both the video surface and the FrameLayout containing it.
- ViewGroup.LayoutParams params = preview.getLayoutParams();
- params.width = width;
- params.height = height;
- preview.setLayoutParams(params);
-
- if (mPreviewVideoContainer != null) {
- ViewGroup.LayoutParams containerParams = mPreviewVideoContainer.getLayoutParams();
- containerParams.width = width;
- containerParams.height = height;
- mPreviewVideoContainer.setLayoutParams(containerParams);
- }
-
- // The width and height are interchanged outside of this method based on the current
- // orientation, so we can transform using "width", which will be either the width or
- // the height.
- Matrix transform = new Matrix();
- transform.setScale(-1, 1, width/2, 0);
- preview.setTransform(transform);
- }
- }
-
- /**
- * Sets the rotation of the preview surface. Called when the dimensions change due to a
- * device orientation change.
- *
- * Please note that the screen orientation passed in is subtracted from 360 to get the actual
- * preview rotation values.
- *
- * @param rotation The screen orientation. One of -
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_0},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_90},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_180},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_270}).
- */
- @Override
- public void setPreviewRotation(int orientation) {
- Log.d(this, "setPreviewRotation: orientation=" + orientation);
- if (sPreviewSurface != null) {
- TextureView preview = sPreviewSurface.getTextureView();
-
- if (preview == null ) {
- return;
- }
-
- preview.setRotation(orientation);
- }
- }
-
- @Override
- public void setPreviewSurfaceSize(int width, int height) {
- final boolean isPreviewSurfaceAvailable = sPreviewSurface != null;
- Log.d(this, "setPreviewSurfaceSize: width=" + width + " height=" + height +
- " isPreviewSurfaceAvailable=" + isPreviewSurfaceAvailable);
- if (isPreviewSurfaceAvailable) {
- sPreviewSurface.setSurfaceDimensions(width, height);
- }
- }
-
- /**
- * returns UI's current orientation.
- */
- @Override
- public int getCurrentRotation() {
- try {
- return getActivity().getWindowManager().getDefaultDisplay().getRotation();
- } catch (Exception e) {
- Log.e(this, "getCurrentRotation: Retrieving current rotation failed. Ex=" + e);
- }
- return ORIENTATION_UNKNOWN;
- }
-
- /**
- * Changes the dimensions of the display video surface. Called when the dimensions change due to
- * a peer resolution update
- *
- * @param width The new width.
- * @param height The new height.
- */
- @Override
- public void setDisplayVideoSize(int width, int height) {
- Log.v(this, "setDisplayVideoSize: width=" + width + " height=" + height);
- if (sDisplaySurface != null) {
- TextureView displayVideo = sDisplaySurface.getTextureView();
- if (displayVideo == null) {
- Log.e(this, "Display Video texture view is null. Bail out");
- return;
- }
- sDisplaySize = new Point(width, height);
- setSurfaceSizeAndTranslation(displayVideo, sDisplaySize);
- } else {
- Log.e(this, "Display Video Surface is null. Bail out");
- }
- }
-
- /**
- * Determines the size of the device screen.
- *
- * @return {@link Point} specifying the width and height of the screen.
- */
- @Override
- public Point getScreenSize() {
- // Get current screen size.
- Display display = getActivity().getWindowManager().getDefaultDisplay();
- Point size = new Point();
- display.getSize(size);
-
- return size;
- }
-
- /**
- * Determines the size of the preview surface.
- *
- * @return {@link Point} specifying the width and height of the preview surface.
- */
- @Override
- public Point getPreviewSize() {
- if (sPreviewSurface == null) {
- return null;
- }
- return sPreviewSurface.getSurfaceDimensions();
- }
-
- /**
- * Inflates the {@link ViewStub} containing the incoming and outgoing surfaces, if necessary,
- * and creates {@link VideoCallSurface} instances to track the surfaces.
- */
- private void inflateVideoCallViews() {
- Log.d(this, "inflateVideoCallViews");
- if (mVideoViews == null ) {
- mVideoViews = mVideoViewsStub.inflate();
- }
-
- if (mVideoViews != null) {
- mPreviewVideoContainer = mVideoViews.findViewById(R.id.previewVideoContainer);
- mCameraOff = mVideoViews.findViewById(R.id.previewCameraOff);
- mPreviewPhoto = (ImageView) mVideoViews.findViewById(R.id.previewProfilePhoto);
-
- TextureView displaySurface = (TextureView) mVideoViews.findViewById(R.id.incomingVideo);
-
- Log.d(this, "inflateVideoCallViews: sVideoSurfacesInUse=" + sVideoSurfacesInUse);
- //If peer adjusted screen size is not available, set screen size to default display size
- Point screenSize = sDisplaySize == null ? getScreenSize() : sDisplaySize;
- setSurfaceSizeAndTranslation(displaySurface, screenSize);
-
- if (!sVideoSurfacesInUse) {
- // Where the video surfaces are not already in use (first time creating them),
- // setup new VideoCallSurface instances to track them.
- Log.d(this, " inflateVideoCallViews screenSize" + screenSize);
-
- sDisplaySurface = new VideoCallSurface(getPresenter(), SURFACE_DISPLAY,
- (TextureView) mVideoViews.findViewById(R.id.incomingVideo), screenSize.x,
- screenSize.y);
- sPreviewSurface = new VideoCallSurface(getPresenter(), SURFACE_PREVIEW,
- (TextureView) mVideoViews.findViewById(R.id.previewVideo));
- sVideoSurfacesInUse = true;
- } else {
- // In this case, the video surfaces are already in use (we are recreating the
- // Fragment after a destroy/create cycle resulting from a rotation.
- sDisplaySurface.recreateView((TextureView) mVideoViews.findViewById(
- R.id.incomingVideo));
- sPreviewSurface.recreateView((TextureView) mVideoViews.findViewById(
- R.id.previewVideo));
- }
-
- // Attempt to center the incoming video view, if it is in the layout.
- final ViewTreeObserver observer = mVideoViews.getViewTreeObserver();
- observer.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
- @Override
- public void onGlobalLayout() {
- // Check if the layout includes the incoming video surface -- this will only be the
- // case for a video call.
- View displayVideo = mVideoViews.findViewById(R.id.incomingVideo);
- if (displayVideo != null) {
- centerDisplayView(displayVideo);
- }
- mIsLayoutComplete = true;
-
- // Remove the listener so we don't continually re-layout.
- ViewTreeObserver observer = mVideoViews.getViewTreeObserver();
- if (observer.isAlive()) {
- observer.removeOnGlobalLayoutListener(this);
- }
- }
- });
- }
- }
-
- /**
- * Resizes a surface so that it has the same size as the full screen and so that it is
- * centered vertically below the call card.
- *
- * @param textureView The {@link TextureView} to resize and position.
- * @param size The size of the screen.
- */
- private void setSurfaceSizeAndTranslation(TextureView textureView, Point size) {
- // Set the surface to have that size.
- ViewGroup.LayoutParams params = textureView.getLayoutParams();
- params.width = size.x;
- params.height = size.y;
- textureView.setLayoutParams(params);
- Log.d(this, "setSurfaceSizeAndTranslation: Size=" + size + "IsLayoutComplete=" +
- mIsLayoutComplete + "IsLandscape=" + mIsLandscape);
-
- // It is only possible to center the display view if layout of the views has completed.
- // It is only after layout is complete that the dimensions of the Call Card has been
- // established, which is a prerequisite to centering the view.
- // Incoming video calls will center the view
- if (mIsLayoutComplete) {
- centerDisplayView(textureView);
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/VideoCallPresenter.java b/InCallUI/src/com/android/incallui/VideoCallPresenter.java
deleted file mode 100644
index 06e3e444070959a4829634e6c11636d092e4039d..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/VideoCallPresenter.java
+++ /dev/null
@@ -1,1306 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.content.Context;
-import android.database.Cursor;
-import android.graphics.Point;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Handler;
-import android.os.Looper;
-import android.provider.ContactsContract;
-import android.telecom.Connection;
-import android.telecom.InCallService.VideoCall;
-import android.telecom.VideoProfile;
-import android.telecom.VideoProfile.CameraCapabilities;
-import android.view.Surface;
-import android.widget.ImageView;
-
-import com.android.contacts.common.ContactPhotoManager;
-import com.android.contacts.common.compat.CompatUtils;
-import com.android.dialer.R;
-import com.android.incallui.InCallPresenter.InCallDetailsListener;
-import com.android.incallui.InCallPresenter.InCallOrientationListener;
-import com.android.incallui.InCallPresenter.InCallStateListener;
-import com.android.incallui.InCallPresenter.IncomingCallListener;
-import com.android.incallui.InCallVideoCallCallbackNotifier.SurfaceChangeListener;
-import com.android.incallui.InCallVideoCallCallbackNotifier.VideoEventListener;
-
-import java.util.Objects;
-
-/**
- * Logic related to the {@link VideoCallFragment} and for managing changes to the video calling
- * surfaces based on other user interface events and incoming events from the
- * {@class VideoCallListener}.
- *
- * When a call's video state changes to bi-directional video, the
- * {@link com.android.incallui.VideoCallPresenter} performs the following negotiation with the
- * telephony layer:
- *
- *
{@code VideoCallPresenter} creates and informs telephony of the display surface.
- *
{@code VideoCallPresenter} creates the preview surface.
- *
{@code VideoCallPresenter} informs telephony of the currently selected camera.
- *
Telephony layer sends {@link CameraCapabilities}, including the
- * dimensions of the video for the current camera.
- *
{@code VideoCallPresenter} adjusts size of the preview surface to match the aspect
- * ratio of the camera.
- *
{@code VideoCallPresenter} informs telephony of the new preview surface.
- *
- *
- * When downgrading to an audio-only video state, the {@code VideoCallPresenter} nulls both
- * surfaces.
- */
-public class VideoCallPresenter extends Presenter implements
- IncomingCallListener, InCallOrientationListener, InCallStateListener,
- InCallDetailsListener, SurfaceChangeListener, VideoEventListener,
- InCallPresenter.InCallEventListener {
- public static final String TAG = "VideoCallPresenter";
-
- public static final boolean DEBUG = false;
-
- /**
- * Runnable which is posted to schedule automatically entering fullscreen mode. Will not auto
- * enter fullscreen mode if the dialpad is visible (doing so would make it impossible to exit
- * the dialpad).
- */
- private Runnable mAutoFullscreenRunnable = new Runnable() {
- @Override
- public void run() {
- if (mAutoFullScreenPending && !InCallPresenter.getInstance().isDialpadVisible()
- && mIsVideoMode) {
-
- Log.v(this, "Automatically entering fullscreen mode.");
- InCallPresenter.getInstance().setFullScreen(true);
- mAutoFullScreenPending = false;
- } else {
- Log.v(this, "Skipping scheduled fullscreen mode.");
- }
- }
- };
-
- /**
- * Defines the state of the preview surface negotiation with the telephony layer.
- */
- private class PreviewSurfaceState {
- /**
- * The camera has not yet been set on the {@link VideoCall}; negotiation has not yet
- * started.
- */
- private static final int NONE = 0;
-
- /**
- * The camera has been set on the {@link VideoCall}, but camera capabilities have not yet
- * been received.
- */
- private static final int CAMERA_SET = 1;
-
- /**
- * The camera capabilties have been received from telephony, but the surface has not yet
- * been set on the {@link VideoCall}.
- */
- private static final int CAPABILITIES_RECEIVED = 2;
-
- /**
- * The surface has been set on the {@link VideoCall}.
- */
- private static final int SURFACE_SET = 3;
- }
-
- /**
- * The minimum width or height of the preview surface. Used when re-sizing the preview surface
- * to match the aspect ratio of the currently selected camera.
- */
- private float mMinimumVideoDimension;
-
- /**
- * The current context.
- */
- private Context mContext;
-
- /**
- * The call the video surfaces are currently related to
- */
- private Call mPrimaryCall;
-
- /**
- * The {@link VideoCall} used to inform the video telephony layer of changes to the video
- * surfaces.
- */
- private VideoCall mVideoCall;
-
- /**
- * Determines if the current UI state represents a video call.
- */
- private int mCurrentVideoState;
-
- /**
- * Call's current state
- */
- private int mCurrentCallState = Call.State.INVALID;
-
- /**
- * Determines the device orientation (portrait/lanscape).
- */
- private int mDeviceOrientation = InCallOrientationEventListener.SCREEN_ORIENTATION_0;
-
- /**
- * Tracks the state of the preview surface negotiation with the telephony layer.
- */
- private int mPreviewSurfaceState = PreviewSurfaceState.NONE;
-
- private static boolean mIsVideoMode = false;
-
- /**
- * Contact photo manager to retrieve cached contact photo information.
- */
- private ContactPhotoManager mContactPhotoManager = null;
-
- /**
- * The URI for the user's profile photo, or {@code null} if not specified.
- */
- private ContactInfoCache.ContactCacheEntry mProfileInfo = null;
-
- /**
- * UI thread handler used for delayed task execution.
- */
- private Handler mHandler;
-
- /**
- * Determines whether video calls should automatically enter full screen mode after
- * {@link #mAutoFullscreenTimeoutMillis} milliseconds.
- */
- private boolean mIsAutoFullscreenEnabled = false;
-
- /**
- * Determines the number of milliseconds after which a video call will automatically enter
- * fullscreen mode. Requires {@link #mIsAutoFullscreenEnabled} to be {@code true}.
- */
- private int mAutoFullscreenTimeoutMillis = 0;
-
- /**
- * Determines if the countdown is currently running to automatically enter full screen video
- * mode.
- */
- private boolean mAutoFullScreenPending = false;
-
- /**
- * Initializes the presenter.
- *
- * @param context The current context.
- */
- public void init(Context context) {
- mContext = context;
- mMinimumVideoDimension = mContext.getResources().getDimension(
- R.dimen.video_preview_small_dimension);
- mHandler = new Handler(Looper.getMainLooper());
- mIsAutoFullscreenEnabled = mContext.getResources()
- .getBoolean(R.bool.video_call_auto_fullscreen);
- mAutoFullscreenTimeoutMillis = mContext.getResources().getInteger(
- R.integer.video_call_auto_fullscreen_timeout);
- }
-
- /**
- * Called when the user interface is ready to be used.
- *
- * @param ui The Ui implementation that is now ready to be used.
- */
- @Override
- public void onUiReady(VideoCallUi ui) {
- super.onUiReady(ui);
- Log.d(this, "onUiReady:");
-
- // Do not register any listeners if video calling is not compatible to safeguard against
- // any accidental calls of video calling code.
- if (!CompatUtils.isVideoCompatible()) {
- return;
- }
-
- // Register for call state changes last
- InCallPresenter.getInstance().addListener(this);
- InCallPresenter.getInstance().addDetailsListener(this);
- InCallPresenter.getInstance().addIncomingCallListener(this);
- InCallPresenter.getInstance().addOrientationListener(this);
- // To get updates of video call details changes
- InCallPresenter.getInstance().addDetailsListener(this);
- InCallPresenter.getInstance().addInCallEventListener(this);
-
- // Register for surface and video events from {@link InCallVideoCallListener}s.
- InCallVideoCallCallbackNotifier.getInstance().addSurfaceChangeListener(this);
- InCallVideoCallCallbackNotifier.getInstance().addVideoEventListener(this);
- mCurrentVideoState = VideoProfile.STATE_AUDIO_ONLY;
- mCurrentCallState = Call.State.INVALID;
-
- final InCallPresenter.InCallState inCallState =
- InCallPresenter.getInstance().getInCallState();
- onStateChange(inCallState, inCallState, CallList.getInstance());
- }
-
- /**
- * Called when the user interface is no longer ready to be used.
- *
- * @param ui The Ui implementation that is no longer ready to be used.
- */
- @Override
- public void onUiUnready(VideoCallUi ui) {
- super.onUiUnready(ui);
- Log.d(this, "onUiUnready:");
-
- if (!CompatUtils.isVideoCompatible()) {
- return;
- }
-
- cancelAutoFullScreen();
-
- InCallPresenter.getInstance().removeListener(this);
- InCallPresenter.getInstance().removeDetailsListener(this);
- InCallPresenter.getInstance().removeIncomingCallListener(this);
- InCallPresenter.getInstance().removeOrientationListener(this);
- InCallPresenter.getInstance().removeInCallEventListener(this);
-
- InCallVideoCallCallbackNotifier.getInstance().removeSurfaceChangeListener(this);
- InCallVideoCallCallbackNotifier.getInstance().removeVideoEventListener(this);
- }
-
- /**
- * Handles the creation of a surface in the {@link VideoCallFragment}.
- *
- * @param surface The surface which was created.
- */
- public void onSurfaceCreated(int surface) {
- Log.d(this, "onSurfaceCreated surface=" + surface + " mVideoCall=" + mVideoCall);
- Log.d(this, "onSurfaceCreated PreviewSurfaceState=" + mPreviewSurfaceState);
- Log.d(this, "onSurfaceCreated presenter=" + this);
-
- final VideoCallUi ui = getUi();
- if (ui == null || mVideoCall == null) {
- Log.w(this, "onSurfaceCreated: Error bad state VideoCallUi=" + ui + " mVideoCall="
- + mVideoCall);
- return;
- }
-
- // If the preview surface has just been created and we have already received camera
- // capabilities, but not yet set the surface, we will set the surface now.
- if (surface == VideoCallFragment.SURFACE_PREVIEW ) {
- if (mPreviewSurfaceState == PreviewSurfaceState.CAPABILITIES_RECEIVED) {
- mPreviewSurfaceState = PreviewSurfaceState.SURFACE_SET;
- mVideoCall.setPreviewSurface(ui.getPreviewVideoSurface());
- } else if (mPreviewSurfaceState == PreviewSurfaceState.NONE && isCameraRequired()){
- enableCamera(mVideoCall, true);
- }
- } else if (surface == VideoCallFragment.SURFACE_DISPLAY) {
- mVideoCall.setDisplaySurface(ui.getDisplayVideoSurface());
- }
- }
-
- /**
- * Handles structural changes (format or size) to a surface.
- *
- * @param surface The surface which changed.
- * @param format The new PixelFormat of the surface.
- * @param width The new width of the surface.
- * @param height The new height of the surface.
- */
- public void onSurfaceChanged(int surface, int format, int width, int height) {
- //Do stuff
- }
-
- /**
- * Handles the destruction of a surface in the {@link VideoCallFragment}.
- * Note: The surface is being released, that is, it is no longer valid.
- *
- * @param surface The surface which was destroyed.
- */
- public void onSurfaceReleased(int surface) {
- Log.d(this, "onSurfaceReleased: mSurfaceId=" + surface);
- if ( mVideoCall == null) {
- Log.w(this, "onSurfaceReleased: VideoCall is null. mSurfaceId=" +
- surface);
- return;
- }
-
- if (surface == VideoCallFragment.SURFACE_DISPLAY) {
- mVideoCall.setDisplaySurface(null);
- } else if (surface == VideoCallFragment.SURFACE_PREVIEW) {
- mVideoCall.setPreviewSurface(null);
- enableCamera(mVideoCall, false);
- }
- }
-
- /**
- * Called by {@link VideoCallFragment} when the surface is detached from UI (TextureView).
- * Note: The surface will be cached by {@link VideoCallFragment}, so we don't immediately
- * null out incoming video surface.
- * @see VideoCallPresenter#onSurfaceReleased(int)
- *
- * @param surface The surface which was detached.
- */
- public void onSurfaceDestroyed(int surface) {
- Log.d(this, "onSurfaceDestroyed: mSurfaceId=" + surface);
- if (mVideoCall == null) {
- return;
- }
-
- final boolean isChangingConfigurations =
- InCallPresenter.getInstance().isChangingConfigurations();
- Log.d(this, "onSurfaceDestroyed: isChangingConfigurations=" + isChangingConfigurations);
-
- if (surface == VideoCallFragment.SURFACE_PREVIEW) {
- if (!isChangingConfigurations) {
- enableCamera(mVideoCall, false);
- } else {
- Log.w(this, "onSurfaceDestroyed: Activity is being destroyed due "
- + "to configuration changes. Not closing the camera.");
- }
- }
- }
-
- /**
- * Handles clicks on the video surfaces by toggling full screen state.
- * Informs the {@link InCallPresenter} of the change so that it can inform the
- * {@link CallCardPresenter} of the change.
- *
- * @param surfaceId The video surface receiving the click.
- */
- public void onSurfaceClick(int surfaceId) {
- boolean isFullscreen = InCallPresenter.getInstance().toggleFullscreenMode();
- Log.v(this, "toggleFullScreen = " + isFullscreen);
- }
-
- /**
- * Handles incoming calls.
- *
- * @param oldState The old in call state.
- * @param newState The new in call state.
- * @param call The call.
- */
- @Override
- public void onIncomingCall(InCallPresenter.InCallState oldState,
- InCallPresenter.InCallState newState, Call call) {
- // same logic should happen as with onStateChange()
- onStateChange(oldState, newState, CallList.getInstance());
- }
-
- /**
- * Handles state changes (including incoming calls)
- *
- * @param newState The in call state.
- * @param callList The call list.
- */
- @Override
- public void onStateChange(InCallPresenter.InCallState oldState,
- InCallPresenter.InCallState newState, CallList callList) {
- Log.d(this, "onStateChange oldState" + oldState + " newState=" + newState +
- " isVideoMode=" + isVideoMode());
-
- if (newState == InCallPresenter.InCallState.NO_CALLS) {
- if (isVideoMode()) {
- exitVideoMode();
- }
-
- cleanupSurfaces();
- }
-
- // Determine the primary active call).
- Call primary = null;
-
- // Determine the call which is the focus of the user's attention. In the case of an
- // incoming call waiting call, the primary call is still the active video call, however
- // the determination of whether we should be in fullscreen mode is based on the type of the
- // incoming call, not the active video call.
- Call currentCall = null;
-
- if (newState == InCallPresenter.InCallState.INCOMING) {
- // We don't want to replace active video call (primary call)
- // with a waiting call, since user may choose to ignore/decline the waiting call and
- // this should have no impact on current active video call, that is, we should not
- // change the camera or UI unless the waiting VT call becomes active.
- primary = callList.getActiveCall();
- currentCall = callList.getIncomingCall();
- if (!VideoUtils.isActiveVideoCall(primary)) {
- primary = callList.getIncomingCall();
- }
- } else if (newState == InCallPresenter.InCallState.OUTGOING) {
- currentCall = primary = callList.getOutgoingCall();
- } else if (newState == InCallPresenter.InCallState.PENDING_OUTGOING) {
- currentCall = primary = callList.getPendingOutgoingCall();
- } else if (newState == InCallPresenter.InCallState.INCALL) {
- currentCall = primary = callList.getActiveCall();
- }
-
- final boolean primaryChanged = !Objects.equals(mPrimaryCall, primary);
- Log.d(this, "onStateChange primaryChanged=" + primaryChanged);
- Log.d(this, "onStateChange primary= " + primary);
- Log.d(this, "onStateChange mPrimaryCall = " + mPrimaryCall);
- if (primaryChanged) {
- onPrimaryCallChanged(primary);
- } else if (mPrimaryCall != null) {
- updateVideoCall(primary);
- }
- updateCallCache(primary);
-
- // If the call context changed, potentially exit fullscreen or schedule auto enter of
- // fullscreen mode.
- // If the current call context is no longer a video call, exit fullscreen mode.
- maybeExitFullscreen(currentCall);
- // Schedule auto-enter of fullscreen mode if the current call context is a video call
- maybeAutoEnterFullscreen(currentCall);
- }
-
- /**
- * Handles a change to the fullscreen mode of the app.
- *
- * @param isFullscreenMode {@code true} if the app is now fullscreen, {@code false} otherwise.
- */
- @Override
- public void onFullscreenModeChanged(boolean isFullscreenMode) {
- cancelAutoFullScreen();
- }
-
- /**
- * Handles changes to the visibility of the secondary caller info bar.
- *
- * @param isVisible {@code true} if the secondary caller info is showing, {@code false}
- * otherwise.
- * @param height the height of the secondary caller info bar.
- */
- @Override
- public void onSecondaryCallerInfoVisibilityChanged(boolean isVisible, int height) {
- Log.d(this,
- "onSecondaryCallerInfoVisibilityChanged : isVisible = " + isVisible + " height = "
- + height);
- getUi().adjustPreviewLocation(isVisible /* shiftUp */, height);
- }
-
- private void checkForVideoStateChange(Call call) {
- final boolean isVideoCall = VideoUtils.isVideoCall(call);
- final boolean hasVideoStateChanged = mCurrentVideoState != call.getVideoState();
-
- Log.d(this, "checkForVideoStateChange: isVideoCall= " + isVideoCall
- + " hasVideoStateChanged=" + hasVideoStateChanged + " isVideoMode="
- + isVideoMode() + " previousVideoState: " +
- VideoProfile.videoStateToString(mCurrentVideoState) + " newVideoState: "
- + VideoProfile.videoStateToString(call.getVideoState()));
-
- if (!hasVideoStateChanged) {
- return;
- }
-
- updateCameraSelection(call);
-
- if (isVideoCall) {
- adjustVideoMode(call);
- } else if (isVideoMode()) {
- exitVideoMode();
- }
- }
-
- private void checkForCallStateChange(Call call) {
- final boolean isVideoCall = VideoUtils.isVideoCall(call);
- final boolean hasCallStateChanged = mCurrentCallState != call.getState();
-
- Log.d(this, "checkForCallStateChange: isVideoCall= " + isVideoCall
- + " hasCallStateChanged=" +
- hasCallStateChanged + " isVideoMode=" + isVideoMode());
-
- if (!hasCallStateChanged) {
- return;
- }
-
- if (isVideoCall) {
- final InCallCameraManager cameraManager = InCallPresenter.getInstance().
- getInCallCameraManager();
-
- String prevCameraId = cameraManager.getActiveCameraId();
- updateCameraSelection(call);
- String newCameraId = cameraManager.getActiveCameraId();
-
- if (!Objects.equals(prevCameraId, newCameraId) && VideoUtils.isActiveVideoCall(call)) {
- enableCamera(call.getVideoCall(), true);
- }
- }
-
- // Make sure we hide or show the video UI if needed.
- showVideoUi(call.getVideoState(), call.getState());
- }
-
- private void cleanupSurfaces() {
- final VideoCallUi ui = getUi();
- if (ui == null) {
- Log.w(this, "cleanupSurfaces");
- return;
- }
- ui.cleanupSurfaces();
- }
-
- private void onPrimaryCallChanged(Call newPrimaryCall) {
- final boolean isVideoCall = VideoUtils.isVideoCall(newPrimaryCall);
- final boolean isVideoMode = isVideoMode();
-
- Log.d(this, "onPrimaryCallChanged: isVideoCall=" + isVideoCall + " isVideoMode="
- + isVideoMode);
-
- if (!isVideoCall && isVideoMode) {
- // Terminate video mode if new primary call is not a video call
- // and we are currently in video mode.
- Log.d(this, "onPrimaryCallChanged: Exiting video mode...");
- exitVideoMode();
- } else if (isVideoCall) {
- Log.d(this, "onPrimaryCallChanged: Entering video mode...");
-
- updateCameraSelection(newPrimaryCall);
- adjustVideoMode(newPrimaryCall);
- }
- checkForOrientationAllowedChange(newPrimaryCall);
- }
-
- private boolean isVideoMode() {
- return mIsVideoMode;
- }
-
- private void updateCallCache(Call call) {
- if (call == null) {
- mCurrentVideoState = VideoProfile.STATE_AUDIO_ONLY;
- mCurrentCallState = Call.State.INVALID;
- mVideoCall = null;
- mPrimaryCall = null;
- } else {
- mCurrentVideoState = call.getVideoState();
- mVideoCall = call.getVideoCall();
- mCurrentCallState = call.getState();
- mPrimaryCall = call;
- }
- }
-
- /**
- * Handles changes to the details of the call. The {@link VideoCallPresenter} is interested in
- * changes to the video state.
- *
- * @param call The call for which the details changed.
- * @param details The new call details.
- */
- @Override
- public void onDetailsChanged(Call call, android.telecom.Call.Details details) {
- Log.d(this, " onDetailsChanged call=" + call + " details=" + details + " mPrimaryCall="
- + mPrimaryCall);
- if (call == null) {
- return;
- }
- // If the details change is not for the currently active call no update is required.
- if (!call.equals(mPrimaryCall)) {
- Log.d(this, " onDetailsChanged: Details not for current active call so returning. ");
- return;
- }
-
- updateVideoCall(call);
-
- updateCallCache(call);
- }
-
- private void updateVideoCall(Call call) {
- checkForVideoCallChange(call);
- checkForVideoStateChange(call);
- checkForCallStateChange(call);
- checkForOrientationAllowedChange(call);
- }
-
- private void checkForOrientationAllowedChange(Call call) {
- InCallPresenter.getInstance().setInCallAllowsOrientationChange(
- VideoUtils.isVideoCall(call));
- }
-
- /**
- * Checks for a change to the video call and changes it if required.
- */
- private void checkForVideoCallChange(Call call) {
- final VideoCall videoCall = call.getTelecomCall().getVideoCall();
- Log.d(this, "checkForVideoCallChange: videoCall=" + videoCall + " mVideoCall="
- + mVideoCall);
- if (!Objects.equals(videoCall, mVideoCall)) {
- changeVideoCall(call);
- }
- }
-
- /**
- * Handles a change to the video call. Sets the surfaces on the previous call to null and sets
- * the surfaces on the new video call accordingly.
- *
- * @param call The new video call.
- */
- private void changeVideoCall(Call call) {
- final VideoCall videoCall = call.getTelecomCall().getVideoCall();
- Log.d(this, "changeVideoCall to videoCall=" + videoCall + " mVideoCall=" + mVideoCall);
- // Null out the surfaces on the previous video call.
- if (mVideoCall != null) {
- // Log.d(this, "Null out the surfaces on the previous video call.");
- // mVideoCall.setDisplaySurface(null);
- // mVideoCall.setPreviewSurface(null);
- }
-
- final boolean hasChanged = mVideoCall == null && videoCall != null;
-
- mVideoCall = videoCall;
- if (mVideoCall == null || call == null) {
- Log.d(this, "Video call or primary call is null. Return");
- return;
- }
-
- if (VideoUtils.isVideoCall(call) && hasChanged) {
- adjustVideoMode(call);
- }
- }
-
- private static boolean isCameraRequired(int videoState) {
- return VideoProfile.isBidirectional(videoState)
- || VideoProfile.isTransmissionEnabled(videoState);
- }
-
- private boolean isCameraRequired() {
- return mPrimaryCall != null && isCameraRequired(mPrimaryCall.getVideoState());
- }
-
- /**
- * Adjusts the current video mode by setting up the preview and display surfaces as necessary.
- * Expected to be called whenever the video state associated with a call changes (e.g. a user
- * turns their camera on or off) to ensure the correct surfaces are shown/hidden.
- * TODO(vt): Need to adjust size and orientation of preview surface here.
- */
- private void adjustVideoMode(Call call) {
- VideoCall videoCall = call.getVideoCall();
- int newVideoState = call.getVideoState();
-
- Log.d(this, "adjustVideoMode videoCall= " + videoCall + " videoState: " + newVideoState);
- VideoCallUi ui = getUi();
- if (ui == null) {
- Log.e(this, "Error VideoCallUi is null so returning");
- return;
- }
-
- showVideoUi(newVideoState, call.getState());
-
- // Communicate the current camera to telephony and make a request for the camera
- // capabilities.
- if (videoCall != null) {
- if (ui.isDisplayVideoSurfaceCreated()) {
- Log.d(this, "Calling setDisplaySurface with " + ui.getDisplayVideoSurface());
- videoCall.setDisplaySurface(ui.getDisplayVideoSurface());
- }
-
- videoCall.setDeviceOrientation(mDeviceOrientation);
- enableCamera(videoCall, isCameraRequired(newVideoState));
- }
- int previousVideoState = mCurrentVideoState;
- mCurrentVideoState = newVideoState;
- mIsVideoMode = true;
-
- // adjustVideoMode may be called if we are already in a 1-way video state. In this case
- // we do not want to trigger auto-fullscreen mode.
- if (!VideoUtils.isVideoCall(previousVideoState) && VideoUtils.isVideoCall(newVideoState)) {
- maybeAutoEnterFullscreen(call);
- }
- }
-
- private void enableCamera(VideoCall videoCall, boolean isCameraRequired) {
- Log.d(this, "enableCamera: VideoCall=" + videoCall + " enabling=" + isCameraRequired);
- if (videoCall == null) {
- Log.w(this, "enableCamera: VideoCall is null.");
- return;
- }
-
- if (isCameraRequired) {
- InCallCameraManager cameraManager = InCallPresenter.getInstance().
- getInCallCameraManager();
- videoCall.setCamera(cameraManager.getActiveCameraId());
- mPreviewSurfaceState = PreviewSurfaceState.CAMERA_SET;
-
- videoCall.requestCameraCapabilities();
- } else {
- mPreviewSurfaceState = PreviewSurfaceState.NONE;
- videoCall.setCamera(null);
- }
- }
-
- /**
- * Exits video mode by hiding the video surfaces and making other adjustments (eg. audio).
- */
- private void exitVideoMode() {
- Log.d(this, "exitVideoMode");
-
- showVideoUi(VideoProfile.STATE_AUDIO_ONLY, Call.State.ACTIVE);
- enableCamera(mVideoCall, false);
- InCallPresenter.getInstance().setFullScreen(false);
-
- mIsVideoMode = false;
- }
-
- /**
- * Based on the current video state and call state, show or hide the incoming and
- * outgoing video surfaces. The outgoing video surface is shown any time video is transmitting.
- * The incoming video surface is shown whenever the video is un-paused and active.
- *
- * @param videoState The video state.
- * @param callState The call state.
- */
- private void showVideoUi(int videoState, int callState) {
- VideoCallUi ui = getUi();
- if (ui == null) {
- Log.e(this, "showVideoUi, VideoCallUi is null returning");
- return;
- }
- boolean showIncomingVideo = showIncomingVideo(videoState, callState);
- boolean showOutgoingVideo = showOutgoingVideo(videoState);
- Log.v(this, "showVideoUi : showIncoming = " + showIncomingVideo + " showOutgoing = "
- + showOutgoingVideo);
- if (showIncomingVideo || showOutgoingVideo) {
- ui.showVideoViews(showOutgoingVideo, showIncomingVideo);
-
- if (VideoProfile.isReceptionEnabled(videoState)) {
- loadProfilePhotoAsync();
- }
- } else {
- ui.hideVideoUi();
- }
-
- InCallPresenter.getInstance().enableScreenTimeout(
- VideoProfile.isAudioOnly(videoState));
- }
-
- /**
- * Determines if the incoming video surface should be shown based on the current videoState and
- * callState. The video surface is shown when incoming video is not paused, the call is active,
- * and video reception is enabled.
- *
- * @param videoState The current video state.
- * @param callState The current call state.
- * @return {@code true} if the incoming video surface should be shown, {@code false} otherwise.
- */
- public static boolean showIncomingVideo(int videoState, int callState) {
- if (!CompatUtils.isVideoCompatible()) {
- return false;
- }
-
- boolean isPaused = VideoProfile.isPaused(videoState);
- boolean isCallActive = callState == Call.State.ACTIVE;
-
- return !isPaused && isCallActive && VideoProfile.isReceptionEnabled(videoState);
- }
-
- /**
- * Determines if the outgoing video surface should be shown based on the current videoState.
- * The video surface is shown if video transmission is enabled.
- *
- * @param videoState The current video state.
- * @return {@code true} if the the outgoing video surface should be shown, {@code false}
- * otherwise.
- */
- public static boolean showOutgoingVideo(int videoState) {
- if (!CompatUtils.isVideoCompatible()) {
- return false;
- }
-
- return VideoProfile.isTransmissionEnabled(videoState);
- }
-
- /**
- * Handles peer video pause state changes.
- *
- * @param call The call which paused or un-pausedvideo transmission.
- * @param paused {@code True} when the video transmission is paused, {@code false} when video
- * transmission resumes.
- */
- @Override
- public void onPeerPauseStateChanged(Call call, boolean paused) {
- if (!call.equals(mPrimaryCall)) {
- return;
- }
-
- // TODO(vt): Show/hide the peer contact photo.
- }
-
- /**
- * Handles peer video dimension changes.
- *
- * @param call The call which experienced a peer video dimension change.
- * @param width The new peer video width .
- * @param height The new peer video height.
- */
- @Override
- public void onUpdatePeerDimensions(Call call, int width, int height) {
- Log.d(this, "onUpdatePeerDimensions: width= " + width + " height= " + height);
- VideoCallUi ui = getUi();
- if (ui == null) {
- Log.e(this, "VideoCallUi is null. Bail out");
- return;
- }
- if (!call.equals(mPrimaryCall)) {
- Log.e(this, "Current call is not equal to primary call. Bail out");
- return;
- }
-
- // Change size of display surface to match the peer aspect ratio
- if (width > 0 && height > 0) {
- setDisplayVideoSize(width, height);
- }
- }
-
- /**
- * Handles any video quality changes in the call.
- *
- * @param call The call which experienced a video quality change.
- * @param videoQuality The new video call quality.
- */
- @Override
- public void onVideoQualityChanged(Call call, int videoQuality) {
- // No-op
- }
-
- /**
- * Handles a change to the dimensions of the local camera. Receiving the camera capabilities
- * triggers the creation of the video
- *
- * @param call The call which experienced the camera dimension change.
- * @param width The new camera video width.
- * @param height The new camera video height.
- */
- @Override
- public void onCameraDimensionsChange(Call call, int width, int height) {
- Log.d(this, "onCameraDimensionsChange call=" + call + " width=" + width + " height="
- + height);
- VideoCallUi ui = getUi();
- if (ui == null) {
- Log.e(this, "onCameraDimensionsChange ui is null");
- return;
- }
-
- if (!call.equals(mPrimaryCall)) {
- Log.e(this, "Call is not primary call");
- return;
- }
-
- mPreviewSurfaceState = PreviewSurfaceState.CAPABILITIES_RECEIVED;
- changePreviewDimensions(width, height);
-
- // Check if the preview surface is ready yet; if it is, set it on the {@code VideoCall}.
- // If it not yet ready, it will be set when when creation completes.
- if (ui.isPreviewVideoSurfaceCreated()) {
- mPreviewSurfaceState = PreviewSurfaceState.SURFACE_SET;
- mVideoCall.setPreviewSurface(ui.getPreviewVideoSurface());
- }
- }
-
- /**
- * Changes the dimensions of the preview surface.
- *
- * @param width The new width.
- * @param height The new height.
- */
- private void changePreviewDimensions(int width, int height) {
- VideoCallUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- // Resize the surface used to display the preview video
- ui.setPreviewSurfaceSize(width, height);
-
- // Configure the preview surface to the correct aspect ratio.
- float aspectRatio = 1.0f;
- if (width > 0 && height > 0) {
- aspectRatio = (float) width / (float) height;
- }
-
- // Resize the textureview housing the preview video and rotate it appropriately based on
- // the device orientation
- setPreviewSize(mDeviceOrientation, aspectRatio);
- }
-
- /**
- * Called when call session event is raised.
- *
- * @param event The call session event.
- */
- @Override
- public void onCallSessionEvent(int event) {
- StringBuilder sb = new StringBuilder();
- sb.append("onCallSessionEvent = ");
-
- switch (event) {
- case Connection.VideoProvider.SESSION_EVENT_RX_PAUSE:
- sb.append("rx_pause");
- break;
- case Connection.VideoProvider.SESSION_EVENT_RX_RESUME:
- sb.append("rx_resume");
- break;
- case Connection.VideoProvider.SESSION_EVENT_CAMERA_FAILURE:
- sb.append("camera_failure");
- break;
- case Connection.VideoProvider.SESSION_EVENT_CAMERA_READY:
- sb.append("camera_ready");
- break;
- default:
- sb.append("unknown event = ");
- sb.append(event);
- break;
- }
- Log.d(this, sb.toString());
- }
-
- /**
- * Handles a change to the call data usage
- *
- * @param dataUsage call data usage value
- */
- @Override
- public void onCallDataUsageChange(long dataUsage) {
- Log.d(this, "onCallDataUsageChange dataUsage=" + dataUsage);
- }
-
- /**
- * Handles changes to the device orientation.
- * @param orientation The screen orientation of the device (one of:
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_0},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_90},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_180},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_270}).
- */
- @Override
- public void onDeviceOrientationChanged(int orientation) {
- mDeviceOrientation = orientation;
-
- VideoCallUi ui = getUi();
- if (ui == null) {
- Log.e(this, "onDeviceOrientationChanged: VideoCallUi is null");
- return;
- }
-
- Point previewDimensions = ui.getPreviewSize();
- if (previewDimensions == null) {
- return;
- }
- Log.d(this, "onDeviceOrientationChanged: orientation=" + orientation + " size: "
- + previewDimensions);
- changePreviewDimensions(previewDimensions.x, previewDimensions.y);
-
- ui.setPreviewRotation(mDeviceOrientation);
- }
-
- /**
- * Sets the preview surface size based on the current device orientation.
- * See: {@link InCallOrientationEventListener#SCREEN_ORIENTATION_0},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_90},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_180},
- * {@link InCallOrientationEventListener#SCREEN_ORIENTATION_270}).
- *
- * @param orientation The device orientation
- * @param aspectRatio The aspect ratio of the camera (width / height).
- */
- private void setPreviewSize(int orientation, float aspectRatio) {
- VideoCallUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- int height;
- int width;
-
- if (orientation == InCallOrientationEventListener.SCREEN_ORIENTATION_90 ||
- orientation == InCallOrientationEventListener.SCREEN_ORIENTATION_270) {
- width = (int) (mMinimumVideoDimension * aspectRatio);
- height = (int) mMinimumVideoDimension;
- } else {
- // Portrait or reverse portrait orientation.
- width = (int) mMinimumVideoDimension;
- height = (int) (mMinimumVideoDimension * aspectRatio);
- }
- ui.setPreviewSize(width, height);
- }
-
- /**
- * Sets the display video surface size based on peer width and height
- *
- * @param width peer width
- * @param height peer height
- */
- private void setDisplayVideoSize(int width, int height) {
- Log.v(this, "setDisplayVideoSize: Received peer width=" + width + " height=" + height);
- VideoCallUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- // Get current display size
- Point size = ui.getScreenSize();
- Log.v(this, "setDisplayVideoSize: windowmgr width=" + size.x
- + " windowmgr height=" + size.y);
- if (size.y * width > size.x * height) {
- // current display height is too much. Correct it
- size.y = (int) (size.x * height / width);
- } else if (size.y * width < size.x * height) {
- // current display width is too much. Correct it
- size.x = (int) (size.y * width / height);
- }
- ui.setDisplayVideoSize(size.x, size.y);
- }
-
- /**
- * Exits fullscreen mode if the current call context has changed to a non-video call.
- *
- * @param call The call.
- */
- protected void maybeExitFullscreen(Call call) {
- if (call == null) {
- return;
- }
-
- if (!VideoUtils.isVideoCall(call) || call.getState() == Call.State.INCOMING) {
- InCallPresenter.getInstance().setFullScreen(false);
- }
- }
-
- /**
- * Schedules auto-entering of fullscreen mode.
- * Will not enter full screen mode if any of the following conditions are met:
- * 1. No call
- * 2. Call is not active
- * 3. Call is not video call
- * 4. Already in fullscreen mode
- * 5. The current video state is not bi-directional (if the remote party stops transmitting,
- * the user's contact photo would dominate in fullscreen mode).
- *
- * @param call The current call.
- */
- protected void maybeAutoEnterFullscreen(Call call) {
- if (!mIsAutoFullscreenEnabled) {
- return;
- }
-
- if (call == null || (
- call != null && (call.getState() != Call.State.ACTIVE ||
- !VideoUtils.isVideoCall(call)) ||
- InCallPresenter.getInstance().isFullscreen()) ||
- !VideoUtils.isBidirectionalVideoCall(call)) {
- // Ensure any previously scheduled attempt to enter fullscreen is cancelled.
- cancelAutoFullScreen();
- return;
- }
-
- if (mAutoFullScreenPending) {
- Log.v(this, "maybeAutoEnterFullscreen : already pending.");
- return;
- }
- Log.v(this, "maybeAutoEnterFullscreen : scheduled");
- mAutoFullScreenPending = true;
- mHandler.postDelayed(mAutoFullscreenRunnable, mAutoFullscreenTimeoutMillis);
- }
-
- /**
- * Cancels pending auto fullscreen mode.
- */
- public void cancelAutoFullScreen() {
- if (!mAutoFullScreenPending) {
- Log.v(this, "cancelAutoFullScreen : none pending.");
- return;
- }
- Log.v(this, "cancelAutoFullScreen : cancelling pending");
- mAutoFullScreenPending = false;
- }
-
- private static void updateCameraSelection(Call call) {
- Log.d(TAG, "updateCameraSelection: call=" + call);
- Log.d(TAG, "updateCameraSelection: call=" + toSimpleString(call));
-
- final Call activeCall = CallList.getInstance().getActiveCall();
- int cameraDir = Call.VideoSettings.CAMERA_DIRECTION_UNKNOWN;
-
- // this function should never be called with null call object, however if it happens we
- // should handle it gracefully.
- if (call == null) {
- cameraDir = Call.VideoSettings.CAMERA_DIRECTION_UNKNOWN;
- com.android.incallui.Log.e(TAG, "updateCameraSelection: Call object is null."
- + " Setting camera direction to default value (CAMERA_DIRECTION_UNKNOWN)");
- }
-
- // Clear camera direction if this is not a video call.
- else if (VideoUtils.isAudioCall(call)) {
- cameraDir = Call.VideoSettings.CAMERA_DIRECTION_UNKNOWN;
- call.getVideoSettings().setCameraDir(cameraDir);
- }
-
- // If this is a waiting video call, default to active call's camera,
- // since we don't want to change the current camera for waiting call
- // without user's permission.
- else if (VideoUtils.isVideoCall(activeCall) && VideoUtils.isIncomingVideoCall(call)) {
- cameraDir = activeCall.getVideoSettings().getCameraDir();
- }
-
- // Infer the camera direction from the video state and store it,
- // if this is an outgoing video call.
- else if (VideoUtils.isOutgoingVideoCall(call) && !isCameraDirectionSet(call) ) {
- cameraDir = toCameraDirection(call.getVideoState());
- call.getVideoSettings().setCameraDir(cameraDir);
- }
-
- // Use the stored camera dir if this is an outgoing video call for which camera direction
- // is set.
- else if (VideoUtils.isOutgoingVideoCall(call)) {
- cameraDir = call.getVideoSettings().getCameraDir();
- }
-
- // Infer the camera direction from the video state and store it,
- // if this is an active video call and camera direction is not set.
- else if (VideoUtils.isActiveVideoCall(call) && !isCameraDirectionSet(call)) {
- cameraDir = toCameraDirection(call.getVideoState());
- call.getVideoSettings().setCameraDir(cameraDir);
- }
-
- // Use the stored camera dir if this is an active video call for which camera direction
- // is set.
- else if (VideoUtils.isActiveVideoCall(call)) {
- cameraDir = call.getVideoSettings().getCameraDir();
- }
-
- // For all other cases infer the camera direction but don't store it in the call object.
- else {
- cameraDir = toCameraDirection(call.getVideoState());
- }
-
- com.android.incallui.Log.d(TAG, "updateCameraSelection: Setting camera direction to " +
- cameraDir + " Call=" + call);
- final InCallCameraManager cameraManager = InCallPresenter.getInstance().
- getInCallCameraManager();
- cameraManager.setUseFrontFacingCamera(cameraDir ==
- Call.VideoSettings.CAMERA_DIRECTION_FRONT_FACING);
- }
-
- private static int toCameraDirection(int videoState) {
- return VideoProfile.isTransmissionEnabled(videoState) &&
- !VideoProfile.isBidirectional(videoState)
- ? Call.VideoSettings.CAMERA_DIRECTION_BACK_FACING
- : Call.VideoSettings.CAMERA_DIRECTION_FRONT_FACING;
- }
-
- private static boolean isCameraDirectionSet(Call call) {
- return VideoUtils.isVideoCall(call) && call.getVideoSettings().getCameraDir()
- != Call.VideoSettings.CAMERA_DIRECTION_UNKNOWN;
- }
-
- private static String toSimpleString(Call call) {
- return call == null ? null : call.toSimpleString();
- }
-
- /**
- * Starts an asynchronous load of the user's profile photo.
- */
- public void loadProfilePhotoAsync() {
- final VideoCallUi ui = getUi();
- if (ui == null) {
- return;
- }
-
- final AsyncTask task = new AsyncTask() {
- /**
- * Performs asynchronous load of the user profile information.
- *
- * @param params The parameters of the task.
- *
- * @return {@code null}.
- */
- @Override
- protected Void doInBackground(Void... params) {
- if (mProfileInfo == null) {
- // Try and read the photo URI from the local profile.
- mProfileInfo = new ContactInfoCache.ContactCacheEntry();
- final Cursor cursor = mContext.getContentResolver().query(
- ContactsContract.Profile.CONTENT_URI, new String[]{
- ContactsContract.CommonDataKinds.Phone._ID,
- ContactsContract.CommonDataKinds.Phone.PHOTO_URI,
- ContactsContract.CommonDataKinds.Phone.LOOKUP_KEY,
- ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME,
- ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME_ALTERNATIVE
- }, null, null, null);
- if (cursor != null) {
- try {
- if (cursor.moveToFirst()) {
- mProfileInfo.lookupKey = cursor.getString(cursor.getColumnIndex(
- ContactsContract.CommonDataKinds.Phone.LOOKUP_KEY));
- String photoUri = cursor.getString(cursor.getColumnIndex(
- ContactsContract.CommonDataKinds.Phone.PHOTO_URI));
- mProfileInfo.displayPhotoUri = photoUri == null ? null
- : Uri.parse(photoUri);
- mProfileInfo.namePrimary = cursor.getString(cursor.getColumnIndex(
- ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
- mProfileInfo.nameAlternative = cursor.getString(
- cursor.getColumnIndex(ContactsContract.CommonDataKinds
- .Phone.DISPLAY_NAME_ALTERNATIVE));
- }
- } finally {
- cursor.close();
- }
- }
- }
- return null;
- }
-
- @Override
- protected void onPostExecute(Void result) {
- // If user profile information was found, issue an async request to load the user's
- // profile photo.
- if (mProfileInfo != null) {
- if (mContactPhotoManager == null) {
- mContactPhotoManager = ContactPhotoManager.getInstance(mContext);
- }
- ContactPhotoManager.DefaultImageRequest imageRequest = (mProfileInfo != null)
- ? null :
- new ContactPhotoManager.DefaultImageRequest(mProfileInfo.namePrimary,
- mProfileInfo.lookupKey, false /* isCircularPhoto */);
-
- ImageView photoView = ui.getPreviewPhotoView();
- if (photoView == null) {
- return;
- }
- mContactPhotoManager.loadDirectoryPhoto(photoView,
- mProfileInfo.displayPhotoUri,
- false /* darkTheme */, false /* isCircular */, imageRequest);
- }
- }
- };
-
- task.execute();
- }
-
- /**
- * Defines the VideoCallUI interactions.
- */
- public interface VideoCallUi extends Ui {
- void showVideoViews(boolean showPreview, boolean showIncoming);
- void hideVideoUi();
- boolean isDisplayVideoSurfaceCreated();
- boolean isPreviewVideoSurfaceCreated();
- Surface getDisplayVideoSurface();
- Surface getPreviewVideoSurface();
- int getCurrentRotation();
- void setPreviewSize(int width, int height);
- void setPreviewSurfaceSize(int width, int height);
- void setDisplayVideoSize(int width, int height);
- Point getScreenSize();
- Point getPreviewSize();
- void cleanupSurfaces();
- ImageView getPreviewPhotoView();
- void adjustPreviewLocation(boolean shiftUp, int offset);
- void setPreviewRotation(int orientation);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/VideoPauseController.java b/InCallUI/src/com/android/incallui/VideoPauseController.java
deleted file mode 100644
index fb873500ef0d81823082bdcd89075b19b34a147e..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/VideoPauseController.java
+++ /dev/null
@@ -1,420 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import com.android.incallui.Call.State;
-import com.android.incallui.InCallPresenter.InCallState;
-import com.android.incallui.InCallPresenter.InCallStateListener;
-import com.android.incallui.InCallPresenter.IncomingCallListener;
-import com.android.incallui.InCallVideoCallCallbackNotifier.SessionModificationListener;
-import com.google.common.base.Preconditions;
-
-import android.telecom.VideoProfile;
-
-/**
- * This class is responsible for generating video pause/resume requests when the InCall UI is sent
- * to the background and subsequently brought back to the foreground.
- */
-class VideoPauseController implements InCallStateListener, IncomingCallListener {
- private static final String TAG = "VideoPauseController";
-
- /**
- * Keeps track of the current active/foreground call.
- */
- private class CallContext {
- public CallContext(Call call) {
- Preconditions.checkNotNull(call);
- update(call);
- }
-
- public void update(Call call) {
- mCall = Preconditions.checkNotNull(call);
- mState = call.getState();
- mVideoState = call.getVideoState();
- }
-
- public int getState() {
- return mState;
- }
-
- public int getVideoState() {
- return mVideoState;
- }
-
- public String toString() {
- return String.format("CallContext {CallId=%s, State=%s, VideoState=%d}",
- mCall.getId(), mState, mVideoState);
- }
-
- public Call getCall() {
- return mCall;
- }
-
- private int mState = State.INVALID;
- private int mVideoState;
- private Call mCall;
- }
-
- private InCallPresenter mInCallPresenter;
- private static VideoPauseController sVideoPauseController;
-
- /**
- * The current call context, if applicable.
- */
- private CallContext mPrimaryCallContext = null;
-
- /**
- * Tracks whether the application is in the background. {@code True} if the application is in
- * the background, {@code false} otherwise.
- */
- private boolean mIsInBackground = false;
-
- /**
- * Singleton accessor for the {@link VideoPauseController}.
- * @return Singleton instance of the {@link VideoPauseController}.
- */
- /*package*/
- static synchronized VideoPauseController getInstance() {
- if (sVideoPauseController == null) {
- sVideoPauseController = new VideoPauseController();
- }
- return sVideoPauseController;
- }
-
- /**
- * Configures the {@link VideoPauseController} to listen to call events. Configured via the
- * {@link com.android.incallui.InCallPresenter}.
- *
- * @param inCallPresenter The {@link com.android.incallui.InCallPresenter}.
- */
- public void setUp(InCallPresenter inCallPresenter) {
- log("setUp");
- mInCallPresenter = Preconditions.checkNotNull(inCallPresenter);
- mInCallPresenter.addListener(this);
- mInCallPresenter.addIncomingCallListener(this);
- }
-
- /**
- * Cleans up the {@link VideoPauseController} by removing all listeners and clearing its
- * internal state. Called from {@link com.android.incallui.InCallPresenter}.
- */
- public void tearDown() {
- log("tearDown...");
- mInCallPresenter.removeListener(this);
- mInCallPresenter.removeIncomingCallListener(this);
- clear();
- }
-
- /**
- * Clears the internal state for the {@link VideoPauseController}.
- */
- private void clear() {
- mInCallPresenter = null;
- mPrimaryCallContext = null;
- mIsInBackground = false;
- }
-
- /**
- * Handles changes in the {@link InCallState}. Triggers pause and resumption of video for the
- * current foreground call.
- *
- * @param oldState The previous {@link InCallState}.
- * @param newState The current {@link InCallState}.
- * @param callList List of current call.
- */
- @Override
- public void onStateChange(InCallState oldState, InCallState newState, CallList callList) {
- log("onStateChange, OldState=" + oldState + " NewState=" + newState);
-
- Call call = null;
- if (newState == InCallState.INCOMING) {
- call = callList.getIncomingCall();
- } else if (newState == InCallState.WAITING_FOR_ACCOUNT) {
- call = callList.getWaitingForAccountCall();
- } else if (newState == InCallState.PENDING_OUTGOING) {
- call = callList.getPendingOutgoingCall();
- } else if (newState == InCallState.OUTGOING) {
- call = callList.getOutgoingCall();
- } else {
- call = callList.getActiveCall();
- }
-
- boolean hasPrimaryCallChanged = !areSame(call, mPrimaryCallContext);
- boolean canVideoPause = VideoUtils.canVideoPause(call);
- log("onStateChange, hasPrimaryCallChanged=" + hasPrimaryCallChanged);
- log("onStateChange, canVideoPause=" + canVideoPause);
- log("onStateChange, IsInBackground=" + mIsInBackground);
-
- if (hasPrimaryCallChanged) {
- onPrimaryCallChanged(call);
- return;
- }
-
- if (isDialing(mPrimaryCallContext) && canVideoPause && mIsInBackground) {
- // Bring UI to foreground if outgoing request becomes active while UI is in
- // background.
- bringToForeground();
- } else if (!isVideoCall(mPrimaryCallContext) && canVideoPause && mIsInBackground) {
- // Bring UI to foreground if VoLTE call becomes active while UI is in
- // background.
- bringToForeground();
- }
-
- updatePrimaryCallContext(call);
- }
-
- /**
- * Handles a change to the primary call.
- *
- * Reject incoming or hangup dialing call: Where the previous call was an incoming call or a
- * call in dialing state, resume the new primary call.
- * Call swap: Where the new primary call is incoming, pause video on the previous primary call.
- *
- * @param call The new primary call.
- */
- private void onPrimaryCallChanged(Call call) {
- log("onPrimaryCallChanged: New call = " + call);
- log("onPrimaryCallChanged: Old call = " + mPrimaryCallContext);
- log("onPrimaryCallChanged, IsInBackground=" + mIsInBackground);
-
- Preconditions.checkState(!areSame(call, mPrimaryCallContext));
- final boolean canVideoPause = VideoUtils.canVideoPause(call);
-
- if ((isIncomingCall(mPrimaryCallContext) || isDialing(mPrimaryCallContext) ||
- (call != null && VideoProfile.isPaused(call.getVideoState())))
- && canVideoPause && !mIsInBackground) {
- // Send resume request for the active call, if user rejects incoming call, ends dialing
- // call, or the call was previously in a paused state and UI is in the foreground.
- sendRequest(call, true);
- } else if (isIncomingCall(call) && canVideoPause(mPrimaryCallContext)) {
- // Send pause request if there is an active video call, and we just received a new
- // incoming call.
- sendRequest(mPrimaryCallContext.getCall(), false);
- }
-
- updatePrimaryCallContext(call);
- }
-
- /**
- * Handles new incoming calls by triggering a change in the primary call.
- *
- * @param oldState the old {@link InCallState}.
- * @param newState the new {@link InCallState}.
- * @param call the incoming call.
- */
- @Override
- public void onIncomingCall(InCallState oldState, InCallState newState, Call call) {
- log("onIncomingCall, OldState=" + oldState + " NewState=" + newState + " Call=" + call);
-
- if (areSame(call, mPrimaryCallContext)) {
- return;
- }
-
- onPrimaryCallChanged(call);
- }
-
- /**
- * Caches a reference to the primary call and stores its previous state.
- *
- * @param call The new primary call.
- */
- private void updatePrimaryCallContext(Call call) {
- if (call == null) {
- mPrimaryCallContext = null;
- } else if (mPrimaryCallContext != null) {
- mPrimaryCallContext.update(call);
- } else {
- mPrimaryCallContext = new CallContext(call);
- }
- }
-
- /**
- * Called when UI goes in/out of the foreground.
- * @param showing true if UI is in the foreground, false otherwise.
- */
- public void onUiShowing(boolean showing) {
- // Only send pause/unpause requests if we are in the INCALL state.
- if (mInCallPresenter == null) {
- return;
- }
- final boolean isInCall = mInCallPresenter.getInCallState() == InCallState.INCALL;
- if (showing) {
- onResume(isInCall);
- } else {
- onPause(isInCall);
- }
- }
-
- /**
- * Called when UI is brought to the foreground. Sends a session modification request to resume
- * the outgoing video.
- * @param isInCall true if phone state is INCALL, false otherwise
- */
- private void onResume(boolean isInCall) {
- log("onResume");
-
- mIsInBackground = false;
- if (canVideoPause(mPrimaryCallContext) && isInCall) {
- sendRequest(mPrimaryCallContext.getCall(), true);
- } else {
- log("onResume. Ignoring...");
- }
- }
-
- /**
- * Called when UI is sent to the background. Sends a session modification request to pause the
- * outgoing video.
- * @param isInCall true if phone state is INCALL, false otherwise
- */
- private void onPause(boolean isInCall) {
- log("onPause");
-
- mIsInBackground = true;
- if (canVideoPause(mPrimaryCallContext) && isInCall) {
- sendRequest(mPrimaryCallContext.getCall(), false);
- } else {
- log("onPause, Ignoring...");
- }
- }
-
- private void bringToForeground() {
- if (mInCallPresenter != null) {
- log("Bringing UI to foreground");
- mInCallPresenter.bringToForeground(false);
- } else {
- loge("InCallPresenter is null. Cannot bring UI to foreground");
- }
- }
-
- /**
- * Sends Pause/Resume request.
- *
- * @param call Call to be paused/resumed.
- * @param resume If true resume request will be sent, otherwise pause request.
- */
- private void sendRequest(Call call, boolean resume) {
- // Check if this call supports pause/un-pause.
- if (!call.can(android.telecom.Call.Details.CAPABILITY_CAN_PAUSE_VIDEO)) {
- return;
- }
-
- if (resume) {
- log("sending resume request, call=" + call);
- call.getVideoCall()
- .sendSessionModifyRequest(VideoUtils.makeVideoUnPauseProfile(call));
- } else {
- log("sending pause request, call=" + call);
- call.getVideoCall().sendSessionModifyRequest(VideoUtils.makeVideoPauseProfile(call));
- }
- }
-
- /**
- * Determines if a given call is the same one stored in a {@link CallContext}.
- *
- * @param call The call.
- * @param callContext The call context.
- * @return {@code true} if the {@link Call} is the same as the one referenced in the
- * {@link CallContext}.
- */
- private static boolean areSame(Call call, CallContext callContext) {
- if (call == null && callContext == null) {
- return true;
- } else if (call == null || callContext == null) {
- return false;
- }
- return call.equals(callContext.getCall());
- }
-
- /**
- * Determines if a video call can be paused. Only a video call which is active can be paused.
- *
- * @param callContext The call context to check.
- * @return {@code true} if the call is an active video call.
- */
- private static boolean canVideoPause(CallContext callContext) {
- return isVideoCall(callContext) && callContext.getState() == Call.State.ACTIVE;
- }
-
- /**
- * Determines if a call referenced by a {@link CallContext} is a video call.
- *
- * @param callContext The call context.
- * @return {@code true} if the call is a video call, {@code false} otherwise.
- */
- private static boolean isVideoCall(CallContext callContext) {
- return callContext != null && VideoUtils.isVideoCall(callContext.getVideoState());
- }
-
- /**
- * Determines if call is in incoming/waiting state.
- *
- * @param call The call context.
- * @return {@code true} if the call is in incoming or waiting state, {@code false} otherwise.
- */
- private static boolean isIncomingCall(CallContext call) {
- return call != null && isIncomingCall(call.getCall());
- }
-
- /**
- * Determines if a call is in incoming/waiting state.
- *
- * @param call The call.
- * @return {@code true} if the call is in incoming or waiting state, {@code false} otherwise.
- */
- private static boolean isIncomingCall(Call call) {
- return call != null && (call.getState() == Call.State.CALL_WAITING
- || call.getState() == Call.State.INCOMING);
- }
-
- /**
- * Determines if a call is dialing.
- *
- * @param call The call context.
- * @return {@code true} if the call is dialing, {@code false} otherwise.
- */
- private static boolean isDialing(CallContext call) {
- return call != null && Call.State.isDialing(call.getState());
- }
-
- /**
- * Determines if a call is holding.
- *
- * @param call The call context.
- * @return {@code true} if the call is holding, {@code false} otherwise.
- */
- private static boolean isHolding(CallContext call) {
- return call != null && call.getState() == Call.State.ONHOLD;
- }
-
- /**
- * Logs a debug message.
- *
- * @param msg The message.
- */
- private void log(String msg) {
- Log.d(this, TAG + msg);
- }
-
- /**
- * Logs an error message.
- *
- * @param msg The message.
- */
- private void loge(String msg) {
- Log.e(this, TAG + msg);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/VideoUtils.java b/InCallUI/src/com/android/incallui/VideoUtils.java
deleted file mode 100644
index a2eb8bcf23780813dd339431c45490f916c732c6..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/VideoUtils.java
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui;
-
-import android.telecom.VideoProfile;
-
-import com.android.contacts.common.compat.CompatUtils;
-
-import com.google.common.base.Preconditions;
-
-public class VideoUtils {
-
- public static boolean isVideoCall(Call call) {
- return call != null && isVideoCall(call.getVideoState());
- }
-
- public static boolean isVideoCall(int videoState) {
- if (!CompatUtils.isVideoCompatible()) {
- return false;
- }
-
- return VideoProfile.isTransmissionEnabled(videoState)
- || VideoProfile.isReceptionEnabled(videoState);
- }
-
- public static boolean isBidirectionalVideoCall(Call call) {
- if (!CompatUtils.isVideoCompatible()) {
- return false;
- }
-
- return VideoProfile.isBidirectional(call.getVideoState());
- }
-
- public static boolean isTransmissionEnabled(Call call) {
- if (!CompatUtils.isVideoCompatible()) {
- return false;
- }
-
- return VideoProfile.isTransmissionEnabled(call.getVideoState());
- }
-
- public static boolean isIncomingVideoCall(Call call) {
- if (!VideoUtils.isVideoCall(call)) {
- return false;
- }
- final int state = call.getState();
- return (state == Call.State.INCOMING) || (state == Call.State.CALL_WAITING);
- }
-
- public static boolean isActiveVideoCall(Call call) {
- return VideoUtils.isVideoCall(call) && call.getState() == Call.State.ACTIVE;
- }
-
- public static boolean isOutgoingVideoCall(Call call) {
- if (!VideoUtils.isVideoCall(call)) {
- return false;
- }
- final int state = call.getState();
- return Call.State.isDialing(state) || state == Call.State.CONNECTING
- || state == Call.State.SELECT_PHONE_ACCOUNT;
- }
-
- public static boolean isAudioCall(Call call) {
- if (!CompatUtils.isVideoCompatible()) {
- return true;
- }
-
- return call != null && VideoProfile.isAudioOnly(call.getVideoState());
- }
-
- // TODO (ims-vt) Check if special handling is needed for CONF calls.
- public static boolean canVideoPause(Call call) {
- return isVideoCall(call) && call.getState() == Call.State.ACTIVE;
- }
-
- public static VideoProfile makeVideoPauseProfile(Call call) {
- Preconditions.checkNotNull(call);
- Preconditions.checkState(!VideoProfile.isAudioOnly(call.getVideoState()));
- return new VideoProfile(getPausedVideoState(call.getVideoState()));
- }
-
- public static VideoProfile makeVideoUnPauseProfile(Call call) {
- Preconditions.checkNotNull(call);
- return new VideoProfile(getUnPausedVideoState(call.getVideoState()));
- }
-
- public static int getUnPausedVideoState(int videoState) {
- return videoState & (~VideoProfile.STATE_PAUSED);
- }
-
- public static int getPausedVideoState(int videoState) {
- return videoState | VideoProfile.STATE_PAUSED;
- }
-
-}
diff --git a/InCallUI/src/com/android/incallui/async/PausableExecutor.java b/InCallUI/src/com/android/incallui/async/PausableExecutor.java
deleted file mode 100644
index 1b8201a796eebd6d0c9103c8470ab1872d18b7b0..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/async/PausableExecutor.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.async;
-
-import com.android.contacts.common.testing.NeededForTesting;
-
-import java.util.concurrent.Executor;
-
-/**
- * Executor that can be used to easily synchronize testing and production code. Production code
- * should call {@link #milestone()} at points in the code where the state of the system is worthy of
- * testing. In a test scenario, this method will pause execution until the test acknowledges the
- * milestone through the use of {@link #ackMilestoneForTesting()}.
- */
-public interface PausableExecutor extends Executor {
-
- /**
- * Method called from asynchronous production code to inform this executor that it has
- * reached a point that puts the system into a state worth testing. TestableExecutors intended
- * for use in a testing environment should cause the calling thread to block. In the production
- * environment this should be a no-op.
- */
- void milestone();
-
- /**
- * Method called from the test code to inform this executor that the state of the production
- * system at the current milestone has been sufficiently tested. Every milestone must be
- * acknowledged.
- */
- @NeededForTesting
- void ackMilestoneForTesting();
-
- /**
- * Method called from the test code to inform this executor that the tests are finished with all
- * milestones. Future calls to {@link #milestone()} or {@link #awaitMilestoneForTesting()}
- * should return immediately.
- */
- @NeededForTesting
- void ackAllMilestonesForTesting();
-
- /**
- * Method called from the test code to block until a milestone has been reached in the
- * production code.
- */
- @NeededForTesting
- void awaitMilestoneForTesting() throws InterruptedException;
-}
diff --git a/InCallUI/src/com/android/incallui/async/PausableExecutorImpl.java b/InCallUI/src/com/android/incallui/async/PausableExecutorImpl.java
deleted file mode 100644
index 15900e57b2af98c86b48576fb1ebb78574b2c084..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/async/PausableExecutorImpl.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.async;
-
-import java.util.concurrent.Executors;
-
-/**
- * {@link PausableExecutor} intended for use in production environments.
- */
-public class PausableExecutorImpl implements PausableExecutor {
-
- @Override
- public void milestone() {}
-
- @Override
- public void ackMilestoneForTesting() {}
-
- @Override
- public void ackAllMilestonesForTesting() {}
-
- @Override
- public void awaitMilestoneForTesting() {}
-
- @Override
- public void execute(Runnable command) {
- Executors.newSingleThreadExecutor().execute(command);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ringtone/DialerRingtoneManager.java b/InCallUI/src/com/android/incallui/ringtone/DialerRingtoneManager.java
deleted file mode 100644
index 39844e5a2f3f4ddc17c9d402eb7cc75f85136c14..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ringtone/DialerRingtoneManager.java
+++ /dev/null
@@ -1,140 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui.ringtone;
-
-import com.google.common.base.Preconditions;
-
-import android.content.ContentResolver;
-import android.net.Uri;
-import android.provider.Settings;
-import android.support.annotation.Nullable;
-
-import com.android.contacts.common.compat.CompatUtils;
-import com.android.contacts.common.testing.NeededForTesting;
-import com.android.incallui.Call;
-import com.android.incallui.Call.State;
-import com.android.incallui.CallList;
-
-/**
- * Class that determines when ringtones should be played and can play the call waiting tone when
- * necessary.
- */
-public class DialerRingtoneManager {
-
- /*
- * Flag used to determine if the Dialer is responsible for playing ringtones for incoming calls.
- * Once we're ready to enable Dialer Ringing, these flags should be removed.
- */
- private static final boolean IS_DIALER_RINGING_ENABLED = false;
- private Boolean mIsDialerRingingEnabledForTesting;
-
- private final InCallTonePlayer mInCallTonePlayer;
- private final CallList mCallList;
-
- /**
- * Creates the DialerRingtoneManager with the given {@link InCallTonePlayer}.
- *
- * @param inCallTonePlayer the tone player used to play in-call tones.
- * @param callList the CallList used to check for {@link State#CALL_WAITING}
- * @throws NullPointerException if inCallTonePlayer or callList are null
- */
- public DialerRingtoneManager(InCallTonePlayer inCallTonePlayer, CallList callList) {
- mInCallTonePlayer = Preconditions.checkNotNull(inCallTonePlayer);
- mCallList = Preconditions.checkNotNull(callList);
- }
-
- /**
- * Determines if a ringtone should be played for the given call state (see {@link State}) and
- * {@link Uri}.
- *
- * @param callState the call state for the call being checked.
- * @param ringtoneUri the ringtone to potentially play.
- * @return {@code true} if the ringtone should be played, {@code false} otherwise.
- */
- public boolean shouldPlayRingtone(int callState, @Nullable Uri ringtoneUri) {
- return isDialerRingingEnabled()
- && translateCallStateForCallWaiting(callState) == State.INCOMING
- && ringtoneUri != null;
- }
-
- /**
- * Determines if an incoming call should vibrate as well as ring.
- *
- * @param resolver {@link ContentResolver} used to look up the
- * {@link Settings.System#VIBRATE_WHEN_RINGING} setting.
- * @return {@code true} if the call should vibrate, {@code false} otherwise.
- */
- public boolean shouldVibrate(ContentResolver resolver) {
- return Settings.System.getInt(resolver, Settings.System.VIBRATE_WHEN_RINGING, 0) != 0;
- }
-
- /**
- * The incoming callState is never set as {@link State#CALL_WAITING} because
- * {@link Call#translateState(int)} doesn't account for that case, check for it here
- */
- private int translateCallStateForCallWaiting(int callState) {
- if (callState != State.INCOMING) {
- return callState;
- }
- return mCallList.getActiveCall() == null ? State.INCOMING : State.CALL_WAITING;
- }
-
- private boolean isDialerRingingEnabled() {
- if (mIsDialerRingingEnabledForTesting != null) {
- return mIsDialerRingingEnabledForTesting;
- }
- return CompatUtils.isNCompatible() && IS_DIALER_RINGING_ENABLED;
- }
-
- /**
- * Determines if a call waiting tone should be played for the the given call state
- * (see {@link State}).
- *
- * @param callState the call state for the call being checked.
- * @return {@code true} if the call waiting tone should be played, {@code false} otherwise.
- */
- public boolean shouldPlayCallWaitingTone(int callState) {
- return isDialerRingingEnabled()
- && translateCallStateForCallWaiting(callState) == State.CALL_WAITING
- && !mInCallTonePlayer.isPlayingTone();
- }
-
- /**
- * Plays the call waiting tone.
- */
- public void playCallWaitingTone() {
- if (!isDialerRingingEnabled()) {
- return;
- }
- mInCallTonePlayer.play(InCallTonePlayer.TONE_CALL_WAITING);
- }
-
- /**
- * Stops playing the call waiting tone.
- */
- public void stopCallWaitingTone() {
- if (!isDialerRingingEnabled()) {
- return;
- }
- mInCallTonePlayer.stop();
- }
-
- @NeededForTesting
- void setDialerRingingEnabledForTesting(boolean status) {
- mIsDialerRingingEnabledForTesting = status;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ringtone/InCallTonePlayer.java b/InCallUI/src/com/android/incallui/ringtone/InCallTonePlayer.java
deleted file mode 100644
index 3a8b03d910900ce8cbe18dc00fc70bcc3e966428..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ringtone/InCallTonePlayer.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.ringtone;
-
-import com.google.common.base.MoreObjects;
-import com.google.common.base.Preconditions;
-
-import android.media.AudioManager;
-import android.media.ToneGenerator;
-import android.support.annotation.Nullable;
-
-import com.android.incallui.Log;
-import com.android.incallui.async.PausableExecutor;
-
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.TimeUnit;
-
-/**
- * Class responsible for playing in-call related tones in a background thread. This class only
- * allows one tone to be played at a time.
- */
-public class InCallTonePlayer {
-
- public static final int TONE_CALL_WAITING = 4;
-
- public static final int VOLUME_RELATIVE_HIGH_PRIORITY = 80;
-
- private final ToneGeneratorFactory mToneGeneratorFactory;
- private final PausableExecutor mExecutor;
- private @Nullable CountDownLatch mNumPlayingTones;
-
- /**
- * Creates a new InCallTonePlayer.
- *
- * @param toneGeneratorFactory the {@link ToneGeneratorFactory} used to create
- * {@link ToneGenerator}s.
- * @param executor the {@link PausableExecutor} used to play tones in a background thread.
- * @throws NullPointerException if audioModeProvider, toneGeneratorFactory, or executor are
- * {@code null}.
- */
- public InCallTonePlayer(ToneGeneratorFactory toneGeneratorFactory, PausableExecutor executor) {
- mToneGeneratorFactory = Preconditions.checkNotNull(toneGeneratorFactory);
- mExecutor = Preconditions.checkNotNull(executor);
- }
-
- /**
- * @return {@code true} if a tone is currently playing, {@code false} otherwise.
- */
- public boolean isPlayingTone() {
- return mNumPlayingTones != null && mNumPlayingTones.getCount() > 0;
- }
-
- /**
- * Plays the given tone in a background thread.
- *
- * @param tone the tone to play.
- * @throws IllegalStateException if a tone is already playing.
- * @throws IllegalArgumentException if the tone is invalid.
- */
- public void play(int tone) {
- if (isPlayingTone()) {
- throw new IllegalStateException("Tone already playing");
- }
- final ToneGeneratorInfo info = getToneGeneratorInfo(tone);
- mNumPlayingTones = new CountDownLatch(1);
- mExecutor.execute(new Runnable() {
- @Override
- public void run() {
- playOnBackgroundThread(info);
- }
- });
- }
-
- private ToneGeneratorInfo getToneGeneratorInfo(int tone) {
- switch (tone) {
- case TONE_CALL_WAITING:
- /*
- * Call waiting tones play until they're stopped either by the user accepting or
- * declining the call so the tone length is set at what's effectively forever. The
- * tone is played at a high priority volume and through STREAM_VOICE_CALL since it's
- * call related and using that stream will route it through bluetooth devices
- * appropriately.
- */
- return new ToneGeneratorInfo(ToneGenerator.TONE_SUP_CALL_WAITING,
- VOLUME_RELATIVE_HIGH_PRIORITY,
- Integer.MAX_VALUE,
- AudioManager.STREAM_VOICE_CALL);
- default:
- throw new IllegalArgumentException("Bad tone: " + tone);
- }
- }
-
- private void playOnBackgroundThread(ToneGeneratorInfo info) {
- ToneGenerator toneGenerator = null;
- try {
- Log.v(this, "Starting tone " + info);
- toneGenerator = mToneGeneratorFactory.newInCallToneGenerator(info.stream, info.volume);
- toneGenerator.startTone(info.tone);
- /*
- * During tests, this will block until the tests call mExecutor.ackMilestone. This call
- * allows for synchronization to the point where the tone has started playing.
- */
- mExecutor.milestone();
- if (mNumPlayingTones != null) {
- mNumPlayingTones.await(info.toneLengthMillis, TimeUnit.MILLISECONDS);
- // Allows for synchronization to the point where the tone has completed playing.
- mExecutor.milestone();
- }
- } catch (InterruptedException e) {
- Log.w(this, "Interrupted while playing in-call tone.");
- } finally {
- if (toneGenerator != null) {
- toneGenerator.release();
- }
- if (mNumPlayingTones != null) {
- mNumPlayingTones.countDown();
- }
- // Allows for synchronization to the point where this background thread has cleaned up.
- mExecutor.milestone();
- }
- }
-
- /**
- * Stops playback of the current tone.
- */
- public void stop() {
- if (mNumPlayingTones != null) {
- mNumPlayingTones.countDown();
- }
- }
-
- private static class ToneGeneratorInfo {
- public final int tone;
- public final int volume;
- public final int toneLengthMillis;
- public final int stream;
-
- public ToneGeneratorInfo(int toneGeneratorType, int volume, int toneLengthMillis,
- int stream) {
- this.tone = toneGeneratorType;
- this.volume = volume;
- this.toneLengthMillis = toneLengthMillis;
- this.stream = stream;
- }
-
- @Override
- public String toString() {
- return MoreObjects.toStringHelper(this)
- .add("tone", tone)
- .add("volume", volume)
- .add("toneLengthMillis", toneLengthMillis).toString();
- }
- }
-}
diff --git a/InCallUI/src/com/android/incallui/ringtone/ToneGeneratorFactory.java b/InCallUI/src/com/android/incallui/ringtone/ToneGeneratorFactory.java
deleted file mode 100644
index ac47c8a7dadee86285b2bb00b8b3e229189dbfa3..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/ringtone/ToneGeneratorFactory.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.ringtone;
-
-import android.media.ToneGenerator;
-
-/**
- * Factory used to create {@link ToneGenerator}s.
- */
-public class ToneGeneratorFactory {
-
- /**
- * Creates a new {@link ToneGenerator} to use while in a call.
- *
- * @param stream the stream through which to play tones.
- * @param volume the volume at which to play tones.
- * @return a new ToneGenerator.
- */
- public ToneGenerator newInCallToneGenerator(int stream, int volume) {
- return new ToneGenerator(stream, volume);
- }
-}
diff --git a/InCallUI/src/com/android/incallui/service/PhoneNumberService.java b/InCallUI/src/com/android/incallui/service/PhoneNumberService.java
deleted file mode 100644
index 70da4ef3a75a6f8dd3a67e56f93e7a27e6bc5f06..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/service/PhoneNumberService.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui.service;
-
-import android.graphics.Bitmap;
-
-/**
- * Provides phone number lookup services.
- */
-public interface PhoneNumberService {
-
- /**
- * Get a phone number number asynchronously.
- *
- * @param phoneNumber The phone number to lookup.
- * @param listener The listener to notify when the phone number lookup is complete.
- * @param imageListener The listener to notify when the image lookup is complete.
- */
- public void getPhoneNumberInfo(String phoneNumber, NumberLookupListener listener,
- ImageLookupListener imageListener, boolean isIncoming);
-
- public interface NumberLookupListener {
-
- /**
- * Callback when a phone number has been looked up.
- *
- * @param info The looked up information. Or (@literal null} if there are no results.
- */
- public void onPhoneNumberInfoComplete(PhoneNumberInfo info);
- }
-
- public interface ImageLookupListener {
-
- /**
- * Callback when a image has been fetched.
- *
- * @param bitmap The fetched image.
- */
- public void onImageFetchComplete(Bitmap bitmap);
- }
-
- public interface PhoneNumberInfo {
- public String getDisplayName();
- public String getNumber();
- public int getPhoneType();
- public String getPhoneLabel();
- public String getNormalizedNumber();
- public String getImageUrl();
- public String getLookupKey();
- public boolean isBusiness();
- public int getLookupSource();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/spam/SpamCallListListener.java b/InCallUI/src/com/android/incallui/spam/SpamCallListListener.java
deleted file mode 100644
index b97f4d099996a118eb0b736f2bd954f5adafa942..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/spam/SpamCallListListener.java
+++ /dev/null
@@ -1,117 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui.spam;
-
-import com.google.common.annotations.VisibleForTesting;
-
-import android.content.Context;
-import android.telecom.DisconnectCause;
-import android.text.TextUtils;
-
-import com.android.dialer.calllog.CallLogAsyncTaskUtil;
-import com.android.incallui.Call;
-import com.android.incallui.CallList;
-import com.android.incallui.Log;
-
-public class SpamCallListListener implements CallList.Listener {
- private static final String TAG = "SpamCallListListener";
-
- private final Context mContext;
-
- public SpamCallListListener(Context context) {
- mContext = context;
- }
-
- @Override
- public void onIncomingCall(final Call call) {
- String number = call.getNumber();
- if (TextUtils.isEmpty(number)) {
- return;
- }
- CallLogAsyncTaskUtil.getNumberInCallHistory(mContext, number,
- new CallLogAsyncTaskUtil.OnGetNumberInCallHistoryListener() {
- @Override
- public void onComplete(boolean inCallHistory) {
- call.setCallHistoryStatus(inCallHistory ?
- Call.CALL_HISTORY_STATUS_PRESENT
- : Call.CALL_HISTORY_STATUS_NOT_PRESENT);
- }
- });
- }
-
- @Override
- public void onUpgradeToVideo(Call call) {}
-
- @Override
- public void onCallListChange(CallList callList) {}
-
- @Override
- public void onDisconnect(Call call) {
- if (shouldShowAfterCallNotification(call)) {
- showNotification(call.getNumber());
- }
- }
-
- /**
- * Posts the intent for displaying the after call spam notification to the user.
- */
- @VisibleForTesting
- /* package */ void showNotification(String number) {
- //TODO(mhashmi): build and show notifications here
- }
-
- /**
- * Determines if the after call notification should be shown for the specified call.
- */
- private boolean shouldShowAfterCallNotification(Call call) {
- String number = call.getNumber();
- if (TextUtils.isEmpty(number)) {
- return false;
- }
-
- Call.LogState logState = call.getLogState();
- if (!logState.isIncoming) {
- return false;
- }
-
- if (logState.duration <= 0) {
- return false;
- }
-
- if (logState.contactLookupResult != Call.LogState.LOOKUP_NOT_FOUND
- && logState.contactLookupResult != Call.LogState.LOOKUP_UNKNOWN) {
- return false;
- }
-
- int callHistoryStatus = call.getCallHistoryStatus();
- if (callHistoryStatus == Call.CALL_HISTORY_STATUS_PRESENT) {
- return false;
- } else if (callHistoryStatus == Call.CALL_HISTORY_STATUS_UNKNOWN) {
- Log.i(TAG, "Call history status is unknown, returning false");
- return false;
- }
-
- // Check if call disconnected because of either user hanging up
- int disconnectCause = call.getDisconnectCause().getCode();
- if (disconnectCause != DisconnectCause.LOCAL && disconnectCause != DisconnectCause.REMOTE) {
- return false;
- }
-
- Log.i(TAG, "shouldShowAfterCallNotification, returning true");
- return true;
- }
-}
\ No newline at end of file
diff --git a/InCallUI/src/com/android/incallui/util/AccessibilityUtil.java b/InCallUI/src/com/android/incallui/util/AccessibilityUtil.java
deleted file mode 100644
index 1fdd2bac6a4e0a6825ca4e62120ae56e7c13bbcd..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/util/AccessibilityUtil.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.incallui.util;
-
-import android.content.Context;
-import android.view.accessibility.AccessibilityManager;
-
-public class AccessibilityUtil {
- public static boolean isTalkBackEnabled(Context context) {
- AccessibilityManager accessibilityManager = (AccessibilityManager) context
- .getSystemService(Context.ACCESSIBILITY_SERVICE);
- return accessibilityManager != null
- && accessibilityManager.isEnabled()
- && accessibilityManager.isTouchExplorationEnabled();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/util/TelecomCallUtil.java b/InCallUI/src/com/android/incallui/util/TelecomCallUtil.java
deleted file mode 100644
index 53ecc29e9aba5485c3f8c834f269d065472f230d..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/util/TelecomCallUtil.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.util;
-
-import android.net.Uri;
-import android.telecom.Call;
-import android.telephony.PhoneNumberUtils;
-
-/**
- * Class to provide a standard interface for obtaining information from the underlying
- * android.telecom.Call. Much of this should be obtained through the incall.Call, but
- * on occasion we need to interact with the telecom.Call directly (eg. call blocking,
- * before the incall.Call has been created).
- */
-public class TelecomCallUtil {
-
- // Whether the call handle is an emergency number.
- public static boolean isEmergencyCall(Call call) {
- Uri handle = call.getDetails().getHandle();
- return PhoneNumberUtils.isEmergencyNumber(
- handle == null ? "" : handle.getSchemeSpecificPart());
- }
-
- public static String getNumber(Call call) {
- if (call == null) {
- return null;
- }
- if (call.getDetails().getGatewayInfo() != null) {
- return call.getDetails().getGatewayInfo()
- .getOriginalAddress().getSchemeSpecificPart();
- }
- Uri handle = getHandle(call);
- return handle == null ? null : handle.getSchemeSpecificPart();
- }
-
- public static Uri getHandle(Call call) {
- return call == null ? null : call.getDetails().getHandle();
- }
-}
diff --git a/InCallUI/src/com/android/incallui/widget/multiwaveview/Ease.java b/InCallUI/src/com/android/incallui/widget/multiwaveview/Ease.java
deleted file mode 100644
index 5ef689771851d8b5201416d2b9fb19bee8488119..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/widget/multiwaveview/Ease.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.widget.multiwaveview;
-
-import android.animation.TimeInterpolator;
-
-class Ease {
- private static final float DOMAIN = 1.0f;
- private static final float DURATION = 1.0f;
- private static final float START = 0.0f;
-
- static class Linear {
- public static final TimeInterpolator easeNone = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return input;
- }
- };
- }
-
- static class Cubic {
- public static final TimeInterpolator easeIn = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return DOMAIN*(input/=DURATION)*input*input + START;
- }
- };
- public static final TimeInterpolator easeOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return DOMAIN*((input=input/DURATION-1)*input*input + 1) + START;
- }
- };
- public static final TimeInterpolator easeInOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return ((input/=DURATION/2) < 1.0f) ?
- (DOMAIN/2*input*input*input + START)
- : (DOMAIN/2*((input-=2)*input*input + 2) + START);
- }
- };
- }
-
- static class Quad {
- public static final TimeInterpolator easeIn = new TimeInterpolator() {
- public float getInterpolation (float input) {
- return DOMAIN*(input/=DURATION)*input + START;
- }
- };
- public static final TimeInterpolator easeOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return -DOMAIN *(input/=DURATION)*(input-2) + START;
- }
- };
- public static final TimeInterpolator easeInOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return ((input/=DURATION/2) < 1) ?
- (DOMAIN/2*input*input + START)
- : (-DOMAIN/2 * ((--input)*(input-2) - 1) + START);
- }
- };
- }
-
- static class Quart {
- public static final TimeInterpolator easeIn = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return DOMAIN*(input/=DURATION)*input*input*input + START;
- }
- };
- public static final TimeInterpolator easeOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return -DOMAIN * ((input=input/DURATION-1)*input*input*input - 1) + START;
- }
- };
- public static final TimeInterpolator easeInOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return ((input/=DURATION/2) < 1) ?
- (DOMAIN/2*input*input*input*input + START)
- : (-DOMAIN/2 * ((input-=2)*input*input*input - 2) + START);
- }
- };
- }
-
- static class Quint {
- public static final TimeInterpolator easeIn = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return DOMAIN*(input/=DURATION)*input*input*input*input + START;
- }
- };
- public static final TimeInterpolator easeOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return DOMAIN*((input=input/DURATION-1)*input*input*input*input + 1) + START;
- }
- };
- public static final TimeInterpolator easeInOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return ((input/=DURATION/2) < 1) ?
- (DOMAIN/2*input*input*input*input*input + START)
- : (DOMAIN/2*((input-=2)*input*input*input*input + 2) + START);
- }
- };
- }
-
- static class Sine {
- public static final TimeInterpolator easeIn = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return -DOMAIN * (float) Math.cos(input/DURATION * (Math.PI/2)) + DOMAIN + START;
- }
- };
- public static final TimeInterpolator easeOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return DOMAIN * (float) Math.sin(input/DURATION * (Math.PI/2)) + START;
- }
- };
- public static final TimeInterpolator easeInOut = new TimeInterpolator() {
- public float getInterpolation(float input) {
- return -DOMAIN/2 * ((float)Math.cos(Math.PI*input/DURATION) - 1.0f) + START;
- }
- };
- }
-
-}
diff --git a/InCallUI/src/com/android/incallui/widget/multiwaveview/GlowPadView.java b/InCallUI/src/com/android/incallui/widget/multiwaveview/GlowPadView.java
deleted file mode 100644
index efeb4b7e36c57f758242c71d37291746cd42a3ad..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/widget/multiwaveview/GlowPadView.java
+++ /dev/null
@@ -1,1473 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.widget.multiwaveview;
-
-import android.animation.Animator;
-import android.animation.Animator.AnimatorListener;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.TimeInterpolator;
-import android.animation.ValueAnimator;
-import android.animation.ValueAnimator.AnimatorUpdateListener;
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.pm.PackageManager;
-import android.content.pm.PackageManager.NameNotFoundException;
-import android.content.res.Resources;
-import android.content.res.TypedArray;
-import android.graphics.Canvas;
-import android.graphics.Rect;
-import android.graphics.drawable.Drawable;
-import android.os.Bundle;
-import android.os.Vibrator;
-import android.support.v4.view.ViewCompat;
-import android.support.v4.view.accessibility.AccessibilityEventCompat;
-import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat;
-import android.support.v4.widget.ExploreByTouchHelper;
-import android.text.TextUtils;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.util.TypedValue;
-import android.view.Gravity;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.accessibility.AccessibilityEvent;
-import android.view.accessibility.AccessibilityManager;
-import android.view.accessibility.AccessibilityNodeInfo;
-import android.view.accessibility.AccessibilityNodeInfo.AccessibilityAction;
-import android.view.accessibility.AccessibilityNodeProvider;
-
-import com.android.dialer.R;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * This is a copy of com.android.internal.widget.multiwaveview.GlowPadView with minor changes
- * to remove dependencies on private api's.
- *
- * Incoporated the scaling functionality.
- *
- * A re-usable widget containing a center, outer ring and wave animation.
- */
-public class GlowPadView extends View {
- private static final String TAG = "GlowPadView";
- private static final boolean DEBUG = false;
-
- // Wave state machine
- private static final int STATE_IDLE = 0;
- private static final int STATE_START = 1;
- private static final int STATE_FIRST_TOUCH = 2;
- private static final int STATE_TRACKING = 3;
- private static final int STATE_SNAP = 4;
- private static final int STATE_FINISH = 5;
-
- // Animation properties.
- private static final float SNAP_MARGIN_DEFAULT = 20.0f; // distance to ring before we snap to it
-
- public interface OnTriggerListener {
- int NO_HANDLE = 0;
- int CENTER_HANDLE = 1;
- public void onGrabbed(View v, int handle);
- public void onReleased(View v, int handle);
- public void onTrigger(View v, int target);
- public void onGrabbedStateChange(View v, int handle);
- public void onFinishFinalAnimation();
- }
-
- // Tuneable parameters for animation
- private static final int WAVE_ANIMATION_DURATION = 1350;
- private static final int RETURN_TO_HOME_DELAY = 1200;
- private static final int RETURN_TO_HOME_DURATION = 200;
- private static final int HIDE_ANIMATION_DELAY = 200;
- private static final int HIDE_ANIMATION_DURATION = 200;
- private static final int SHOW_ANIMATION_DURATION = 200;
- private static final int SHOW_ANIMATION_DELAY = 50;
- private static final int INITIAL_SHOW_HANDLE_DURATION = 200;
- private static final int REVEAL_GLOW_DELAY = 0;
- private static final int REVEAL_GLOW_DURATION = 0;
-
- private static final float TAP_RADIUS_SCALE_ACCESSIBILITY_ENABLED = 1.3f;
- private static final float TARGET_SCALE_EXPANDED = 1.0f;
- private static final float TARGET_SCALE_COLLAPSED = 0.8f;
- private static final float RING_SCALE_EXPANDED = 1.0f;
- private static final float RING_SCALE_COLLAPSED = 0.5f;
-
- private ArrayList mTargetDrawables = new ArrayList();
- private AnimationBundle mWaveAnimations = new AnimationBundle();
- private AnimationBundle mTargetAnimations = new AnimationBundle();
- private AnimationBundle mGlowAnimations = new AnimationBundle();
- private ArrayList mTargetDescriptions;
- private ArrayList mDirectionDescriptions;
- private OnTriggerListener mOnTriggerListener;
- private TargetDrawable mHandleDrawable;
- private TargetDrawable mOuterRing;
- private Vibrator mVibrator;
-
- private int mFeedbackCount = 3;
- private int mVibrationDuration = 0;
- private int mGrabbedState;
- private int mActiveTarget = -1;
- private float mGlowRadius;
- private float mWaveCenterX;
- private float mWaveCenterY;
- private int mMaxTargetHeight;
- private int mMaxTargetWidth;
- private float mRingScaleFactor = 1f;
- private boolean mAllowScaling;
-
- private float mOuterRadius = 0.0f;
- private float mSnapMargin = 0.0f;
- private boolean mDragging;
- private int mNewTargetResources;
-
- private AccessibilityNodeProvider mAccessibilityNodeProvider;
- private GlowpadExploreByTouchHelper mExploreByTouchHelper;
-
- private class AnimationBundle extends ArrayList {
- private static final long serialVersionUID = 0xA84D78726F127468L;
- private boolean mSuspended;
-
- public void start() {
- if (mSuspended) return; // ignore attempts to start animations
- final int count = size();
- for (int i = 0; i < count; i++) {
- Tweener anim = get(i);
- anim.animator.start();
- }
- }
-
- public void cancel() {
- final int count = size();
- for (int i = 0; i < count; i++) {
- Tweener anim = get(i);
- anim.animator.cancel();
- }
- clear();
- }
-
- public void stop() {
- final int count = size();
- for (int i = 0; i < count; i++) {
- Tweener anim = get(i);
- anim.animator.end();
- }
- clear();
- }
-
- public void setSuspended(boolean suspend) {
- mSuspended = suspend;
- }
- };
-
- private AnimatorListener mResetListener = new AnimatorListenerAdapter() {
- public void onAnimationEnd(Animator animator) {
- switchToState(STATE_IDLE, mWaveCenterX, mWaveCenterY);
- dispatchOnFinishFinalAnimation();
- }
- };
-
- private AnimatorListener mResetListenerWithPing = new AnimatorListenerAdapter() {
- public void onAnimationEnd(Animator animator) {
- ping();
- switchToState(STATE_IDLE, mWaveCenterX, mWaveCenterY);
- dispatchOnFinishFinalAnimation();
- }
- };
-
- private AnimatorUpdateListener mUpdateListener = new AnimatorUpdateListener() {
- public void onAnimationUpdate(ValueAnimator animation) {
- invalidate();
- }
- };
-
- private boolean mAnimatingTargets;
- private AnimatorListener mTargetUpdateListener = new AnimatorListenerAdapter() {
- public void onAnimationEnd(Animator animator) {
- if (mNewTargetResources != 0) {
- internalSetTargetResources(mNewTargetResources);
- mNewTargetResources = 0;
- hideTargets(false, false);
- }
- mAnimatingTargets = false;
- }
- };
- private int mTargetResourceId;
- private int mTargetDescriptionsResourceId;
- private int mDirectionDescriptionsResourceId;
- private boolean mAlwaysTrackFinger;
- private int mHorizontalInset;
- private int mVerticalInset;
- private int mGravity = Gravity.TOP;
- private boolean mInitialLayout = true;
- private Tweener mBackgroundAnimator;
- private PointCloud mPointCloud;
- private float mInnerRadius;
- private int mPointerId;
-
- public GlowPadView(Context context) {
- this(context, null);
- }
-
- public GlowPadView(Context context, AttributeSet attrs) {
- super(context, attrs);
- Resources res = context.getResources();
-
- TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.GlowPadView);
- mInnerRadius = a.getDimension(R.styleable.GlowPadView_innerRadius, mInnerRadius);
- mOuterRadius = a.getDimension(R.styleable.GlowPadView_outerRadius, mOuterRadius);
- mSnapMargin = a.getDimension(R.styleable.GlowPadView_snapMargin, mSnapMargin);
- mVibrationDuration = a.getInt(R.styleable.GlowPadView_vibrationDuration,
- mVibrationDuration);
- mFeedbackCount = a.getInt(R.styleable.GlowPadView_feedbackCount,
- mFeedbackCount);
- mAllowScaling = a.getBoolean(R.styleable.GlowPadView_allowScaling, false);
- TypedValue handle = a.peekValue(R.styleable.GlowPadView_handleDrawable);
- setHandleDrawable(handle != null ? handle.resourceId : R.drawable.ic_incall_audio_handle);
- mOuterRing = new TargetDrawable(res,
- getResourceId(a, R.styleable.GlowPadView_outerRingDrawable), 1);
-
- mAlwaysTrackFinger = a.getBoolean(R.styleable.GlowPadView_alwaysTrackFinger, false);
-
- int pointId = getResourceId(a, R.styleable.GlowPadView_pointDrawable);
- Drawable pointDrawable = pointId != 0 ? res.getDrawable(pointId) : null;
- mGlowRadius = a.getDimension(R.styleable.GlowPadView_glowRadius, 0.0f);
-
- TypedValue outValue = new TypedValue();
-
- // Read array of target drawables
- if (a.getValue(R.styleable.GlowPadView_targetDrawables, outValue)) {
- internalSetTargetResources(outValue.resourceId);
- }
- if (mTargetDrawables == null || mTargetDrawables.size() == 0) {
- throw new IllegalStateException("Must specify at least one target drawable");
- }
-
- // Read array of target descriptions
- if (a.getValue(R.styleable.GlowPadView_targetDescriptions, outValue)) {
- final int resourceId = outValue.resourceId;
- if (resourceId == 0) {
- throw new IllegalStateException("Must specify target descriptions");
- }
- setTargetDescriptionsResourceId(resourceId);
- }
-
- // Read array of direction descriptions
- if (a.getValue(R.styleable.GlowPadView_directionDescriptions, outValue)) {
- final int resourceId = outValue.resourceId;
- if (resourceId == 0) {
- throw new IllegalStateException("Must specify direction descriptions");
- }
- setDirectionDescriptionsResourceId(resourceId);
- }
-
- // Use gravity attribute from LinearLayout
- //a = context.obtainStyledAttributes(attrs, R.styleable.LinearLayout);
- mGravity = a.getInt(R.styleable.GlowPadView_android_gravity, Gravity.TOP);
- a.recycle();
-
-
- setVibrateEnabled(mVibrationDuration > 0);
-
- assignDefaultsIfNeeded();
-
- mPointCloud = new PointCloud(pointDrawable);
- mPointCloud.makePointCloud(mInnerRadius, mOuterRadius);
- mPointCloud.glowManager.setRadius(mGlowRadius);
-
- mExploreByTouchHelper = new GlowpadExploreByTouchHelper(this);
- ViewCompat.setAccessibilityDelegate(this, mExploreByTouchHelper);
- }
-
- private int getResourceId(TypedArray a, int id) {
- TypedValue tv = a.peekValue(id);
- return tv == null ? 0 : tv.resourceId;
- }
-
- private void dump() {
- Log.v(TAG, "Outer Radius = " + mOuterRadius);
- Log.v(TAG, "SnapMargin = " + mSnapMargin);
- Log.v(TAG, "FeedbackCount = " + mFeedbackCount);
- Log.v(TAG, "VibrationDuration = " + mVibrationDuration);
- Log.v(TAG, "GlowRadius = " + mGlowRadius);
- Log.v(TAG, "WaveCenterX = " + mWaveCenterX);
- Log.v(TAG, "WaveCenterY = " + mWaveCenterY);
- }
-
- public void suspendAnimations() {
- mWaveAnimations.setSuspended(true);
- mTargetAnimations.setSuspended(true);
- mGlowAnimations.setSuspended(true);
- }
-
- public void resumeAnimations() {
- mWaveAnimations.setSuspended(false);
- mTargetAnimations.setSuspended(false);
- mGlowAnimations.setSuspended(false);
- mWaveAnimations.start();
- mTargetAnimations.start();
- mGlowAnimations.start();
- }
-
- @Override
- protected int getSuggestedMinimumWidth() {
- // View should be large enough to contain the background + handle and
- // target drawable on either edge.
- return (int) (Math.max(mOuterRing.getWidth(), 2 * mOuterRadius) + mMaxTargetWidth);
- }
-
- @Override
- protected int getSuggestedMinimumHeight() {
- // View should be large enough to contain the unlock ring + target and
- // target drawable on either edge
- return (int) (Math.max(mOuterRing.getHeight(), 2 * mOuterRadius) + mMaxTargetHeight);
- }
-
- /**
- * This gets the suggested width accounting for the ring's scale factor.
- */
- protected int getScaledSuggestedMinimumWidth() {
- return (int) (mRingScaleFactor * Math.max(mOuterRing.getWidth(), 2 * mOuterRadius)
- + mMaxTargetWidth);
- }
-
- /**
- * This gets the suggested height accounting for the ring's scale factor.
- */
- protected int getScaledSuggestedMinimumHeight() {
- return (int) (mRingScaleFactor * Math.max(mOuterRing.getHeight(), 2 * mOuterRadius)
- + mMaxTargetHeight);
- }
-
- private int resolveMeasured(int measureSpec, int desired)
- {
- int result = 0;
- int specSize = MeasureSpec.getSize(measureSpec);
- switch (MeasureSpec.getMode(measureSpec)) {
- case MeasureSpec.UNSPECIFIED:
- result = desired;
- break;
- case MeasureSpec.AT_MOST:
- result = Math.min(specSize, desired);
- break;
- case MeasureSpec.EXACTLY:
- default:
- result = specSize;
- }
- return result;
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- final int minimumWidth = getSuggestedMinimumWidth();
- final int minimumHeight = getSuggestedMinimumHeight();
- int computedWidth = resolveMeasured(widthMeasureSpec, minimumWidth);
- int computedHeight = resolveMeasured(heightMeasureSpec, minimumHeight);
-
- mRingScaleFactor = computeScaleFactor(minimumWidth, minimumHeight,
- computedWidth, computedHeight);
-
- int scaledWidth = getScaledSuggestedMinimumWidth();
- int scaledHeight = getScaledSuggestedMinimumHeight();
-
- computeInsets(computedWidth - scaledWidth, computedHeight - scaledHeight);
- setMeasuredDimension(computedWidth, computedHeight);
- }
-
- private void switchToState(int state, float x, float y) {
- switch (state) {
- case STATE_IDLE:
- deactivateTargets();
- hideGlow(0, 0, 0.0f, null);
- startBackgroundAnimation(0, 0.0f);
- mHandleDrawable.setState(TargetDrawable.STATE_INACTIVE);
- mHandleDrawable.setAlpha(1.0f);
- break;
-
- case STATE_START:
- startBackgroundAnimation(0, 0.0f);
- break;
-
- case STATE_FIRST_TOUCH:
- mHandleDrawable.setAlpha(0.0f);
- deactivateTargets();
- showTargets(true);
- startBackgroundAnimation(INITIAL_SHOW_HANDLE_DURATION, 1.0f);
- setGrabbedState(OnTriggerListener.CENTER_HANDLE);
-
- final AccessibilityManager accessibilityManager =
- (AccessibilityManager) getContext().getSystemService(
- Context.ACCESSIBILITY_SERVICE);
- if (accessibilityManager.isEnabled()) {
- announceTargets();
- }
- break;
-
- case STATE_TRACKING:
- mHandleDrawable.setAlpha(0.0f);
- break;
-
- case STATE_SNAP:
- // TODO: Add transition states (see list_selector_background_transition.xml)
- mHandleDrawable.setAlpha(0.0f);
- showGlow(REVEAL_GLOW_DURATION , REVEAL_GLOW_DELAY, 0.0f, null);
- break;
-
- case STATE_FINISH:
- doFinish();
- break;
- }
- }
-
- private void showGlow(int duration, int delay, float finalAlpha,
- AnimatorListener finishListener) {
- mGlowAnimations.cancel();
- mGlowAnimations.add(Tweener.to(mPointCloud.glowManager, duration,
- "ease", Ease.Cubic.easeIn,
- "delay", delay,
- "alpha", finalAlpha,
- "onUpdate", mUpdateListener,
- "onComplete", finishListener));
- mGlowAnimations.start();
- }
-
- private void hideGlow(int duration, int delay, float finalAlpha,
- AnimatorListener finishListener) {
- mGlowAnimations.cancel();
- mGlowAnimations.add(Tweener.to(mPointCloud.glowManager, duration,
- "ease", Ease.Quart.easeOut,
- "delay", delay,
- "alpha", finalAlpha,
- "x", 0.0f,
- "y", 0.0f,
- "onUpdate", mUpdateListener,
- "onComplete", finishListener));
- mGlowAnimations.start();
- }
-
- private void deactivateTargets() {
- final int count = mTargetDrawables.size();
- for (int i = 0; i < count; i++) {
- TargetDrawable target = mTargetDrawables.get(i);
- target.setState(TargetDrawable.STATE_INACTIVE);
- }
- mActiveTarget = -1;
- }
-
- /**
- * Dispatches a trigger event to listener. Ignored if a listener is not set.
- * @param whichTarget the target that was triggered.
- */
- private void dispatchTriggerEvent(int whichTarget) {
- vibrate();
- if (mOnTriggerListener != null) {
- mOnTriggerListener.onTrigger(this, whichTarget);
- }
- }
-
- private void dispatchOnFinishFinalAnimation() {
- if (mOnTriggerListener != null) {
- mOnTriggerListener.onFinishFinalAnimation();
- }
- }
-
- private void doFinish() {
- final int activeTarget = mActiveTarget;
- final boolean targetHit = activeTarget != -1;
-
- if (targetHit) {
- if (DEBUG) Log.v(TAG, "Finish with target hit = " + targetHit);
-
- highlightSelected(activeTarget);
-
- // Inform listener of any active targets. Typically only one will be active.
- hideGlow(RETURN_TO_HOME_DURATION, RETURN_TO_HOME_DELAY, 0.0f, mResetListener);
- dispatchTriggerEvent(activeTarget);
- if (!mAlwaysTrackFinger) {
- // Force ring and targets to finish animation to final expanded state
- mTargetAnimations.stop();
- }
- } else {
- // Animate handle back to the center based on current state.
- hideGlow(HIDE_ANIMATION_DURATION, 0, 0.0f, mResetListenerWithPing);
- hideTargets(true, false);
- }
-
- setGrabbedState(OnTriggerListener.NO_HANDLE);
- }
-
- private void highlightSelected(int activeTarget) {
- // Highlight the given target and fade others
- mTargetDrawables.get(activeTarget).setState(TargetDrawable.STATE_ACTIVE);
- hideUnselected(activeTarget);
- }
-
- private void hideUnselected(int active) {
- for (int i = 0; i < mTargetDrawables.size(); i++) {
- if (i != active) {
- mTargetDrawables.get(i).setAlpha(0.0f);
- }
- }
- }
-
- private void hideTargets(boolean animate, boolean expanded) {
- mTargetAnimations.cancel();
- // Note: these animations should complete at the same time so that we can swap out
- // the target assets asynchronously from the setTargetResources() call.
- mAnimatingTargets = animate;
- final int duration = animate ? HIDE_ANIMATION_DURATION : 0;
- final int delay = animate ? HIDE_ANIMATION_DELAY : 0;
-
- final float targetScale = expanded ?
- TARGET_SCALE_EXPANDED : TARGET_SCALE_COLLAPSED;
- final int length = mTargetDrawables.size();
- final TimeInterpolator interpolator = Ease.Cubic.easeOut;
- for (int i = 0; i < length; i++) {
- TargetDrawable target = mTargetDrawables.get(i);
- target.setState(TargetDrawable.STATE_INACTIVE);
- mTargetAnimations.add(Tweener.to(target, duration,
- "ease", interpolator,
- "alpha", 0.0f,
- "scaleX", targetScale,
- "scaleY", targetScale,
- "delay", delay,
- "onUpdate", mUpdateListener));
- }
-
- float ringScaleTarget = expanded ?
- RING_SCALE_EXPANDED : RING_SCALE_COLLAPSED;
- ringScaleTarget *= mRingScaleFactor;
- mTargetAnimations.add(Tweener.to(mOuterRing, duration,
- "ease", interpolator,
- "alpha", 0.0f,
- "scaleX", ringScaleTarget,
- "scaleY", ringScaleTarget,
- "delay", delay,
- "onUpdate", mUpdateListener,
- "onComplete", mTargetUpdateListener));
-
- mTargetAnimations.start();
- }
-
- private void showTargets(boolean animate) {
- mTargetAnimations.stop();
- mAnimatingTargets = animate;
- final int delay = animate ? SHOW_ANIMATION_DELAY : 0;
- final int duration = animate ? SHOW_ANIMATION_DURATION : 0;
- final int length = mTargetDrawables.size();
- for (int i = 0; i < length; i++) {
- TargetDrawable target = mTargetDrawables.get(i);
- target.setState(TargetDrawable.STATE_INACTIVE);
- mTargetAnimations.add(Tweener.to(target, duration,
- "ease", Ease.Cubic.easeOut,
- "alpha", 1.0f,
- "scaleX", 1.0f,
- "scaleY", 1.0f,
- "delay", delay,
- "onUpdate", mUpdateListener));
- }
- float ringScale = mRingScaleFactor * RING_SCALE_EXPANDED;
- mTargetAnimations.add(Tweener.to(mOuterRing, duration,
- "ease", Ease.Cubic.easeOut,
- "alpha", 1.0f,
- "scaleX", ringScale,
- "scaleY", ringScale,
- "delay", delay,
- "onUpdate", mUpdateListener,
- "onComplete", mTargetUpdateListener));
-
- mTargetAnimations.start();
- }
-
- private void vibrate() {
- if (mVibrator != null) {
- mVibrator.vibrate(mVibrationDuration);
- }
- }
-
- private ArrayList loadDrawableArray(int resourceId) {
- Resources res = getContext().getResources();
- TypedArray array = res.obtainTypedArray(resourceId);
- final int count = array.length();
- ArrayList drawables = new ArrayList(count);
- for (int i = 0; i < count; i++) {
- TypedValue value = array.peekValue(i);
- TargetDrawable target = new TargetDrawable(res, value != null ? value.resourceId : 0, 3);
- drawables.add(target);
- }
- array.recycle();
- return drawables;
- }
-
- private void internalSetTargetResources(int resourceId) {
- final ArrayList targets = loadDrawableArray(resourceId);
- mTargetDrawables = targets;
- mTargetResourceId = resourceId;
-
- int maxWidth = mHandleDrawable.getWidth();
- int maxHeight = mHandleDrawable.getHeight();
- final int count = targets.size();
- for (int i = 0; i < count; i++) {
- TargetDrawable target = targets.get(i);
- maxWidth = Math.max(maxWidth, target.getWidth());
- maxHeight = Math.max(maxHeight, target.getHeight());
- }
- if (mMaxTargetWidth != maxWidth || mMaxTargetHeight != maxHeight) {
- mMaxTargetWidth = maxWidth;
- mMaxTargetHeight = maxHeight;
- requestLayout(); // required to resize layout and call updateTargetPositions()
- } else {
- updateTargetPositions(mWaveCenterX, mWaveCenterY);
- updatePointCloudPosition(mWaveCenterX, mWaveCenterY);
- }
- }
- /**
- * Loads an array of drawables from the given resourceId.
- *
- * @param resourceId
- */
- public void setTargetResources(int resourceId) {
- if (mAnimatingTargets) {
- // postpone this change until we return to the initial state
- mNewTargetResources = resourceId;
- } else {
- internalSetTargetResources(resourceId);
- }
- }
-
- public int getTargetResourceId() {
- return mTargetResourceId;
- }
-
- /**
- * Sets the handle drawable to the drawable specified by the resource ID.
- * @param resourceId
- */
- public void setHandleDrawable(int resourceId) {
- if (mHandleDrawable != null) {
- mHandleDrawable.setDrawable(getResources(), resourceId);
- } else {
- mHandleDrawable = new TargetDrawable(getResources(), resourceId, 1);
- }
- mHandleDrawable.setState(TargetDrawable.STATE_INACTIVE);
- }
-
- /**
- * Sets the resource id specifying the target descriptions for accessibility.
- *
- * @param resourceId The resource id.
- */
- public void setTargetDescriptionsResourceId(int resourceId) {
- mTargetDescriptionsResourceId = resourceId;
- if (mTargetDescriptions != null) {
- mTargetDescriptions.clear();
- }
- }
-
- /**
- * Gets the resource id specifying the target descriptions for accessibility.
- *
- * @return The resource id.
- */
- public int getTargetDescriptionsResourceId() {
- return mTargetDescriptionsResourceId;
- }
-
- /**
- * Sets the resource id specifying the target direction descriptions for accessibility.
- *
- * @param resourceId The resource id.
- */
- public void setDirectionDescriptionsResourceId(int resourceId) {
- mDirectionDescriptionsResourceId = resourceId;
- if (mDirectionDescriptions != null) {
- mDirectionDescriptions.clear();
- }
- }
-
- /**
- * Gets the resource id specifying the target direction descriptions.
- *
- * @return The resource id.
- */
- public int getDirectionDescriptionsResourceId() {
- return mDirectionDescriptionsResourceId;
- }
-
- /**
- * Enable or disable vibrate on touch.
- *
- * @param enabled
- */
- public void setVibrateEnabled(boolean enabled) {
- if (enabled && mVibrator == null) {
- mVibrator = (Vibrator) getContext().getSystemService(Context.VIBRATOR_SERVICE);
- } else {
- mVibrator = null;
- }
- }
-
- /**
- * Starts wave animation.
- *
- */
- public void ping() {
- if (mFeedbackCount > 0) {
- boolean doWaveAnimation = true;
- final AnimationBundle waveAnimations = mWaveAnimations;
-
- // Don't do a wave if there's already one in progress
- if (waveAnimations.size() > 0 && waveAnimations.get(0).animator.isRunning()) {
- long t = waveAnimations.get(0).animator.getCurrentPlayTime();
- if (t < WAVE_ANIMATION_DURATION/2) {
- doWaveAnimation = false;
- }
- }
-
- if (doWaveAnimation) {
- startWaveAnimation();
- }
- }
- }
-
- private void stopAndHideWaveAnimation() {
- mWaveAnimations.cancel();
- mPointCloud.waveManager.setAlpha(0.0f);
- }
-
- private void startWaveAnimation() {
- mWaveAnimations.cancel();
- mPointCloud.waveManager.setAlpha(1.0f);
- mPointCloud.waveManager.setRadius(mHandleDrawable.getWidth()/2.0f);
- mWaveAnimations.add(Tweener.to(mPointCloud.waveManager, WAVE_ANIMATION_DURATION,
- "ease", Ease.Quad.easeOut,
- "delay", 0,
- "radius", 2.0f * mOuterRadius,
- "onUpdate", mUpdateListener,
- "onComplete",
- new AnimatorListenerAdapter() {
- public void onAnimationEnd(Animator animator) {
- mPointCloud.waveManager.setRadius(0.0f);
- mPointCloud.waveManager.setAlpha(0.0f);
- }
- }));
- mWaveAnimations.start();
- }
-
- /**
- * Resets the widget to default state and cancels all animation. If animate is 'true', will
- * animate objects into place. Otherwise, objects will snap back to place.
- *
- * @param animate
- */
- public void reset(boolean animate) {
- mGlowAnimations.stop();
- mTargetAnimations.stop();
- startBackgroundAnimation(0, 0.0f);
- stopAndHideWaveAnimation();
- hideTargets(animate, false);
- hideGlow(0, 0, 0.0f, null);
- Tweener.reset();
- }
-
- private void startBackgroundAnimation(int duration, float alpha) {
- final Drawable background = getBackground();
- if (mAlwaysTrackFinger && background != null) {
- if (mBackgroundAnimator != null) {
- mBackgroundAnimator.animator.cancel();
- }
- mBackgroundAnimator = Tweener.to(background, duration,
- "ease", Ease.Cubic.easeIn,
- "alpha", (int)(255.0f * alpha),
- "delay", SHOW_ANIMATION_DELAY);
- mBackgroundAnimator.animator.start();
- }
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- final int action = event.getActionMasked();
- boolean handled = false;
- switch (action) {
- case MotionEvent.ACTION_POINTER_DOWN:
- case MotionEvent.ACTION_DOWN:
- if (DEBUG) Log.v(TAG, "*** DOWN ***");
- handleDown(event);
- handleMove(event);
- handled = true;
- break;
-
- case MotionEvent.ACTION_MOVE:
- if (DEBUG) Log.v(TAG, "*** MOVE ***");
- handleMove(event);
- handled = true;
- break;
-
- case MotionEvent.ACTION_POINTER_UP:
- case MotionEvent.ACTION_UP:
- if (DEBUG) Log.v(TAG, "*** UP ***");
- handleMove(event);
- handleUp(event);
- handled = true;
- break;
-
- case MotionEvent.ACTION_CANCEL:
- if (DEBUG) Log.v(TAG, "*** CANCEL ***");
- handleMove(event);
- handleCancel(event);
- handled = true;
- break;
- }
- invalidate();
- return handled ? true : super.onTouchEvent(event);
- }
-
- private void updateGlowPosition(float x, float y) {
- float dx = x - mOuterRing.getX();
- float dy = y - mOuterRing.getY();
- dx *= 1f / mRingScaleFactor;
- dy *= 1f / mRingScaleFactor;
- mPointCloud.glowManager.setX(mOuterRing.getX() + dx);
- mPointCloud.glowManager.setY(mOuterRing.getY() + dy);
- }
-
- private void handleDown(MotionEvent event) {
- int actionIndex = event.getActionIndex();
- float eventX = event.getX(actionIndex);
- float eventY = event.getY(actionIndex);
- switchToState(STATE_START, eventX, eventY);
- if (!trySwitchToFirstTouchState(eventX, eventY)) {
- mDragging = false;
- } else {
- mPointerId = event.getPointerId(actionIndex);
- updateGlowPosition(eventX, eventY);
- }
- }
-
- private void handleUp(MotionEvent event) {
- if (DEBUG && mDragging) Log.v(TAG, "** Handle RELEASE");
- int actionIndex = event.getActionIndex();
- if (event.getPointerId(actionIndex) == mPointerId) {
- switchToState(STATE_FINISH, event.getX(actionIndex), event.getY(actionIndex));
- }
- }
-
- private void handleCancel(MotionEvent event) {
- if (DEBUG && mDragging) Log.v(TAG, "** Handle CANCEL");
-
- // We should drop the active target here but it interferes with
- // moving off the screen in the direction of the navigation bar. At some point we may
- // want to revisit how we handle this. For now we'll allow a canceled event to
- // activate the current target.
-
- // mActiveTarget = -1; // Drop the active target if canceled.
-
- int actionIndex = event.findPointerIndex(mPointerId);
- actionIndex = actionIndex == -1 ? 0 : actionIndex;
- switchToState(STATE_FINISH, event.getX(actionIndex), event.getY(actionIndex));
- }
-
- private void handleMove(MotionEvent event) {
- int activeTarget = -1;
- final int historySize = event.getHistorySize();
- ArrayList targets = mTargetDrawables;
- int ntargets = targets.size();
- float x = 0.0f;
- float y = 0.0f;
- int actionIndex = event.findPointerIndex(mPointerId);
-
- if (actionIndex == -1) {
- return; // no data for this pointer
- }
-
- for (int k = 0; k < historySize + 1; k++) {
- float eventX = k < historySize ? event.getHistoricalX(actionIndex, k)
- : event.getX(actionIndex);
- float eventY = k < historySize ? event.getHistoricalY(actionIndex, k)
- :event.getY(actionIndex);
- // tx and ty are relative to wave center
- float tx = eventX - mWaveCenterX;
- float ty = eventY - mWaveCenterY;
- float touchRadius = (float) Math.hypot(tx, ty);
- final float scale = touchRadius > mOuterRadius ? mOuterRadius / touchRadius : 1.0f;
- float limitX = tx * scale;
- float limitY = ty * scale;
- double angleRad = Math.atan2(-ty, tx);
-
- if (!mDragging) {
- trySwitchToFirstTouchState(eventX, eventY);
- }
-
- if (mDragging) {
- // For multiple targets, snap to the one that matches
- final float snapRadius = mRingScaleFactor * mOuterRadius - mSnapMargin;
- final float snapDistance2 = snapRadius * snapRadius;
- // Find first target in range
- for (int i = 0; i < ntargets; i++) {
- TargetDrawable target = targets.get(i);
-
- double targetMinRad = (i - 0.5) * 2 * Math.PI / ntargets;
- double targetMaxRad = (i + 0.5) * 2 * Math.PI / ntargets;
- if (target.isEnabled()) {
- boolean angleMatches =
- (angleRad > targetMinRad && angleRad <= targetMaxRad) ||
- (angleRad + 2 * Math.PI > targetMinRad &&
- angleRad + 2 * Math.PI <= targetMaxRad);
- if (angleMatches && (dist2(tx, ty) > snapDistance2)) {
- activeTarget = i;
- }
- }
- }
- }
- x = limitX;
- y = limitY;
- }
-
- if (!mDragging) {
- return;
- }
-
- if (activeTarget != -1) {
- switchToState(STATE_SNAP, x,y);
- updateGlowPosition(x, y);
- } else {
- switchToState(STATE_TRACKING, x, y);
- updateGlowPosition(x, y);
- }
-
- if (mActiveTarget != activeTarget) {
- // Defocus the old target
- if (mActiveTarget != -1) {
- TargetDrawable target = targets.get(mActiveTarget);
- target.setState(TargetDrawable.STATE_INACTIVE);
- }
- // Focus the new target
- if (activeTarget != -1) {
- TargetDrawable target = targets.get(activeTarget);
- target.setState(TargetDrawable.STATE_FOCUSED);
- final AccessibilityManager accessibilityManager =
- (AccessibilityManager) getContext().getSystemService(
- Context.ACCESSIBILITY_SERVICE);
- if (accessibilityManager.isEnabled()) {
- String targetContentDescription = getTargetDescription(activeTarget);
- announceForAccessibility(targetContentDescription);
- }
- }
- }
- mActiveTarget = activeTarget;
- }
-
- @Override
- public boolean onHoverEvent(MotionEvent event) {
- final AccessibilityManager accessibilityManager =
- (AccessibilityManager) getContext().getSystemService(
- Context.ACCESSIBILITY_SERVICE);
- if (accessibilityManager.isTouchExplorationEnabled()) {
- final int action = event.getAction();
- switch (action) {
- case MotionEvent.ACTION_HOVER_ENTER:
- event.setAction(MotionEvent.ACTION_DOWN);
- break;
- case MotionEvent.ACTION_HOVER_MOVE:
- event.setAction(MotionEvent.ACTION_MOVE);
- break;
- case MotionEvent.ACTION_HOVER_EXIT:
- event.setAction(MotionEvent.ACTION_UP);
- break;
- }
- onTouchEvent(event);
- event.setAction(action);
- }
- super.onHoverEvent(event);
- return true;
- }
-
- /**
- * Sets the current grabbed state, and dispatches a grabbed state change
- * event to our listener.
- */
- private void setGrabbedState(int newState) {
- if (newState != mGrabbedState) {
- if (newState != OnTriggerListener.NO_HANDLE) {
- vibrate();
- }
- mGrabbedState = newState;
- if (mOnTriggerListener != null) {
- if (newState == OnTriggerListener.NO_HANDLE) {
- mOnTriggerListener.onReleased(this, OnTriggerListener.CENTER_HANDLE);
- } else {
- mOnTriggerListener.onGrabbed(this, OnTriggerListener.CENTER_HANDLE);
- }
- mOnTriggerListener.onGrabbedStateChange(this, newState);
- }
- }
- }
-
- private boolean trySwitchToFirstTouchState(float x, float y) {
- final float tx = x - mWaveCenterX;
- final float ty = y - mWaveCenterY;
- if (mAlwaysTrackFinger || dist2(tx,ty) <= getScaledGlowRadiusSquared()) {
- if (DEBUG) Log.v(TAG, "** Handle HIT");
- switchToState(STATE_FIRST_TOUCH, x, y);
- updateGlowPosition(tx, ty);
- mDragging = true;
- return true;
- }
- return false;
- }
-
- private void assignDefaultsIfNeeded() {
- if (mOuterRadius == 0.0f) {
- mOuterRadius = Math.max(mOuterRing.getWidth(), mOuterRing.getHeight())/2.0f;
- }
- if (mSnapMargin == 0.0f) {
- mSnapMargin = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
- SNAP_MARGIN_DEFAULT, getContext().getResources().getDisplayMetrics());
- }
- if (mInnerRadius == 0.0f) {
- mInnerRadius = mHandleDrawable.getWidth() / 10.0f;
- }
- }
-
- private void computeInsets(int dx, int dy) {
- final int layoutDirection = getLayoutDirection();
- final int absoluteGravity = Gravity.getAbsoluteGravity(mGravity, layoutDirection);
-
- switch (absoluteGravity & Gravity.HORIZONTAL_GRAVITY_MASK) {
- case Gravity.LEFT:
- mHorizontalInset = 0;
- break;
- case Gravity.RIGHT:
- mHorizontalInset = dx;
- break;
- case Gravity.CENTER_HORIZONTAL:
- default:
- mHorizontalInset = dx / 2;
- break;
- }
- switch (absoluteGravity & Gravity.VERTICAL_GRAVITY_MASK) {
- case Gravity.TOP:
- mVerticalInset = 0;
- break;
- case Gravity.BOTTOM:
- mVerticalInset = dy;
- break;
- case Gravity.CENTER_VERTICAL:
- default:
- mVerticalInset = dy / 2;
- break;
- }
- }
-
- /**
- * Given the desired width and height of the ring and the allocated width and height, compute
- * how much we need to scale the ring.
- */
- private float computeScaleFactor(int desiredWidth, int desiredHeight,
- int actualWidth, int actualHeight) {
-
- // Return unity if scaling is not allowed.
- if (!mAllowScaling) return 1f;
-
- final int layoutDirection = getLayoutDirection();
- final int absoluteGravity = Gravity.getAbsoluteGravity(mGravity, layoutDirection);
-
- float scaleX = 1f;
- float scaleY = 1f;
-
- // We use the gravity as a cue for whether we want to scale on a particular axis.
- // We only scale to fit horizontally if we're not pinned to the left or right. Likewise,
- // we only scale to fit vertically if we're not pinned to the top or bottom. In these
- // cases, we want the ring to hang off the side or top/bottom, respectively.
- switch (absoluteGravity & Gravity.HORIZONTAL_GRAVITY_MASK) {
- case Gravity.LEFT:
- case Gravity.RIGHT:
- break;
- case Gravity.CENTER_HORIZONTAL:
- default:
- if (desiredWidth > actualWidth) {
- scaleX = (1f * actualWidth - mMaxTargetWidth) /
- (desiredWidth - mMaxTargetWidth);
- }
- break;
- }
- switch (absoluteGravity & Gravity.VERTICAL_GRAVITY_MASK) {
- case Gravity.TOP:
- case Gravity.BOTTOM:
- break;
- case Gravity.CENTER_VERTICAL:
- default:
- if (desiredHeight > actualHeight) {
- scaleY = (1f * actualHeight - mMaxTargetHeight) /
- (desiredHeight - mMaxTargetHeight);
- }
- break;
- }
- return Math.min(scaleX, scaleY);
- }
-
- private float getRingWidth() {
- return mRingScaleFactor * Math.max(mOuterRing.getWidth(), 2 * mOuterRadius);
- }
-
- private float getRingHeight() {
- return mRingScaleFactor * Math.max(mOuterRing.getHeight(), 2 * mOuterRadius);
- }
-
- @Override
- protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
- super.onLayout(changed, left, top, right, bottom);
- final int width = right - left;
- final int height = bottom - top;
-
- // Target placement width/height. This puts the targets on the greater of the ring
- // width or the specified outer radius.
- final float placementWidth = getRingWidth();
- final float placementHeight = getRingHeight();
- float newWaveCenterX = mHorizontalInset
- + (mMaxTargetWidth + placementWidth) / 2;
- float newWaveCenterY = mVerticalInset
- + (mMaxTargetHeight + placementHeight) / 2;
-
- if (mInitialLayout) {
- stopAndHideWaveAnimation();
- hideTargets(false, false);
- mInitialLayout = false;
- }
-
- mOuterRing.setPositionX(newWaveCenterX);
- mOuterRing.setPositionY(newWaveCenterY);
-
- mPointCloud.setScale(mRingScaleFactor);
-
- mHandleDrawable.setPositionX(newWaveCenterX);
- mHandleDrawable.setPositionY(newWaveCenterY);
-
- updateTargetPositions(newWaveCenterX, newWaveCenterY);
- updatePointCloudPosition(newWaveCenterX, newWaveCenterY);
- updateGlowPosition(newWaveCenterX, newWaveCenterY);
-
- mWaveCenterX = newWaveCenterX;
- mWaveCenterY = newWaveCenterY;
-
- if (DEBUG) dump();
- }
-
- private void updateTargetPositions(float centerX, float centerY) {
- // Reposition the target drawables if the view changed.
- ArrayList targets = mTargetDrawables;
- final int size = targets.size();
- final float alpha = (float) (-2.0f * Math.PI / size);
- for (int i = 0; i < size; i++) {
- final TargetDrawable targetIcon = targets.get(i);
- final float angle = alpha * i;
- targetIcon.setPositionX(centerX);
- targetIcon.setPositionY(centerY);
- targetIcon.setX(getRingWidth() / 2 * (float) Math.cos(angle));
- targetIcon.setY(getRingHeight() / 2 * (float) Math.sin(angle));
- }
- }
-
- private void updatePointCloudPosition(float centerX, float centerY) {
- mPointCloud.setCenter(centerX, centerY);
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- mPointCloud.draw(canvas);
- mOuterRing.draw(canvas);
- final int ntargets = mTargetDrawables.size();
- for (int i = 0; i < ntargets; i++) {
- TargetDrawable target = mTargetDrawables.get(i);
- if (target != null) {
- target.draw(canvas);
- }
- }
- mHandleDrawable.draw(canvas);
- }
-
- public void setOnTriggerListener(OnTriggerListener listener) {
- mOnTriggerListener = listener;
- }
-
- private float square(float d) {
- return d * d;
- }
-
- private float dist2(float dx, float dy) {
- return dx*dx + dy*dy;
- }
-
- private float getScaledGlowRadiusSquared() {
- final float scaledTapRadius;
- final AccessibilityManager accessibilityManager =
- (AccessibilityManager) getContext().getSystemService(
- Context.ACCESSIBILITY_SERVICE);
- if (accessibilityManager.isEnabled()) {
- scaledTapRadius = TAP_RADIUS_SCALE_ACCESSIBILITY_ENABLED * mGlowRadius;
- } else {
- scaledTapRadius = mGlowRadius;
- }
- return square(scaledTapRadius);
- }
-
- private void announceTargets() {
- StringBuilder utterance = new StringBuilder();
- final int targetCount = mTargetDrawables.size();
- for (int i = 0; i < targetCount; i++) {
- String targetDescription = getTargetDescription(i);
- String directionDescription = getDirectionDescription(i);
- if (!TextUtils.isEmpty(targetDescription)
- && !TextUtils.isEmpty(directionDescription)) {
- String text = String.format(directionDescription, targetDescription);
- utterance.append(text);
- }
- }
- if (utterance.length() > 0) {
- announceForAccessibility(utterance.toString());
- }
- }
-
- private String getTargetDescription(int index) {
- if (mTargetDescriptions == null || mTargetDescriptions.isEmpty()) {
- mTargetDescriptions = loadDescriptions(mTargetDescriptionsResourceId);
- if (mTargetDrawables.size() != mTargetDescriptions.size()) {
- Log.w(TAG, "The number of target drawables must be"
- + " equal to the number of target descriptions.");
- return null;
- }
- }
- return mTargetDescriptions.get(index);
- }
-
- private String getDirectionDescription(int index) {
- if (mDirectionDescriptions == null || mDirectionDescriptions.isEmpty()) {
- mDirectionDescriptions = loadDescriptions(mDirectionDescriptionsResourceId);
- if (mTargetDrawables.size() != mDirectionDescriptions.size()) {
- Log.w(TAG, "The number of target drawables must be"
- + " equal to the number of direction descriptions.");
- return null;
- }
- }
- return mDirectionDescriptions.get(index);
- }
-
- private ArrayList loadDescriptions(int resourceId) {
- TypedArray array = getContext().getResources().obtainTypedArray(resourceId);
- final int count = array.length();
- ArrayList targetContentDescriptions = new ArrayList(count);
- for (int i = 0; i < count; i++) {
- String contentDescription = array.getString(i);
- targetContentDescriptions.add(contentDescription);
- }
- array.recycle();
- return targetContentDescriptions;
- }
-
- public int getResourceIdForTarget(int index) {
- final TargetDrawable drawable = mTargetDrawables.get(index);
- return drawable == null ? 0 : drawable.getResourceId();
- }
-
- public void setEnableTarget(int resourceId, boolean enabled) {
- for (int i = 0; i < mTargetDrawables.size(); i++) {
- final TargetDrawable target = mTargetDrawables.get(i);
- if (target.getResourceId() == resourceId) {
- target.setEnabled(enabled);
- break; // should never be more than one match
- }
- }
- }
-
- /**
- * Gets the position of a target in the array that matches the given resource.
- * @param resourceId
- * @return the index or -1 if not found
- */
- public int getTargetPosition(int resourceId) {
- for (int i = 0; i < mTargetDrawables.size(); i++) {
- final TargetDrawable target = mTargetDrawables.get(i);
- if (target.getResourceId() == resourceId) {
- return i; // should never be more than one match
- }
- }
- return -1;
- }
-
- private boolean replaceTargetDrawables(Resources res, int existingResourceId,
- int newResourceId) {
- if (existingResourceId == 0 || newResourceId == 0) {
- return false;
- }
-
- boolean result = false;
- final ArrayList drawables = mTargetDrawables;
- final int size = drawables.size();
- for (int i = 0; i < size; i++) {
- final TargetDrawable target = drawables.get(i);
- if (target != null && target.getResourceId() == existingResourceId) {
- target.setDrawable(res, newResourceId);
- result = true;
- }
- }
-
- if (result) {
- requestLayout(); // in case any given drawable's size changes
- }
-
- return result;
- }
-
- /**
- * Searches the given package for a resource to use to replace the Drawable on the
- * target with the given resource id
- * @param component of the .apk that contains the resource
- * @param name of the metadata in the .apk
- * @param existingResId the resource id of the target to search for
- * @return true if found in the given package and replaced at least one target Drawables
- */
- public boolean replaceTargetDrawablesIfPresent(ComponentName component, String name,
- int existingResId) {
- if (existingResId == 0) return false;
-
- boolean replaced = false;
- if (component != null) {
- try {
- PackageManager packageManager = getContext().getPackageManager();
- // Look for the search icon specified in the activity meta-data
- Bundle metaData = packageManager.getActivityInfo(
- component, PackageManager.GET_META_DATA).metaData;
- if (metaData != null) {
- int iconResId = metaData.getInt(name);
- if (iconResId != 0) {
- Resources res = packageManager.getResourcesForActivity(component);
- replaced = replaceTargetDrawables(res, existingResId, iconResId);
- }
- }
- } catch (NameNotFoundException e) {
- Log.w(TAG, "Failed to swap drawable; "
- + component.flattenToShortString() + " not found", e);
- } catch (Resources.NotFoundException nfe) {
- Log.w(TAG, "Failed to swap drawable from "
- + component.flattenToShortString(), nfe);
- }
- }
- if (!replaced) {
- // Restore the original drawable
- replaceTargetDrawables(getContext().getResources(), existingResId, existingResId);
- }
- return replaced;
- }
-
- public class GlowpadExploreByTouchHelper extends ExploreByTouchHelper {
-
- private Rect mBounds = new Rect();
-
- public GlowpadExploreByTouchHelper(View forView) {
- super(forView);
- }
-
- @Override
- protected int getVirtualViewAt(float x, float y) {
- if (mGrabbedState == OnTriggerListener.CENTER_HANDLE) {
- for (int i = 0; i < mTargetDrawables.size(); i++) {
- final TargetDrawable target = mTargetDrawables.get(i);
- if (target.isEnabled() && target.getBounds().contains((int) x, (int) y)) {
- return i;
- }
- }
- return INVALID_ID;
- } else {
- return HOST_ID;
- }
- }
-
- @Override
- protected void getVisibleVirtualViews(List virtualViewIds) {
- if (mGrabbedState == OnTriggerListener.CENTER_HANDLE) {
- // Add virtual views backwards so that accessibility services like switch
- // access traverse them in the correct order
- for (int i = mTargetDrawables.size() - 1; i >= 0; i--) {
- if (mTargetDrawables.get(i).isEnabled()) {
- virtualViewIds.add(i);
- }
- }
- }
- }
-
- @Override
- protected void onPopulateEventForVirtualView(int virtualViewId, AccessibilityEvent event) {
- if (virtualViewId >= 0 && virtualViewId < mTargetDescriptions.size()) {
- event.setContentDescription(mTargetDescriptions.get(virtualViewId));
- }
- }
-
- @Override
- public void onInitializeAccessibilityEvent(View host, AccessibilityEvent event) {
- if (host == GlowPadView.this && event.getEventType()
- == AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED) {
- event.setContentChangeTypes(AccessibilityEvent.CONTENT_CHANGE_TYPE_SUBTREE);
- }
- super.onInitializeAccessibilityEvent(host, event);
- }
-
- @Override
- public void onPopulateNodeForHost(AccessibilityNodeInfoCompat node) {
- if (mGrabbedState == OnTriggerListener.NO_HANDLE) {
- node.setClickable(true);
- node.addAction(AccessibilityNodeInfoCompat.ACTION_CLICK);
- }
- mBounds.set(0, 0, GlowPadView.this.getWidth(), GlowPadView.this.getHeight());
- node.setBoundsInParent(mBounds);
- }
-
- @Override
- public boolean performAccessibilityAction(View host, int action, Bundle args) {
- if (mGrabbedState == OnTriggerListener.NO_HANDLE) {
- // Simulate handle being grabbed to expose targets.
- trySwitchToFirstTouchState(mWaveCenterX, mWaveCenterY);
- invalidateRoot();
- return true;
- }
- return super.performAccessibilityAction(host, action, args);
- }
-
- @Override
- protected void onPopulateNodeForVirtualView(int virtualViewId,
- AccessibilityNodeInfoCompat node) {
- if (virtualViewId < mTargetDrawables.size()) {
- final TargetDrawable target = mTargetDrawables.get(virtualViewId);
- node.setBoundsInParent(target.getBounds());
- node.setClickable(true);
- node.addAction(AccessibilityNodeInfoCompat.ACTION_CLICK);
- node.setContentDescription(getTargetDescription(virtualViewId));
- }
- }
-
- @Override
- protected boolean onPerformActionForVirtualView(int virtualViewId, int action,
- Bundle arguments) {
- if (action == AccessibilityNodeInfo.ACTION_CLICK) {
- if (virtualViewId >= 0 && virtualViewId < mTargetDrawables.size()) {
- dispatchTriggerEvent(virtualViewId);
- return true;
- }
- }
- return false;
- }
-
- }
-}
diff --git a/InCallUI/src/com/android/incallui/widget/multiwaveview/PointCloud.java b/InCallUI/src/com/android/incallui/widget/multiwaveview/PointCloud.java
deleted file mode 100644
index 07a2cb964c489392a983d93bd7d7de1c4efe95ce..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/widget/multiwaveview/PointCloud.java
+++ /dev/null
@@ -1,235 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.widget.multiwaveview;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.drawable.Drawable;
-import android.util.Log;
-
-import java.util.ArrayList;
-
-public class PointCloud {
- private static final float MIN_POINT_SIZE = 2.0f;
- private static final float MAX_POINT_SIZE = 4.0f;
- private static final int INNER_POINTS = 8;
- private static final String TAG = "PointCloud";
- private ArrayList mPointCloud = new ArrayList();
- private Drawable mDrawable;
- private float mCenterX;
- private float mCenterY;
- private Paint mPaint;
- private float mScale = 1.0f;
- private static final float PI = (float) Math.PI;
-
- // These allow us to have multiple concurrent animations.
- WaveManager waveManager = new WaveManager();
- GlowManager glowManager = new GlowManager();
- private float mOuterRadius;
-
- public class WaveManager {
- private float radius = 50;
- private float width = 200.0f; // TODO: Make configurable
- private float alpha = 0.0f;
- public void setRadius(float r) {
- radius = r;
- }
-
- public float getRadius() {
- return radius;
- }
-
- public void setAlpha(float a) {
- alpha = a;
- }
-
- public float getAlpha() {
- return alpha;
- }
- };
-
- public class GlowManager {
- private float x;
- private float y;
- private float radius = 0.0f;
- private float alpha = 0.0f;
-
- public void setX(float x1) {
- x = x1;
- }
-
- public float getX() {
- return x;
- }
-
- public void setY(float y1) {
- y = y1;
- }
-
- public float getY() {
- return y;
- }
-
- public void setAlpha(float a) {
- alpha = a;
- }
-
- public float getAlpha() {
- return alpha;
- }
-
- public void setRadius(float r) {
- radius = r;
- }
-
- public float getRadius() {
- return radius;
- }
- }
-
- class Point {
- float x;
- float y;
- float radius;
-
- public Point(float x2, float y2, float r) {
- x = (float) x2;
- y = (float) y2;
- radius = r;
- }
- }
-
- public PointCloud(Drawable drawable) {
- mPaint = new Paint();
- mPaint.setFilterBitmap(true);
- mPaint.setColor(Color.rgb(255, 255, 255)); // TODO: make configurable
- mPaint.setAntiAlias(true);
- mPaint.setDither(true);
-
- mDrawable = drawable;
- if (mDrawable != null) {
- drawable.setBounds(0, 0, drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight());
- }
- }
-
- public void setCenter(float x, float y) {
- mCenterX = x;
- mCenterY = y;
- }
-
- public void makePointCloud(float innerRadius, float outerRadius) {
- if (innerRadius == 0) {
- Log.w(TAG, "Must specify an inner radius");
- return;
- }
- mOuterRadius = outerRadius;
- mPointCloud.clear();
- final float pointAreaRadius = (outerRadius - innerRadius);
- final float ds = (2.0f * PI * innerRadius / INNER_POINTS);
- final int bands = (int) Math.round(pointAreaRadius / ds);
- final float dr = pointAreaRadius / bands;
- float r = innerRadius;
- for (int b = 0; b <= bands; b++, r += dr) {
- float circumference = 2.0f * PI * r;
- final int pointsInBand = (int) (circumference / ds);
- float eta = PI/2.0f;
- float dEta = 2.0f * PI / pointsInBand;
- for (int i = 0; i < pointsInBand; i++) {
- float x = r * (float) Math.cos(eta);
- float y = r * (float) Math.sin(eta);
- eta += dEta;
- mPointCloud.add(new Point(x, y, r));
- }
- }
- }
-
- public void setScale(float scale) {
- mScale = scale;
- }
-
- public float getScale() {
- return mScale;
- }
-
- private static float hypot(float x, float y) {
- return (float) Math.hypot(x, y);
- }
-
- private static float max(float a, float b) {
- return a > b ? a : b;
- }
-
- public int getAlphaForPoint(Point point) {
- // Contribution from positional glow
- float glowDistance = hypot(glowManager.x - point.x, glowManager.y - point.y);
- float glowAlpha = 0.0f;
-
- if (glowDistance < glowManager.radius) {
- double cos = Math.cos(Math.PI * 0.25d * glowDistance / glowManager.radius);
- glowAlpha = glowManager.alpha * max(0.0f, (float) Math.pow(cos, 10.0d));
- }
-
- // Compute contribution from Wave
- float radius = hypot(point.x, point.y);
- float distanceToWaveRing = (radius - waveManager.radius);
- float waveAlpha = 0.0f;
- if (distanceToWaveRing < waveManager.width * 0.5f && distanceToWaveRing < 0.0f) {
- double cos = Math.cos(Math.PI * 0.25d * distanceToWaveRing / waveManager.width);
- waveAlpha = waveManager.alpha * max(0.0f, (float) Math.pow(cos, 20.0d));
- }
-
- return (int) (max(glowAlpha, waveAlpha) * 255);
- }
-
- private float interp(float min, float max, float f) {
- return min + (max - min) * f;
- }
-
- public void draw(Canvas canvas) {
- ArrayList points = mPointCloud;
- canvas.save(Canvas.MATRIX_SAVE_FLAG);
- canvas.scale(mScale, mScale, mCenterX, mCenterY);
- for (int i = 0; i < points.size(); i++) {
- Point point = points.get(i);
- final float pointSize = interp(MAX_POINT_SIZE, MIN_POINT_SIZE,
- point.radius / mOuterRadius);
- final float px = point.x + mCenterX;
- final float py = point.y + mCenterY;
- int alpha = getAlphaForPoint(point);
-
- if (alpha == 0) continue;
-
- if (mDrawable != null) {
- canvas.save(Canvas.MATRIX_SAVE_FLAG);
- final float cx = mDrawable.getIntrinsicWidth() * 0.5f;
- final float cy = mDrawable.getIntrinsicHeight() * 0.5f;
- final float s = pointSize / MAX_POINT_SIZE;
- canvas.scale(s, s, px, py);
- canvas.translate(px - cx, py - cy);
- mDrawable.setAlpha(alpha);
- mDrawable.draw(canvas);
- canvas.restore();
- } else {
- mPaint.setAlpha(alpha);
- canvas.drawCircle(px, py, pointSize, mPaint);
- }
- }
- canvas.restore();
- }
-
-}
diff --git a/InCallUI/src/com/android/incallui/widget/multiwaveview/TargetDrawable.java b/InCallUI/src/com/android/incallui/widget/multiwaveview/TargetDrawable.java
deleted file mode 100644
index adc5324ebaae2ea45dd3b73cdac211a1efefba79..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/widget/multiwaveview/TargetDrawable.java
+++ /dev/null
@@ -1,250 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.widget.multiwaveview;
-
-import android.content.res.Resources;
-import android.graphics.Canvas;
-import android.graphics.ColorFilter;
-import android.graphics.Rect;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.StateListDrawable;
-import android.util.Log;
-
-public class TargetDrawable {
- private static final String TAG = "TargetDrawable";
- private static final boolean DEBUG = false;
-
- public static final int[] STATE_ACTIVE =
- { android.R.attr.state_enabled, android.R.attr.state_active };
- public static final int[] STATE_INACTIVE =
- { android.R.attr.state_enabled, -android.R.attr.state_active };
- public static final int[] STATE_FOCUSED =
- { android.R.attr.state_enabled, -android.R.attr.state_active,
- android.R.attr.state_focused };
-
- private float mTranslationX = 0.0f;
- private float mTranslationY = 0.0f;
- private float mPositionX = 0.0f;
- private float mPositionY = 0.0f;
- private float mScaleX = 1.0f;
- private float mScaleY = 1.0f;
- private float mAlpha = 1.0f;
- private Drawable mDrawable;
- private boolean mEnabled = true;
- private final int mResourceId;
- private int mNumDrawables = 1;
- private Rect mBounds;
-
- /**
- * This is changed from the framework version to pass in the number of drawables in the
- * container. The framework version relies on private api's to get the count from
- * StateListDrawable.
- *
- * @param res
- * @param resId
- * @param count The number of drawables in the resource.
- */
- public TargetDrawable(Resources res, int resId, int count) {
- mResourceId = resId;
- setDrawable(res, resId);
- mNumDrawables = count;
- }
-
- public void setDrawable(Resources res, int resId) {
- // Note we explicitly don't set mResourceId to resId since we allow the drawable to be
- // swapped at runtime and want to re-use the existing resource id for identification.
- Drawable drawable = resId == 0 ? null : res.getDrawable(resId);
- // Mutate the drawable so we can animate shared drawable properties.
- mDrawable = drawable != null ? drawable.mutate() : null;
- resizeDrawables();
- setState(STATE_INACTIVE);
- }
-
- public TargetDrawable(TargetDrawable other) {
- mResourceId = other.mResourceId;
- // Mutate the drawable so we can animate shared drawable properties.
- mDrawable = other.mDrawable != null ? other.mDrawable.mutate() : null;
- resizeDrawables();
- setState(STATE_INACTIVE);
- }
-
- public void setState(int [] state) {
- if (mDrawable instanceof StateListDrawable) {
- StateListDrawable d = (StateListDrawable) mDrawable;
- d.setState(state);
- }
- }
-
- /**
- * Returns true if the drawable is a StateListDrawable and is in the focused state.
- *
- * @return
- */
- public boolean isActive() {
- if (mDrawable instanceof StateListDrawable) {
- StateListDrawable d = (StateListDrawable) mDrawable;
- int[] states = d.getState();
- for (int i = 0; i < states.length; i++) {
- if (states[i] == android.R.attr.state_focused) {
- return true;
- }
- }
- }
- return false;
- }
-
- /**
- * Returns true if this target is enabled. Typically an enabled target contains a valid
- * drawable in a valid state. Currently all targets with valid drawables are valid.
- *
- * @return
- */
- public boolean isEnabled() {
- return mDrawable != null && mEnabled;
- }
-
- /**
- * Makes drawables in a StateListDrawable all the same dimensions.
- * If not a StateListDrawable, then justs sets the bounds to the intrinsic size of the
- * drawable.
- */
- private void resizeDrawables() {
- if (mDrawable instanceof StateListDrawable) {
- StateListDrawable d = (StateListDrawable) mDrawable;
- int maxWidth = 0;
- int maxHeight = 0;
-
- for (int i = 0; i < mNumDrawables; i++) {
- d.selectDrawable(i);
- Drawable childDrawable = d.getCurrent();
- maxWidth = Math.max(maxWidth, childDrawable.getIntrinsicWidth());
- maxHeight = Math.max(maxHeight, childDrawable.getIntrinsicHeight());
- }
-
- if (DEBUG) Log.v(TAG, "union of childDrawable rects " + d + " to: "
- + maxWidth + "x" + maxHeight);
- d.setBounds(0, 0, maxWidth, maxHeight);
-
- for (int i = 0; i < mNumDrawables; i++) {
- d.selectDrawable(i);
- Drawable childDrawable = d.getCurrent();
- if (DEBUG) Log.v(TAG, "sizing drawable " + childDrawable + " to: "
- + maxWidth + "x" + maxHeight);
- childDrawable.setBounds(0, 0, maxWidth, maxHeight);
- }
- } else if (mDrawable != null) {
- mDrawable.setBounds(0, 0,
- mDrawable.getIntrinsicWidth(), mDrawable.getIntrinsicHeight());
- }
- }
-
- public void setX(float x) {
- mTranslationX = x;
- }
-
- public void setY(float y) {
- mTranslationY = y;
- }
-
- public void setScaleX(float x) {
- mScaleX = x;
- }
-
- public void setScaleY(float y) {
- mScaleY = y;
- }
-
- public void setAlpha(float alpha) {
- mAlpha = alpha;
- }
-
- public float getX() {
- return mTranslationX;
- }
-
- public float getY() {
- return mTranslationY;
- }
-
- public float getScaleX() {
- return mScaleX;
- }
-
- public float getScaleY() {
- return mScaleY;
- }
-
- public float getAlpha() {
- return mAlpha;
- }
-
- public void setPositionX(float x) {
- mPositionX = x;
- }
-
- public void setPositionY(float y) {
- mPositionY = y;
- }
-
- public float getPositionX() {
- return mPositionX;
- }
-
- public float getPositionY() {
- return mPositionY;
- }
-
- public int getWidth() {
- return mDrawable != null ? mDrawable.getIntrinsicWidth() : 0;
- }
-
- public int getHeight() {
- return mDrawable != null ? mDrawable.getIntrinsicHeight() : 0;
- }
-
- public Rect getBounds() {
- if (mBounds == null) {
- mBounds = new Rect();
- }
- mBounds.set((int) (mTranslationX + mPositionX - getWidth() * 0.5),
- (int) (mTranslationY + mPositionY - getHeight() * 0.5),
- (int) (mTranslationX + mPositionX + getWidth() * 0.5),
- (int) (mTranslationY + mPositionY + getHeight() * 0.5));
- return mBounds;
- }
-
- public void draw(Canvas canvas) {
- if (mDrawable == null || !mEnabled) {
- return;
- }
- canvas.save(Canvas.MATRIX_SAVE_FLAG);
- canvas.scale(mScaleX, mScaleY, mPositionX, mPositionY);
- canvas.translate(mTranslationX + mPositionX, mTranslationY + mPositionY);
- canvas.translate(-0.5f * getWidth(), -0.5f * getHeight());
- mDrawable.setAlpha((int) Math.round(mAlpha * 255f));
- mDrawable.draw(canvas);
- canvas.restore();
- }
-
- public void setEnabled(boolean enabled) {
- mEnabled = enabled;
- }
-
- public int getResourceId() {
- return mResourceId;
- }
-}
diff --git a/InCallUI/src/com/android/incallui/widget/multiwaveview/Tweener.java b/InCallUI/src/com/android/incallui/widget/multiwaveview/Tweener.java
deleted file mode 100644
index 7222442fed93a5d5839eabe9973c6fb5b851063f..0000000000000000000000000000000000000000
--- a/InCallUI/src/com/android/incallui/widget/multiwaveview/Tweener.java
+++ /dev/null
@@ -1,178 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.incallui.widget.multiwaveview;
-
-import android.animation.Animator;
-import android.animation.Animator.AnimatorListener;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.ObjectAnimator;
-import android.animation.PropertyValuesHolder;
-import android.animation.TimeInterpolator;
-import android.animation.ValueAnimator.AnimatorUpdateListener;
-import android.util.Log;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map.Entry;
-
-class Tweener {
- private static final String TAG = "Tweener";
- private static final boolean DEBUG = false;
-
- ObjectAnimator animator;
- private static HashMap