@@ -57,7 +57,7 @@ public void Dispose()
57
57
58
58
if ( m_jobject != IntPtr . Zero )
59
59
{
60
- AndroidJNISafe . DeleteGlobalRef ( m_jobject ) ;
60
+ AndroidJNISafe . QueueDeleteGlobalRef ( m_jobject ) ;
61
61
}
62
62
}
63
63
@@ -797,7 +797,9 @@ protected void _Set<FieldType>(IntPtr fieldID, FieldType val)
797
797
AndroidJNISafe . SetCharField ( m_jobject , fieldID , ( Char ) ( object ) val ) ;
798
798
}
799
799
else if ( typeof ( FieldType ) == typeof ( String ) )
800
+ {
800
801
AndroidJNISafe . SetStringField ( m_jobject , fieldID , ( String ) ( object ) val ) ;
802
+ }
801
803
else if ( typeof ( FieldType ) == typeof ( AndroidJavaClass ) )
802
804
{
803
805
AndroidJNISafe . SetObjectField ( m_jobject , fieldID , val == null ? IntPtr . Zero : ( ( AndroidJavaClass ) ( object ) val ) . m_jclass ) ;
@@ -806,10 +808,14 @@ protected void _Set<FieldType>(IntPtr fieldID, FieldType val)
806
808
{
807
809
AndroidJNISafe . SetObjectField ( m_jobject , fieldID , val == null ? IntPtr . Zero : ( ( AndroidJavaObject ) ( object ) val ) . m_jobject ) ;
808
810
}
811
+ else if ( AndroidReflection . IsAssignableFrom ( typeof ( AndroidJavaProxy ) , typeof ( FieldType ) ) )
812
+ {
813
+ AndroidJNISafe . SetObjectField ( m_jobject , fieldID , val == null ? IntPtr . Zero : ( ( AndroidJavaProxy ) ( object ) val ) . GetRawProxy ( ) ) ;
814
+ }
809
815
else if ( AndroidReflection . IsAssignableFrom ( typeof ( System . Array ) , typeof ( FieldType ) ) )
810
816
{
811
817
IntPtr jobject = AndroidJNIHelper . ConvertToJNIArray ( ( Array ) ( object ) val ) ;
812
- AndroidJNISafe . SetObjectField ( m_jclass , fieldID , jobject ) ;
818
+ AndroidJNISafe . SetObjectField ( m_jobject , fieldID , jobject ) ;
813
819
}
814
820
else
815
821
{
@@ -1011,6 +1017,10 @@ protected void _SetStatic<FieldType>(IntPtr fieldID, FieldType val)
1011
1017
{
1012
1018
AndroidJNISafe . SetStaticObjectField ( m_jclass , fieldID , val == null ? IntPtr . Zero : ( ( AndroidJavaObject ) ( object ) val ) . m_jobject ) ;
1013
1019
}
1020
+ else if ( AndroidReflection . IsAssignableFrom ( typeof ( AndroidJavaProxy ) , typeof ( FieldType ) ) )
1021
+ {
1022
+ AndroidJNISafe . SetStaticObjectField ( m_jclass , fieldID , val == null ? IntPtr . Zero : ( ( AndroidJavaProxy ) ( object ) val ) . GetRawProxy ( ) ) ;
1023
+ }
1014
1024
else if ( AndroidReflection . IsAssignableFrom ( typeof ( System . Array ) , typeof ( FieldType ) ) )
1015
1025
{
1016
1026
IntPtr jobject = AndroidJNIHelper . ConvertToJNIArray ( ( Array ) ( object ) val ) ;
@@ -1551,16 +1561,46 @@ public static IntPtr ConvertToJNIArray(System.Array array)
1551
1561
{
1552
1562
jniObjs [ i ] = objArray [ i ] . GetRawObject ( ) ;
1553
1563
IntPtr objectType = objArray [ i ] . GetRawClass ( ) ;
1554
- if ( arrayType != objectType )
1564
+ if ( arrayType == IntPtr . Zero )
1555
1565
{
1556
- if ( arrayType == IntPtr . Zero )
1557
- {
1558
- arrayType = objectType ;
1559
- }
1560
- else
1561
- {
1562
- arrayType = fallBackType ; // java/lang/Object
1563
- }
1566
+ arrayType = objectType ;
1567
+ }
1568
+ else if ( arrayType != fallBackType && ! AndroidJNI . IsSameObject ( arrayType , objectType ) )
1569
+ {
1570
+ arrayType = fallBackType ; // java/lang/Object
1571
+ }
1572
+ }
1573
+ else
1574
+ {
1575
+ jniObjs [ i ] = IntPtr . Zero ;
1576
+ }
1577
+ }
1578
+ // zero sized array will call this with IntPtr.Zero type translated into java/lang/Object
1579
+ IntPtr res = AndroidJNISafe . ToObjectArray ( jniObjs , arrayType ) ;
1580
+ AndroidJNISafe . DeleteLocalRef ( fallBackType ) ;
1581
+ return res ;
1582
+ }
1583
+ else if ( AndroidReflection . IsAssignableFrom ( typeof ( AndroidJavaProxy ) , type ) )
1584
+ {
1585
+ AndroidJavaProxy [ ] objArray = ( AndroidJavaProxy [ ] ) array ;
1586
+ int arrayLen = array . GetLength ( 0 ) ;
1587
+ IntPtr [ ] jniObjs = new IntPtr [ arrayLen ] ;
1588
+ IntPtr fallBackType = AndroidJNISafe . FindClass ( "java/lang/Object" ) ;
1589
+ IntPtr arrayType = IntPtr . Zero ;
1590
+
1591
+ for ( int i = 0 ; i < arrayLen ; ++ i )
1592
+ {
1593
+ if ( objArray [ i ] != null )
1594
+ {
1595
+ jniObjs [ i ] = objArray [ i ] . GetRawProxy ( ) ;
1596
+ IntPtr objectType = objArray [ i ] . javaInterface . GetRawClass ( ) ;
1597
+ if ( arrayType == IntPtr . Zero )
1598
+ {
1599
+ arrayType = objectType ;
1600
+ }
1601
+ else if ( arrayType != fallBackType && ! AndroidJNI . IsSameObject ( arrayType , objectType ) )
1602
+ {
1603
+ arrayType = fallBackType ; // java/lang/Object
1564
1604
}
1565
1605
}
1566
1606
else
@@ -1573,6 +1613,7 @@ public static IntPtr ConvertToJNIArray(System.Array array)
1573
1613
AndroidJNISafe . DeleteLocalRef ( fallBackType ) ;
1574
1614
return res ;
1575
1615
}
1616
+
1576
1617
else
1577
1618
{
1578
1619
throw new Exception ( "JNI; Unknown array type '" + type + "'" ) ;
@@ -1832,6 +1873,13 @@ public static string GetSignature(object obj)
1832
1873
return "L" + javaClass . Call < System . String > ( "getName" ) + ";" ;
1833
1874
}
1834
1875
}
1876
+ else if ( obj == ( object ) type && AndroidReflection . IsAssignableFrom ( typeof ( AndroidJavaProxy ) , type ) )
1877
+ {
1878
+ // underlying Java class/interface can be found only for an actual object of 'type',
1879
+ // and we cannot use Activator.CreateInstance(type) here because default constructor might not exist for 'type',
1880
+ // returning empty string, this way ReflectionHelper finds field by name only.
1881
+ return "" ;
1882
+ }
1835
1883
else if ( type . Equals ( typeof ( AndroidJavaRunnable ) ) )
1836
1884
{
1837
1885
return "Ljava/lang/Runnable;" ;
@@ -1861,7 +1909,7 @@ public static string GetSignature(object obj)
1861
1909
System . Text . StringBuilder sb = new System . Text . StringBuilder ( ) ;
1862
1910
sb . Append ( '[' ) ;
1863
1911
sb . Append ( GetSignature ( type . GetElementType ( ) ) ) ;
1864
- return sb . ToString ( ) ;
1912
+ return sb . Length > 1 ? sb . ToString ( ) : "" ;
1865
1913
}
1866
1914
else
1867
1915
{
0 commit comments