هل هناك طريقة للوصول إلى إدخالات التقويم دون استخدام gdata-جافا العميل؟

StackOverflow https://stackoverflow.com/questions/846942

  •  21-08-2019
  •  | 
  •  

سؤال

هل من الممكن الحصول على إدخالات التقويم من دون اتصال الهاتف؟ ويبدو أن الطريقة الوحيدة هي استخدام gdata-جافا العميل .

هل كانت مفيدة؟

المحلول

وهذه الإجابات جيدة، ولكنها جميعا تنطوي بجد ترميز Calendar URI (والذي رأيته في ثلاثة التجسيد مختلفة عبر أجهزة الروبوت مختلفة).

وهناك طريقة أفضل للحصول على هذا URI (التي من الصعب رموز اسم فئة وحقل بدلا من ذلك) سيكون شيئا من هذا القبيل:

Class<?> calendarProviderClass = Class.forName("android.provider.Calendar");
Field uriField = calendarProviderClass.getField("CONTENT_URI");
Uri calendarUri = (Uri) uriField.get(null);

وهذه ليست مثالية (وسوف كسر إذا كانوا من أي وقت مضى إزالة الطبقة android.provider.Calendar أو مجال CONTENT_URI) ولكنه يعمل على المزيد من المنصات من أي URI بجد رمز واحد.

لاحظ أن هذه الأساليب انعكاس سوف يرمي exceptions التي سوف تحتاج إلى أن يقبض أو إعادة القيت من قبل طريقة الاستدعاء.

نصائح أخرى

وجوزيف والحلول اسحق للوصول إلى تقويم تعمل فقط في الروبوت 2.1 والإصدارات السابقة. تغيرت جوجل محتوى قاعدة URI في 2.2 من "المحتوى: // تقويم" إلى "المحتوى: //com.android.calendar". هذا التغيير يعني أفضل نهج هو محاولة للحصول على المؤشر باستخدام قاعدة URI القديم، وإذا كان المؤشر عاد لاغيا، ثم حاول قاعدة جديدة URI.

تجدر الإشارة إلى أن حصلت على هذا النهج من فتح رمز اختبار مصدر أن شين كوندر ولورين دارسي مع توفير العمل مع الروبوت التقويم المادة.

private final static String BASE_CALENDAR_URI_PRE_2_2 = "content://calendar";
private final static String BASE_CALENDAR_URI_2_2 = "content://com.android.calendar";
/*
 * Determines if we need to use a pre 2.2 calendar Uri, or a 2.2 calendar Uri, and returns the base Uri
 */
private String getCalendarUriBase() {
    Uri calendars = Uri.parse(BASE_CALENDAR_URI_PRE_2_2 + "/calendars");
    try {
        Cursor managedCursor = managedQuery(calendars, null, null, null, null);
        if (managedCursor != null) {
            return BASE_CALENDAR_URI_PRE_2_2;
        }
        else {
            calendars = Uri.parse(BASE_CALENDAR_URI_2_2 + "/calendars");
            managedCursor = managedQuery(calendars, null, null, null, null);

            if (managedCursor != null) {
                return BASE_CALENDAR_URI_2_2;
            }
        }
    } catch (Exception e) { /* eat any exceptions */ }

    return null; // No working calendar URI found
}

وحاليا، لم يكن ذلك ممكنا دون استخدام واجهات برمجة التطبيقات الخاصة (انظر آخر جوزيف.) هناك مزود التقويم، ولكنها ليست العام حتى الان. يمكن أن تتغير في أي وقت وكسر التطبيق الخاص بك.
رغم ذلك، فإنه على الأرجح لن تتغير (لا أعتقد أنها سوف تغييره من "تقويم")، لذلك قد يكون قادرا على استخدامها. لكن توصيتي هي استخدام فئة منفصلة مثل هذا:

public class CalendarProvider {
     public static final Uri CONTENT_URI = Uri.parse("content://calendar");
     public static final String TITLE = "title";
     public static final String ....

واستخدام تلك بدلا من السلاسل مباشرة. هذا وسوف تمكنك من تغييره بسهولة جدا إذا / عندما يتغير API أو اعلانه.

ويمكنك استخدام CalendarContract من هنا: https://github.com/dschuermann/android- تقويم التوافق

ومن نفس الفئة API كما تتوفر على الروبوت 4، ولكن يجبرون على العمل مع الروبوت> = 2.2.

وحول API التي يمكن أن تغير ... وسيكون نهج ContentProvider كله لا يغير ذلك بسرعة حتى يمكن التغلب بالفعل الكثير من المشاكل عن طريق تحديث فقط السلاسل. لذلك إنشاء الثوابت يمكنك استخدامها على كامل المشروع.

public static final String URI_CONTENT_CALENDAR_EVENTS = "content://calendar/events";

ContentResolver contentResolver = context.getContentResolver();
Cursor cursor = contentResolver.query(Uri.parse(URI_CONTENT_CALENDAR_EVENTS), null, null, null, null);
    //etc

إذا كنت ترغب في API الخاص السليم سيكون لديك لإنشاء POJO وبعض الخدمات مثل هذا:

public class CalendarEvent {
    private long id;
    private long date;
    //etc...
}

public interface CalendarService {

    public Set<CalendarEvent> getAllCalendarEvents();

    public CalendarEvent findCalendarEventById(long id);

    public CalendarEvent findCalendarEventByDate(long date);

}

ووهلم جرا. بهذه الطريقة سيكون لديك فقط لتحديث الكائن CalendarEvent وهذه الخدمة في حالة التغييرات API.

وحل نيك ينطوي managedQuery، والتي لم يتم تعريف في فئة السياق. وفي كثير من الأحيان عندما تقوم بتشغيل أشياء في الخلفية هل تريد أن استخدام كائن السياق. وفيما يلي نسخة معدلة:

وجمهور سلسلة getCalendarUriBase () {

وعودة (android.os.Build.VERSION.SDK_INT> = 8)؟ "المحتوى: //com.android.calendar": "المحتوى: // تقويم". }

لا ينبغي أن يتم الصيد لاغية هنا منذ قد يكون هناك المزيد من الاستثناءات حتى لو نجح managedQuery في وقت سابق.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top