كتابة الطرق الأصلية

يدعم J2ObjC تضمين Object-C في أساليب Java الأصلية، بشكل مشابه جدًا لكيفية دعم JSNI من GWT لتضمين JavaScript. يكمن الفرق الرئيسي بين تضمين J2ObjC وGWT في أنّ J2ObjC يستخدم الترميزَين /*-[ و]-*/ لتوضيح كود Intent. يُطلق على هذه المنشأة اسم OCNI (الواجهة الأصلية للهدف) لتمييزها عن JSNI التابع لشركة GWT.

إليك مثال من إصدار مكتبة محاكاة JRE من java.lang.System:

  public static native long currentTimeMillis() /*-[
    // Use NSDate
    return (long long) ([[NSDate date] timeIntervalSince1970] * 1000);
  ]-*/;

ينسخ J2ObjC التعليق، ناقص المحددات، لإنشاء نص الطريقة:

  + (long long int)currentTimeMillis {
    // Use NSDate
    return (long long) ([[NSDate date] timeIntervalSince1970] * 1000);
  }

عمليات استيراد الإعلانات المدمجة مع المحتوى

يفحص J2ObjC رمز Java الذي تتم ترجمته لإضافة توجيهات #import لتبعياتها، بالإضافة إلى استيراد إطار عمل Foundation. ومع ذلك، يجب إضافة أي عمليات استيراد لا تحتاج إليها سوى الرموز البرمجية الأصلية بشكل منفصل. لإضافة عمليات استيراد، أضِف قسم OCNI أعلى الفئة الأولى في ملف مصدر Java وحدّد عمليات الاستيراد فيه، على سبيل المثال:

  package my.project;

  /*-[
  #import "java/lang/NullPointerException.h"
  ]-*/

  public class Test {
    native void test() /*-[
      @throw [[JavaLangNullPointerException alloc] init];
    ]-*/;
  }

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

وحدات سكنية أصلية

تبحث دالة J2ObjC عن كتل OCNI داخل نص الفئة. تتم إضافة هذه الكتل بدون تعديل إلى الملف المُترجَم، في الموضع نفسه بالنسبة إلى أعضاء الفئة المُترجَمين. وفي ما يلي مثال لذلك:

  /*-[
    static void log(NSString *msg) {
      NSLog(@"%@", msg);
    }
  ]-*/;

يمكن استدعاء الدالة C هذه من أي طرق أصلية تم تعريفها بعد حظر OCNI هذا.

أحد الخيارات الخاصة لمجموعة OCNI هذه يؤدي إلى إدراج رمز في العنوان الذي تم إنشاؤه بدلاً من ملف m.: /*-HEADER[...]

استدعاء طرق Java من Native Code

public native void bar(JSNIExample x, String s) /*-[
  // Call instance method instanceFoo() on this
  [self instanceFooWithNSString:s];

  // Call instance method instanceFoo() on x
  [x instanceFooWithNSString:s];

  // Call static method staticFoo()
  JSNIExample_staticFooWithNSString_(s);
]-*/;

الوصول إلى الحقول من Native Code

لقراءة حقل مثيل، استخدِم إما myInstanceField_ أو self->myInstanceField_. تتجنب اللاحقة اللاحقة التضارب مع الطرق التي تحمل نفس الاسم.

تجدر الإشارة إلى أنّ الحقول التي لها أسماء محجوزة ستحتوي على شرطتَين سفليتَين. على سبيل المثال، يعد الحقل المسمى "id" قانونيًا في Java، ولكن ليس في الهدف C. عند ترجمة هذا الحقل، ستتم تسمية هذا الحقل "id__". وبالتالي، يُرجى التحقق من الملفات التي تم إنشاؤها في حالة عدم وجود أخطاء في برنامج التجميع "بدون مثل هذه الحقول".

للكتابة إلى حقل مثيل كائن، استخدِم JSNIExample_set_myInstanceField(string).

قراءة حقل ثابت: JSNIExample_get_myStaticField()

كتابة حقل ثابت: JSNIExample_set_myStaticField(value)

J2ObjC وGWT

تم اختيار محدِّدات مختلفة بحيث يتم تجاهل تعليقات GWT JSNI في إصدار J2ObjC التالي (تم استخدام المحدِّدات نفسها سابقًا في GWT). وهذا يعني أن مصدر Java واحد يمكن أن يحتوي على طرق أصلية تتضمن عمليات تنفيذ Target-C وGWT وAndroid (عبر JNI):

  static native void log(String text) /*-{ // left-brace for JavaScript
    console.log(text);
  }-*/ /*-[                                // left-bracket for Objective-C
     NSLog(@"%@", text);
  ]-*/;

J2ObjC وAndroid

ينفّذ كل من J2ObjC وAndroid الطريقة الأصلية "تعمل فقط"، وذلك نظرًا لتنفيذ طرق Android الأصلية في ملف JNI C أو C++ منفصل. تتم إزالة أي تعليقات OCNI في فئات Java عند تجميعها بواسطة javac لنظام التشغيل Android أو أي نظام Java آخر.