diff options
author | Yeongjong Lee <yj34.lee@samsung.com> | 2020-01-23 07:30:13 +0900 |
---|---|---|
committer | WooHyun Jung <wh0705.jung@samsung.com> | 2020-01-23 07:30:14 +0900 |
commit | 97098dcc50b62e51dad3469619ed55242ca01a80 (patch) | |
tree | 33d372fef1f883a12f4172ceb9ab07223ca28805 | |
parent | 5137f6d143c681fcf4f53e4e45df8af1a538ae75 (diff) |
csharp: cleanup concrete class
Summary:
Concrete class is only used to call static member of NativeMethod. they don't
need any inheritance and implementation of c functions.
Depends on D9893
Test Plan: ninja test
Reviewers: lauromoura, felipealmeida
Subscribers: Jaehyun_Cho, woohyun, segfaultxavi, cedric, #reviewers, #committers
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D9894
-rw-r--r-- | src/bin/eolian_mono/eolian/mono/events.hh | 2 | ||||
-rw-r--r-- | src/bin/eolian_mono/eolian/mono/klass.hh | 108 | ||||
-rw-r--r-- | src/bin/eolian_mono/eolian/mono/name_helpers.hh | 17 | ||||
-rw-r--r-- | src/bin/eolian_mono/eolian/mono/struct_definition.hh | 3 | ||||
-rw-r--r-- | src/bindings/mono/eina_mono/eina_container_common.cs | 24 | ||||
-rw-r--r-- | src/bindings/mono/eo_mono/iwrapper.cs | 12 | ||||
-rw-r--r-- | src/tests/efl_mono/Eo.cs | 32 | ||||
-rw-r--r-- | src/tests/efl_mono/dummy_test_object.c | 22 | ||||
-rw-r--r-- | src/tests/efl_mono/dummy_test_object.eo | 17 |
9 files changed, 106 insertions, 131 deletions
diff --git a/src/bin/eolian_mono/eolian/mono/events.hh b/src/bin/eolian_mono/eolian/mono/events.hh index 7405f8c2e1..b6cb4aa511 100644 --- a/src/bin/eolian_mono/eolian/mono/events.hh +++ b/src/bin/eolian_mono/eolian/mono/events.hh | |||
@@ -131,7 +131,7 @@ struct unpack_event_args_visitor | |||
131 | } | 131 | } |
132 | bool operator()(grammar::attributes::klass_name const& cls) const | 132 | bool operator()(grammar::attributes::klass_name const& cls) const |
133 | { | 133 | { |
134 | return as_generator("(Efl.Eo.Globals.CreateWrapperFor(info) as " + name_helpers::klass_full_concrete_name(cls) + ")").generate(sink, attributes::unused, *context); | 134 | return as_generator("(Efl.Eo.Globals.CreateWrapperFor(info) as " + name_helpers::klass_full_interface_name(cls) + ")").generate(sink, attributes::unused, *context); |
135 | } | 135 | } |
136 | bool operator()(attributes::complex_type_def const& types) const | 136 | bool operator()(attributes::complex_type_def const& types) const |
137 | { | 137 | { |
diff --git a/src/bin/eolian_mono/eolian/mono/klass.hh b/src/bin/eolian_mono/eolian/mono/klass.hh index 072ea6c143..da6fd6d45c 100644 --- a/src/bin/eolian_mono/eolian/mono/klass.hh +++ b/src/bin/eolian_mono/eolian/mono/klass.hh | |||
@@ -193,98 +193,9 @@ struct klass | |||
193 | auto concrete_cxt = context_add_tag(class_context{class_context::concrete, | 193 | auto concrete_cxt = context_add_tag(class_context{class_context::concrete, |
194 | name_helpers::klass_full_concrete_or_interface_name(cls)}, | 194 | name_helpers::klass_full_concrete_or_interface_name(cls)}, |
195 | context); | 195 | context); |
196 | auto concrete_name = name_helpers::klass_concrete_name(cls); | ||
197 | auto interface_name = name_helpers::klass_interface_name(cls); | ||
198 | 196 | ||
199 | // We can't make these internal yet as they have methods that are used by | 197 | if(!generate_native_inherit_class(sink, cls, change_indentation(indent, concrete_cxt))) |
200 | // other classes that implement the interface. | ||
201 | if(!as_generator | ||
202 | ( | ||
203 | documentation(1) | ||
204 | << scope_tab << "public sealed " << (is_partial ? "partial ":"") << "class " << concrete_name << " :\n" | ||
205 | << scope_tab(2) << (root ? "Efl.Eo.EoWrapper" : "") << (klass_full_concrete_or_interface_name % "") | ||
206 | << ",\n" << scope_tab(2) << interface_name | ||
207 | << *(",\n" << scope_tab(2) << name_helpers::klass_full_concrete_or_interface_name) << "\n" | ||
208 | << scope_tab << "{\n" | ||
209 | ).generate(sink, std::make_tuple(cls, inherit_classes, inherit_interfaces), concrete_cxt)) | ||
210 | return false; | ||
211 | |||
212 | if (!generate_fields(sink, cls, concrete_cxt)) | ||
213 | return false; | ||
214 | |||
215 | if (!as_generator | ||
216 | ( | ||
217 | scope_tab(2) << "/// <summary>Subclasses should override this constructor if they are expected to be instantiated from native code.\n" | ||
218 | << scope_tab(2) << "/// Do not call this constructor directly.</summary>\n" | ||
219 | << scope_tab(2) << "/// <param name=\"ch\">Tag struct storing the native handle of the object being constructed.</param>\n" | ||
220 | << scope_tab(2) << "private " << concrete_name << "(ConstructingHandle ch) : base(ch)\n" | ||
221 | << scope_tab(2) << "{\n" | ||
222 | << scope_tab(2) << "}\n\n" | ||
223 | ) | ||
224 | .generate(sink, attributes::unused, concrete_cxt)) | ||
225 | return false; | ||
226 | |||
227 | if (!as_generator | ||
228 | ( | ||
229 | scope_tab(2) << "[System.Runtime.InteropServices.DllImport(" << context_find_tag<library_context>(concrete_cxt).actual_library_name(cls.filename) | ||
230 | << ")] internal static extern System.IntPtr\n" | ||
231 | << scope_tab(2) << scope_tab << name_helpers::klass_get_name(cls) << "();\n\n" | ||
232 | << scope_tab(2) << "/// <summary>Initializes a new instance of the <see cref=\"" << interface_name << "\"/> class.\n" | ||
233 | << scope_tab(2) << "/// Internal usage: This is used when interacting with C code and should not be used directly.</summary>\n" | ||
234 | << scope_tab(2) << "/// <param name=\"wh\">The native pointer to be wrapped.</param>\n" | ||
235 | << scope_tab(2) << "private " << concrete_name << "(Efl.Eo.WrappingHandle wh) : base(wh)\n" | ||
236 | << scope_tab(2) << "{\n" | ||
237 | << scope_tab(2) << "}\n\n" | ||
238 | ) | ||
239 | .generate(sink, attributes::unused, concrete_cxt)) | ||
240 | return false; | ||
241 | |||
242 | if (!generate_events(sink, cls, concrete_cxt)) | ||
243 | return false; | ||
244 | |||
245 | if (!as_generator(lit("#pragma warning disable CS0628\n")).generate(sink, attributes::unused, concrete_cxt)) | ||
246 | return false; | ||
247 | |||
248 | // Parts | ||
249 | if(!as_generator(*(part_definition)) | ||
250 | .generate(sink, cls.parts, concrete_cxt)) return false; | ||
251 | |||
252 | // Concrete function definitions | ||
253 | auto implemented_methods = helpers::get_all_implementable_methods(cls, concrete_cxt); | ||
254 | if(!as_generator(*(function_definition)) | ||
255 | .generate(sink, implemented_methods, concrete_cxt)) return false; | ||
256 | |||
257 | // Async wrappers | ||
258 | if(!as_generator(*(async_function_definition)).generate(sink, implemented_methods, concrete_cxt)) | ||
259 | return false; | ||
260 | |||
261 | // Property wrappers | ||
262 | if (!as_generator(*(property_wrapper_definition(cls))).generate(sink, cls.properties, concrete_cxt)) | ||
263 | return false; | ||
264 | |||
265 | for (auto&& klass : helpers::non_implemented_interfaces(cls, concrete_cxt)) | ||
266 | { | ||
267 | attributes::klass_def c(get_klass(klass, cls.unit), cls.unit); | ||
268 | if (!as_generator(*(property_wrapper_definition(cls))).generate(sink, c.properties, concrete_cxt)) | ||
269 | return false; | ||
270 | } | ||
271 | |||
272 | if (!as_generator(lit("#pragma warning restore CS0628\n")).generate(sink, attributes::unused, concrete_cxt)) | ||
273 | return false; | ||
274 | |||
275 | // Copied from nativeinherit class, used when setting up providers. | ||
276 | if(!as_generator( | ||
277 | scope_tab(2) << "private static IntPtr GetEflClassStatic()\n" | ||
278 | << scope_tab(2) << "{\n" | ||
279 | << scope_tab(2) << scope_tab << "return " << name_helpers::klass_get_full_name(cls) << "();\n" | ||
280 | << scope_tab(2) << "}\n\n" | ||
281 | ).generate(sink, attributes::unused, concrete_cxt)) | ||
282 | return false; | ||
283 | |||
284 | if(!generate_native_inherit_class(sink, cls, change_indentation(indent.inc(), concrete_cxt))) | ||
285 | return true; | 198 | return true; |
286 | |||
287 | if(!as_generator(scope_tab << "}\n").generate(sink, attributes::unused, concrete_cxt)) return false; | ||
288 | } | 199 | } |
289 | 200 | ||
290 | // Inheritable class | 201 | // Inheritable class |
@@ -427,6 +338,7 @@ struct klass | |||
427 | auto inherit_name = name_helpers::klass_inherit_name(cls); | 338 | auto inherit_name = name_helpers::klass_inherit_name(cls); |
428 | auto implementable_methods = helpers::get_all_registerable_methods(cls, context); | 339 | auto implementable_methods = helpers::get_all_registerable_methods(cls, context); |
429 | bool root = !helpers::has_regular_ancestor(cls); | 340 | bool root = !helpers::has_regular_ancestor(cls); |
341 | bool is_concrete = context_find_tag<class_context>(context).current_wrapper_kind == class_context::concrete; | ||
430 | auto const& indent = current_indentation(inative_cxt).inc(); | 342 | auto const& indent = current_indentation(inative_cxt).inc(); |
431 | std::string klass_since; | 343 | std::string klass_since; |
432 | 344 | ||
@@ -447,11 +359,23 @@ struct klass | |||
447 | << klass_since | 359 | << klass_since |
448 | << indent << "/// </summary>\n" | 360 | << indent << "/// </summary>\n" |
449 | << indent << "[EditorBrowsable(EditorBrowsableState.Never)]\n" | 361 | << indent << "[EditorBrowsable(EditorBrowsableState.Never)]\n" |
450 | << indent << "internal new class " << native_inherit_name << " : " << (root ? "Efl.Eo.EoWrapper.NativeMethods" : base_name) << "\n" | 362 | << indent << "internal " << (is_concrete ? "" : "new ") << "class " << native_inherit_name << " : " << (root ? "Efl.Eo.EoWrapper.NativeMethods" : base_name) << "\n" |
451 | << indent << "{\n" | 363 | << indent << "{\n" |
452 | ).generate(sink, attributes::unused, inative_cxt)) | 364 | ).generate(sink, attributes::unused, inative_cxt)) |
453 | return false; | 365 | return false; |
454 | 366 | ||
367 | if(is_concrete) | ||
368 | { | ||
369 | if (!as_generator | ||
370 | ( | ||
371 | scope_tab(2) << "[System.Runtime.InteropServices.DllImport(" << context_find_tag<library_context>(context).actual_library_name(cls.filename) | ||
372 | << ")] internal static extern System.IntPtr\n" | ||
373 | << scope_tab(2) << scope_tab << name_helpers::klass_get_name(cls) << "();\n" | ||
374 | ) | ||
375 | .generate(sink, attributes::unused, inative_cxt)) | ||
376 | return false; | ||
377 | } | ||
378 | |||
455 | if(implementable_methods.size() >= 1) | 379 | if(implementable_methods.size() >= 1) |
456 | { | 380 | { |
457 | if(!as_generator( | 381 | if(!as_generator( |
@@ -502,7 +426,7 @@ struct klass | |||
502 | ).generate(sink, attributes::unused, inative_cxt)) | 426 | ).generate(sink, attributes::unused, inative_cxt)) |
503 | return false; | 427 | return false; |
504 | 428 | ||
505 | if (!root || context_find_tag<class_context>(context).current_wrapper_kind != class_context::concrete) | 429 | if (!root || !is_concrete) |
506 | if(!as_generator(indent << scope_tab << scope_tab << "descs.AddRange(base.GetEoOps(type, false));\n").generate(sink, attributes::unused, inative_cxt)) | 430 | if(!as_generator(indent << scope_tab << scope_tab << "descs.AddRange(base.GetEoOps(type, false));\n").generate(sink, attributes::unused, inative_cxt)) |
507 | return false; | 431 | return false; |
508 | 432 | ||
diff --git a/src/bin/eolian_mono/eolian/mono/name_helpers.hh b/src/bin/eolian_mono/eolian/mono/name_helpers.hh index 7f71d9279b..ae958ba623 100644 --- a/src/bin/eolian_mono/eolian/mono/name_helpers.hh +++ b/src/bin/eolian_mono/eolian/mono/name_helpers.hh | |||
@@ -399,9 +399,7 @@ struct klass_full_interface_name_generator | |||
399 | template<typename T> | 399 | template<typename T> |
400 | inline std::string klass_concrete_name(T const& klass) | 400 | inline std::string klass_concrete_name(T const& klass) |
401 | { | 401 | { |
402 | return utils::remove_all(klass.eolian_name, '_') + ((klass.type == attributes::class_type::mixin | 402 | return utils::remove_all(klass.eolian_name, '_'); |
403 | || klass.type == attributes::class_type::interface_) | ||
404 | ? "Concrete" : ""); | ||
405 | } | 403 | } |
406 | 404 | ||
407 | template<typename T> | 405 | template<typename T> |
@@ -467,14 +465,19 @@ inline std::string klass_inherit_name(T const& klass) | |||
467 | } | 465 | } |
468 | 466 | ||
469 | template<typename T> | 467 | template<typename T> |
470 | inline std::string klass_native_inherit_name(EINA_UNUSED T const& klass) | 468 | inline std::string klass_native_inherit_name(T const& klass) |
471 | { | 469 | { |
472 | return "NativeMethods"; | 470 | return ((klass.type == attributes::class_type::mixin |
471 | || klass.type == attributes::class_type::interface_) ? klass_interface_name(klass) : "") + "NativeMethods"; | ||
473 | } | 472 | } |
474 | 473 | ||
475 | template<typename T> | 474 | template<typename T> |
476 | inline std::string klass_full_native_inherit_name(T const& klass) | 475 | inline std::string klass_full_native_inherit_name(T const& klass) |
477 | { | 476 | { |
477 | if(klass.type == attributes::class_type::mixin | ||
478 | || klass.type == attributes::class_type::interface_) | ||
479 | return join_namespaces(klass.namespaces, '.', managed_namespace) + klass_native_inherit_name(klass); | ||
480 | |||
478 | return klass_full_concrete_name(klass) + "." + klass_native_inherit_name(klass); | 481 | return klass_full_concrete_name(klass) + "." + klass_native_inherit_name(klass); |
479 | } | 482 | } |
480 | 483 | ||
@@ -487,6 +490,10 @@ inline std::string klass_get_name(T const& clsname) | |||
487 | template<typename T> | 490 | template<typename T> |
488 | inline std::string klass_get_full_name(T const& clsname) | 491 | inline std::string klass_get_full_name(T const& clsname) |
489 | { | 492 | { |
493 | if(clsname.type == attributes::class_type::mixin | ||
494 | || clsname.type == attributes::class_type::interface_) | ||
495 | return klass_get_name(clsname); | ||
496 | |||
490 | return klass_full_concrete_name(clsname) + "." + klass_get_name(clsname); | 497 | return klass_full_concrete_name(clsname) + "." + klass_get_name(clsname); |
491 | } | 498 | } |
492 | 499 | ||
diff --git a/src/bin/eolian_mono/eolian/mono/struct_definition.hh b/src/bin/eolian_mono/eolian/mono/struct_definition.hh index 176b5518d7..1f4152aa74 100644 --- a/src/bin/eolian_mono/eolian/mono/struct_definition.hh +++ b/src/bin/eolian_mono/eolian/mono/struct_definition.hh | |||
@@ -190,11 +190,10 @@ struct to_external_field_convert_generator | |||
190 | if (klass) | 190 | if (klass) |
191 | { | 191 | { |
192 | auto interface_name = name_helpers::klass_full_interface_name(*klass); | 192 | auto interface_name = name_helpers::klass_full_interface_name(*klass); |
193 | auto concrete_name = name_helpers::klass_full_concrete_name(*klass); | ||
194 | if (!as_generator( | 193 | if (!as_generator( |
195 | "\n" | 194 | "\n" |
196 | << indent << scope_tab << scope_tab << "_external_struct." << string | 195 | << indent << scope_tab << scope_tab << "_external_struct." << string |
197 | << " = (" << concrete_name << ") Efl.Eo.Globals.CreateWrapperFor(_internal_struct." << string << ");\n" | 196 | << " = (" << interface_name << ") Efl.Eo.Globals.CreateWrapperFor(_internal_struct." << string << ");\n" |
198 | ).generate(sink, std::make_tuple(field_name, field_name), context)) | 197 | ).generate(sink, std::make_tuple(field_name, field_name), context)) |
199 | return false; | 198 | return false; |
200 | } | 199 | } |
diff --git a/src/bindings/mono/eina_mono/eina_container_common.cs b/src/bindings/mono/eina_mono/eina_container_common.cs index 192469a033..a07153e51a 100644 --- a/src/bindings/mono/eina_mono/eina_container_common.cs +++ b/src/bindings/mono/eina_mono/eina_container_common.cs | |||
@@ -1003,22 +1003,6 @@ internal static class TraitFunctions | |||
1003 | 1003 | ||
1004 | private static IDictionary<System.Type, object> register = new Dictionary<System.Type, object>(); | 1004 | private static IDictionary<System.Type, object> register = new Dictionary<System.Type, object>(); |
1005 | 1005 | ||
1006 | private static System.Type AsEflInstantiableType(System.Type type) | ||
1007 | { | ||
1008 | if (!IsEflObject(type)) | ||
1009 | { | ||
1010 | return null; | ||
1011 | } | ||
1012 | |||
1013 | if (type.IsInterface) | ||
1014 | { | ||
1015 | string fullName = type.FullName + "Concrete"; | ||
1016 | return type.Assembly.GetType(fullName); // That was our best guess... | ||
1017 | } | ||
1018 | |||
1019 | return type; // Not interface, so it should be a concrete. | ||
1020 | } | ||
1021 | |||
1022 | public static object RegisterTypeTraits<T>() | 1006 | public static object RegisterTypeTraits<T>() |
1023 | { | 1007 | { |
1024 | Eina.Log.Debug($"Finding TypeTraits for {typeof(T).Name}"); | 1008 | Eina.Log.Debug($"Finding TypeTraits for {typeof(T).Name}"); |
@@ -1026,14 +1010,6 @@ internal static class TraitFunctions | |||
1026 | var type = typeof(T); | 1010 | var type = typeof(T); |
1027 | if (IsEflObject(type)) | 1011 | if (IsEflObject(type)) |
1028 | { | 1012 | { |
1029 | System.Type concrete = AsEflInstantiableType(type); | ||
1030 | if (concrete == null || !type.IsAssignableFrom(concrete)) | ||
1031 | { | ||
1032 | throw new Exception("Failed to get a suitable concrete class for this type."); | ||
1033 | } | ||
1034 | |||
1035 | // No need to pass concrete as the traits class will use reflection to get the actually most | ||
1036 | // derived type returned. | ||
1037 | traits = new EflObjectElementTraits<T>(); | 1013 | traits = new EflObjectElementTraits<T>(); |
1038 | } | 1014 | } |
1039 | else if (IsString(type)) | 1015 | else if (IsString(type)) |
diff --git a/src/bindings/mono/eo_mono/iwrapper.cs b/src/bindings/mono/eo_mono/iwrapper.cs index 780735fcca..ceae250bc9 100644 --- a/src/bindings/mono/eo_mono/iwrapper.cs +++ b/src/bindings/mono/eo_mono/iwrapper.cs | |||
@@ -1221,14 +1221,12 @@ internal static class ClassRegister | |||
1221 | 1221 | ||
1222 | if (objectType.IsInterface) | 1222 | if (objectType.IsInterface) |
1223 | { | 1223 | { |
1224 | // Try to get the *Concrete class | 1224 | // Try to get the *NativeMethods class |
1225 | var assembly = objectType.Assembly; | 1225 | var nativeMethods = (Efl.Eo.NativeClass)System.Attribute.GetCustomAttributes(objectType)?.FirstOrDefault(attr => attr is Efl.Eo.NativeClass); |
1226 | objectType = assembly.GetType(objectType.FullName + "Concrete"); | 1226 | if (nativeMethods == null) |
1227 | |||
1228 | if (objectType == null) | ||
1229 | { | ||
1230 | return IntPtr.Zero; | 1227 | return IntPtr.Zero; |
1231 | } | 1228 | |
1229 | return nativeMethods.GetEflClass(); | ||
1232 | } | 1230 | } |
1233 | 1231 | ||
1234 | var method = objectType.GetMethod("GetEflClassStatic", | 1232 | var method = objectType.GetMethod("GetEflClassStatic", |
diff --git a/src/tests/efl_mono/Eo.cs b/src/tests/efl_mono/Eo.cs index 70e9d29c16..8d00155e10 100644 --- a/src/tests/efl_mono/Eo.cs +++ b/src/tests/efl_mono/Eo.cs | |||
@@ -385,6 +385,16 @@ class TestEoMultipleChildClasses | |||
385 | 385 | ||
386 | class TestCsharpProperties | 386 | class TestCsharpProperties |
387 | { | 387 | { |
388 | |||
389 | private class MyObject : Dummy.TestObject | ||
390 | { | ||
391 | public MyObject(Efl.Object parent = null) : base(parent) | ||
392 | { | ||
393 | } | ||
394 | private MyObject(ConstructingHandle ch) : base(ch) | ||
395 | { | ||
396 | } | ||
397 | } | ||
388 | public static void test_csharp_properties() | 398 | public static void test_csharp_properties() |
389 | { | 399 | { |
390 | var obj = new Dummy.TestObject(); | 400 | var obj = new Dummy.TestObject(); |
@@ -428,6 +438,28 @@ class TestCsharpProperties | |||
428 | iface.Dispose(); | 438 | iface.Dispose(); |
429 | } | 439 | } |
430 | 440 | ||
441 | public static void test_iface_value_property() | ||
442 | { | ||
443 | var obj = new Dummy.TestObject(); | ||
444 | var prop = new MyObject(); | ||
445 | |||
446 | obj.IfaceValueProp = prop; | ||
447 | Test.AssertEquals(obj.IfaceValueProp, prop); | ||
448 | |||
449 | obj.Dispose(); | ||
450 | prop.Dispose(); | ||
451 | } | ||
452 | |||
453 | public static void test_iface_value_from_c() | ||
454 | { | ||
455 | var obj = new Dummy.TestObject(); | ||
456 | |||
457 | obj.SetIfaceKlassProp(typeof(MyObject)); | ||
458 | Test.AssertEquals(obj.IfaceValueFromC.GetType(), typeof(MyObject)); | ||
459 | |||
460 | obj.Dispose(); | ||
461 | } | ||
462 | |||
431 | public static void test_csharp_multi_valued_prop() | 463 | public static void test_csharp_multi_valued_prop() |
432 | { | 464 | { |
433 | var obj = new Dummy.TestObject(); | 465 | var obj = new Dummy.TestObject(); |
diff --git a/src/tests/efl_mono/dummy_test_object.c b/src/tests/efl_mono/dummy_test_object.c index b87aff1cd4..687737a4aa 100644 --- a/src/tests/efl_mono/dummy_test_object.c +++ b/src/tests/efl_mono/dummy_test_object.c | |||
@@ -38,6 +38,8 @@ typedef struct Dummy_Test_Object_Data | |||
38 | int prop1; | 38 | int prop1; |
39 | int prop2; | 39 | int prop2; |
40 | Eo *hidden_object; | 40 | Eo *hidden_object; |
41 | Dummy_Test_Iface *iface_value_prop; | ||
42 | Efl_Class *iface_klass; | ||
41 | 43 | ||
42 | // Containers passed to C# as iterator/accessors | 44 | // Containers passed to C# as iterator/accessors |
43 | Eina_Array *out_array; | 45 | Eina_Array *out_array; |
@@ -4784,6 +4786,26 @@ Eo *_dummy_test_object_hidden_object_get(EINA_UNUSED const Eo *obj, Dummy_Test_O | |||
4784 | return pd->hidden_object; | 4786 | return pd->hidden_object; |
4785 | } | 4787 | } |
4786 | 4788 | ||
4789 | Dummy_Test_Iface *_dummy_test_object_iface_value_prop_get(EINA_UNUSED const Eo *obj, Dummy_Test_Object_Data *pd) | ||
4790 | { | ||
4791 | return pd->iface_value_prop; | ||
4792 | } | ||
4793 | |||
4794 | void _dummy_test_object_iface_value_prop_set(EINA_UNUSED Eo *obj, Dummy_Test_Object_Data *pd, Dummy_Test_Iface *prop) | ||
4795 | { | ||
4796 | pd->iface_value_prop = prop; | ||
4797 | } | ||
4798 | |||
4799 | void _dummy_test_object_iface_klass_prop_set(EINA_UNUSED Eo *obj, Dummy_Test_Object_Data *pd, Efl_Class *klass) | ||
4800 | { | ||
4801 | pd->iface_klass = klass; | ||
4802 | } | ||
4803 | |||
4804 | Dummy_Test_Iface *_dummy_test_object_iface_value_from_c_get(const Eo *obj, Dummy_Test_Object_Data *pd) | ||
4805 | { | ||
4806 | return efl_add(pd->iface_klass, (Eo*)obj); | ||
4807 | } | ||
4808 | |||
4787 | // Inherit | 4809 | // Inherit |
4788 | int _dummy_inherit_helper_receive_dummy_and_call_int_out(Dummy_Test_Object *x) | 4810 | int _dummy_inherit_helper_receive_dummy_and_call_int_out(Dummy_Test_Object *x) |
4789 | { | 4811 | { |
diff --git a/src/tests/efl_mono/dummy_test_object.eo b/src/tests/efl_mono/dummy_test_object.eo index cf2ae7ce03..ee24e5ef9b 100644 --- a/src/tests/efl_mono/dummy_test_object.eo +++ b/src/tests/efl_mono/dummy_test_object.eo | |||
@@ -1664,6 +1664,23 @@ class Dummy.Test_Object extends Efl.Object implements Dummy.Test_Iface { | |||
1664 | obj: Efl.Object; | 1664 | obj: Efl.Object; |
1665 | } | 1665 | } |
1666 | } | 1666 | } |
1667 | @property iface_value_prop { | ||
1668 | values { | ||
1669 | prop: Dummy.Test_Iface; | ||
1670 | } | ||
1671 | } | ||
1672 | @property iface_klass_prop { | ||
1673 | set {} | ||
1674 | values { | ||
1675 | klass: Efl.Class; | ||
1676 | } | ||
1677 | } | ||
1678 | @property iface_value_from_c { | ||
1679 | get {} | ||
1680 | values { | ||
1681 | prop: Dummy.Test_Iface; | ||
1682 | } | ||
1683 | } | ||
1667 | } | 1684 | } |
1668 | implements { | 1685 | implements { |
1669 | Efl.Object.constructor; | 1686 | Efl.Object.constructor; |