diff options
author | Hermet Park <hermetpark@gmail.com> | 2020-01-23 10:16:22 +0900 |
---|---|---|
committer | Hermet Park <hermetpark@gmail.com> | 2020-01-23 10:16:22 +0900 |
commit | d30dd3140c588388ddb32a6ed79fcc47b3e187a8 (patch) | |
tree | 79b1049ee7ed18ec9c7e2de1978caeb1fb5e5c20 | |
parent | 911c1c49f97280cb7714459bf4fd9a9d09e1642b (diff) | |
parent | 68d7f584cb78402dbe884d3a7b902c4735d96f8a (diff) | |
download | efl-d30dd3140c588388ddb32a6ed79fcc47b3e187a8.tar.gz |
Merge branch 'master' into devs/hermet/lottie
31 files changed, 592 insertions, 173 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 } bool operator()(grammar::attributes::klass_name const& cls) const { - return as_generator("(Efl.Eo.Globals.CreateWrapperFor(info) as " + name_helpers::klass_full_concrete_name(cls) + ")").generate(sink, attributes::unused, *context); + return as_generator("(Efl.Eo.Globals.CreateWrapperFor(info) as " + name_helpers::klass_full_interface_name(cls) + ")").generate(sink, attributes::unused, *context); } bool operator()(attributes::complex_type_def const& types) const { diff --git a/src/bin/eolian_mono/eolian/mono/function_definition.hh b/src/bin/eolian_mono/eolian/mono/function_definition.hh index fcc8a88f15..3c30cdd3fe 100644 --- a/src/bin/eolian_mono/eolian/mono/function_definition.hh +++ b/src/bin/eolian_mono/eolian/mono/function_definition.hh @@ -284,8 +284,9 @@ struct property_extension_method_definition_generator if (property.setter.is_engaged()) { attributes::type_def prop_type = property.setter->parameters[0].type; - if (!as_generator(scope_tab(2) << "public static Efl.BindableProperty<" << type(true) << "> " << managed_name << "<T>(this Efl.Ui.ItemFactory<T> fac) where T : " - << name_helpers::klass_full_concrete_or_interface_name(cls) << " {\n" + if (!as_generator(scope_tab(2) << "public static Efl.BindableProperty<" << type(true) << "> " << managed_name << "<T>(this Efl.Ui.ItemFactory<T> fac, Efl.Csharp.ExtensionTag<" + << name_helpers::klass_full_concrete_or_interface_name(cls) + << ", T>magic = null) where T : " << name_helpers::klass_full_concrete_or_interface_name(cls) << " {\n" << scope_tab(2) << scope_tab << "return new Efl.BindableProperty<" << type(true) << ">(\"" << property.name << "\", fac);\n" << scope_tab(2) << "}\n\n" ).generate(sink, std::make_tuple(prop_type, prop_type), context)) @@ -300,8 +301,9 @@ struct property_extension_method_definition_generator if (property.setter.is_engaged()) { attributes::type_def prop_type = property.setter->parameters[0].type; - if (!as_generator(scope_tab(2) << "public static Efl.BindableProperty<" << type(true) << "> " << managed_name << "<T>(this Efl.BindablePart<T> part) where T : " - << name_helpers::klass_full_concrete_or_interface_name(cls) << " {\n" + if (!as_generator(scope_tab(2) << "public static Efl.BindableProperty<" << type(true) << "> " << managed_name << "<T>(this Efl.BindablePart<T> part, Efl.Csharp.ExtensionTag<" + << name_helpers::klass_full_concrete_or_interface_name(cls) + << ", T>magic = null) where T : " << name_helpers::klass_full_concrete_or_interface_name(cls) << " {\n" << scope_tab(2) << scope_tab << "Contract.Requires(part != null, nameof(part));\n" << scope_tab(2) << scope_tab << "return new Efl.BindableProperty<" << type(true) << ">(part.PartName, \"" << property.name << "\", part.Binder);\n" << scope_tab(2) << "}\n\n" 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 auto concrete_cxt = context_add_tag(class_context{class_context::concrete, name_helpers::klass_full_concrete_or_interface_name(cls)}, context); - auto concrete_name = name_helpers::klass_concrete_name(cls); - auto interface_name = name_helpers::klass_interface_name(cls); - // We can't make these internal yet as they have methods that are used by - // other classes that implement the interface. - if(!as_generator - ( - documentation(1) - << scope_tab << "public sealed " << (is_partial ? "partial ":"") << "class " << concrete_name << " :\n" - << scope_tab(2) << (root ? "Efl.Eo.EoWrapper" : "") << (klass_full_concrete_or_interface_name % "") - << ",\n" << scope_tab(2) << interface_name - << *(",\n" << scope_tab(2) << name_helpers::klass_full_concrete_or_interface_name) << "\n" - << scope_tab << "{\n" - ).generate(sink, std::make_tuple(cls, inherit_classes, inherit_interfaces), concrete_cxt)) - return false; - - if (!generate_fields(sink, cls, concrete_cxt)) - return false; - - if (!as_generator - ( - scope_tab(2) << "/// <summary>Subclasses should override this constructor if they are expected to be instantiated from native code.\n" - << scope_tab(2) << "/// Do not call this constructor directly.</summary>\n" - << scope_tab(2) << "/// <param name=\"ch\">Tag struct storing the native handle of the object being constructed.</param>\n" - << scope_tab(2) << "private " << concrete_name << "(ConstructingHandle ch) : base(ch)\n" - << scope_tab(2) << "{\n" - << scope_tab(2) << "}\n\n" - ) - .generate(sink, attributes::unused, concrete_cxt)) - return false; - - if (!as_generator - ( - scope_tab(2) << "[System.Runtime.InteropServices.DllImport(" << context_find_tag<library_context>(concrete_cxt).actual_library_name(cls.filename) - << ")] internal static extern System.IntPtr\n" - << scope_tab(2) << scope_tab << name_helpers::klass_get_name(cls) << "();\n\n" - << scope_tab(2) << "/// <summary>Initializes a new instance of the <see cref=\"" << interface_name << "\"/> class.\n" - << scope_tab(2) << "/// Internal usage: This is used when interacting with C code and should not be used directly.</summary>\n" - << scope_tab(2) << "/// <param name=\"wh\">The native pointer to be wrapped.</param>\n" - << scope_tab(2) << "private " << concrete_name << "(Efl.Eo.WrappingHandle wh) : base(wh)\n" - << scope_tab(2) << "{\n" - << scope_tab(2) << "}\n\n" - ) - .generate(sink, attributes::unused, concrete_cxt)) - return false; - - if (!generate_events(sink, cls, concrete_cxt)) - return false; - - if (!as_generator(lit("#pragma warning disable CS0628\n")).generate(sink, attributes::unused, concrete_cxt)) - return false; - - // Parts - if(!as_generator(*(part_definition)) - .generate(sink, cls.parts, concrete_cxt)) return false; - - // Concrete function definitions - auto implemented_methods = helpers::get_all_implementable_methods(cls, concrete_cxt); - if(!as_generator(*(function_definition)) - .generate(sink, implemented_methods, concrete_cxt)) return false; - - // Async wrappers - if(!as_generator(*(async_function_definition)).generate(sink, implemented_methods, concrete_cxt)) - return false; - - // Property wrappers - if (!as_generator(*(property_wrapper_definition(cls))).generate(sink, cls.properties, concrete_cxt)) - return false; - - for (auto&& klass : helpers::non_implemented_interfaces(cls, concrete_cxt)) - { - attributes::klass_def c(get_klass(klass, cls.unit), cls.unit); - if (!as_generator(*(property_wrapper_definition(cls))).generate(sink, c.properties, concrete_cxt)) - return false; - } - - if (!as_generator(lit("#pragma warning restore CS0628\n")).generate(sink, attributes::unused, concrete_cxt)) - return false; - - // Copied from nativeinherit class, used when setting up providers. - if(!as_generator( - scope_tab(2) << "private static IntPtr GetEflClassStatic()\n" - << scope_tab(2) << "{\n" - << scope_tab(2) << scope_tab << "return " << name_helpers::klass_get_full_name(cls) << "();\n" - << scope_tab(2) << "}\n\n" - ).generate(sink, attributes::unused, concrete_cxt)) - return false; - - if(!generate_native_inherit_class(sink, cls, change_indentation(indent.inc(), concrete_cxt))) + if(!generate_native_inherit_class(sink, cls, change_indentation(indent, concrete_cxt))) return true; - - if(!as_generator(scope_tab << "}\n").generate(sink, attributes::unused, concrete_cxt)) return false; } // Inheritable class @@ -427,6 +338,7 @@ struct klass auto inherit_name = name_helpers::klass_inherit_name(cls); auto implementable_methods = helpers::get_all_registerable_methods(cls, context); bool root = !helpers::has_regular_ancestor(cls); + bool is_concrete = context_find_tag<class_context>(context).current_wrapper_kind == class_context::concrete; auto const& indent = current_indentation(inative_cxt).inc(); std::string klass_since; @@ -447,11 +359,23 @@ struct klass << klass_since << indent << "/// </summary>\n" << indent << "[EditorBrowsable(EditorBrowsableState.Never)]\n" - << indent << "internal new class " << native_inherit_name << " : " << (root ? "Efl.Eo.EoWrapper.NativeMethods" : base_name) << "\n" + << indent << "internal " << (is_concrete ? "" : "new ") << "class " << native_inherit_name << " : " << (root ? "Efl.Eo.EoWrapper.NativeMethods" : base_name) << "\n" << indent << "{\n" ).generate(sink, attributes::unused, inative_cxt)) return false; + if(is_concrete) + { + if (!as_generator + ( + scope_tab(2) << "[System.Runtime.InteropServices.DllImport(" << context_find_tag<library_context>(context).actual_library_name(cls.filename) + << ")] internal static extern System.IntPtr\n" + << scope_tab(2) << scope_tab << name_helpers::klass_get_name(cls) << "();\n" + ) + .generate(sink, attributes::unused, inative_cxt)) + return false; + } + if(implementable_methods.size() >= 1) { if(!as_generator( @@ -502,7 +426,7 @@ struct klass ).generate(sink, attributes::unused, inative_cxt)) return false; - if (!root || context_find_tag<class_context>(context).current_wrapper_kind != class_context::concrete) + if (!root || !is_concrete) if(!as_generator(indent << scope_tab << scope_tab << "descs.AddRange(base.GetEoOps(type, false));\n").generate(sink, attributes::unused, inative_cxt)) return false; 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 template<typename T> inline std::string klass_concrete_name(T const& klass) { - return utils::remove_all(klass.eolian_name, '_') + ((klass.type == attributes::class_type::mixin - || klass.type == attributes::class_type::interface_) - ? "Concrete" : ""); + return utils::remove_all(klass.eolian_name, '_'); } template<typename T> @@ -467,14 +465,19 @@ inline std::string klass_inherit_name(T const& klass) } template<typename T> -inline std::string klass_native_inherit_name(EINA_UNUSED T const& klass) +inline std::string klass_native_inherit_name(T const& klass) { - return "NativeMethods"; + return ((klass.type == attributes::class_type::mixin + || klass.type == attributes::class_type::interface_) ? klass_interface_name(klass) : "") + "NativeMethods"; } template<typename T> inline std::string klass_full_native_inherit_name(T const& klass) { + if(klass.type == attributes::class_type::mixin + || klass.type == attributes::class_type::interface_) + return join_namespaces(klass.namespaces, '.', managed_namespace) + klass_native_inherit_name(klass); + return klass_full_concrete_name(klass) + "." + klass_native_inherit_name(klass); } @@ -487,6 +490,10 @@ inline std::string klass_get_name(T const& clsname) template<typename T> inline std::string klass_get_full_name(T const& clsname) { + if(clsname.type == attributes::class_type::mixin + || clsname.type == attributes::class_type::interface_) + return klass_get_name(clsname); + return klass_full_concrete_name(clsname) + "." + klass_get_name(clsname); } diff --git a/src/bin/eolian_mono/eolian/mono/part_definition.hh b/src/bin/eolian_mono/eolian/mono/part_definition.hh index d87b0b56ac..4facf27209 100644 --- a/src/bin/eolian_mono/eolian/mono/part_definition.hh +++ b/src/bin/eolian_mono/eolian/mono/part_definition.hh @@ -70,8 +70,9 @@ struct part_extension_method_definition_generator bindableClass = "Efl.BindableFactoryPart"; if (!as_generator( - scope_tab(2) << "public static " << bindableClass << "<" << part_klass_name << "> " << name_helpers::managed_part_name(part) << "<T>(this Efl.Ui.ItemFactory<T> fac) where T : " - << name_helpers::klass_full_concrete_or_interface_name(cls) << "\n" + scope_tab(2) << "public static " << bindableClass << "<" << part_klass_name << "> " << name_helpers::managed_part_name(part) << "<T>(this Efl.Ui.ItemFactory<T> fac, Efl.Csharp.ExtensionTag<" + << name_helpers::klass_full_concrete_or_interface_name(cls) + << ", T> x=null) where T : " << name_helpers::klass_full_concrete_or_interface_name(cls) << "\n" << scope_tab(2) << "{\n" << scope_tab(2) << scope_tab << "return new " << bindableClass << "<" << part_klass_name << ">(\"" << part.name << "\", fac);\n" << scope_tab(2) << "}\n\n" 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 if (klass) { auto interface_name = name_helpers::klass_full_interface_name(*klass); - auto concrete_name = name_helpers::klass_full_concrete_name(*klass); if (!as_generator( "\n" << indent << scope_tab << scope_tab << "_external_struct." << string - << " = (" << concrete_name << ") Efl.Eo.Globals.CreateWrapperFor(_internal_struct." << string << ");\n" + << " = (" << interface_name << ") Efl.Eo.Globals.CreateWrapperFor(_internal_struct." << string << ");\n" ).generate(sink, std::make_tuple(field_name, field_name), context)) return false; } diff --git a/src/bindings/mono/efl_mono/Bind.cs b/src/bindings/mono/efl_mono/Bind.cs index 302f1dadd2..2a4fcbded5 100644 --- a/src/bindings/mono/efl_mono/Bind.cs +++ b/src/bindings/mono/efl_mono/Bind.cs @@ -148,6 +148,20 @@ public class BindableFactoryPart<T> } } +namespace Csharp +{ + +/// <summary>Helper class to differentiate between factory extension methods. +/// +/// For internal use only.</summary> +[EditorBrowsable(EditorBrowsableState.Never)] +public class ExtensionTag<TBase, TInherited> + where TInherited : TBase +{ +} + +} + } #endif 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 private static IDictionary<System.Type, object> register = new Dictionary<System.Type, object>(); - private static System.Type AsEflInstantiableType(System.Type type) - { - if (!IsEflObject(type)) - { - return null; - } - - if (type.IsInterface) - { - string fullName = type.FullName + "Concrete"; - return type.Assembly.GetType(fullName); // That was our best guess... - } - - return type; // Not interface, so it should be a concrete. - } - public static object RegisterTypeTraits<T>() { Eina.Log.Debug($"Finding TypeTraits for {typeof(T).Name}"); @@ -1026,14 +1010,6 @@ internal static class TraitFunctions var type = typeof(T); if (IsEflObject(type)) { - System.Type concrete = AsEflInstantiableType(type); - if (concrete == null || !type.IsAssignableFrom(concrete)) - { - throw new Exception("Failed to get a suitable concrete class for this type."); - } - - // No need to pass concrete as the traits class will use reflection to get the actually most - // derived type returned. traits = new EflObjectElementTraits<T>(); } 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 if (objectType.IsInterface) { - // Try to get the *Concrete class - var assembly = objectType.Assembly; - objectType = assembly.GetType(objectType.FullName + "Concrete"); - - if (objectType == null) - { + // Try to get the *NativeMethods class + var nativeMethods = (Efl.Eo.NativeClass)System.Attribute.GetCustomAttributes(objectType)?.FirstOrDefault(attr => attr is Efl.Eo.NativeClass); + if (nativeMethods == null) return IntPtr.Zero; - } + + return nativeMethods.GetEflClass(); } var method = objectType.GetMethod("GetEflClassStatic", diff --git a/src/lib/ecore_wl2/Ecore_Wl2.h b/src/lib/ecore_wl2/Ecore_Wl2.h index 6a54812204..da664939b7 100644 --- a/src/lib/ecore_wl2/Ecore_Wl2.h +++ b/src/lib/ecore_wl2/Ecore_Wl2.h @@ -1121,6 +1121,18 @@ EAPI void ecore_wl2_window_type_set(Ecore_Wl2_Window *window, Ecore_Wl2_Window_T EAPI Ecore_Wl2_Window_Type ecore_wl2_window_type_get(Ecore_Wl2_Window *window); /** + * Find the output that a given window is on + * + * @param window The window to find the output for + * + * @return An Ecore_Wl2_Output if found, or NULL otherwise + * + * @ingroup Ecore_Wl2_Window_Group + * @since 1.20 + */ +EAPI Ecore_Wl2_Output *ecore_wl2_window_output_find(Ecore_Wl2_Window *window); + +/** * Set if window rotation is supported by the window manager * * @param window @@ -1449,6 +1461,17 @@ EAPI Eina_Stringshare *ecore_wl2_input_name_get(Ecore_Wl2_Input *input); EAPI Eina_Bool ecore_wl2_input_keyboard_repeat_get(const Ecore_Wl2_Input *input, double *rate, double *delay); /** + * Set the keyboard repeat rate and delay of an input + * @param input The input + * @param rate Pointer to store the repeat rate (in seconds) + * @param rate Pointer to store the repeat delay (in seconds) + * @return True if repeat is enabled + * @ingroup Ecore_Wl2_Input_Group + * @since 1.24 + */ +EAPI Eina_Bool ecore_wl2_input_keyboard_repeat_set(Ecore_Wl2_Input *input, double rate, double delay); + +/** * Retrieves the mouse position of the seat * * @param input The seat @@ -1475,6 +1498,31 @@ EAPI Eina_Bool ecore_wl2_input_pointer_xy_get(const Ecore_Wl2_Input *input, int EAPI void ecore_wl2_input_pointer_set(Ecore_Wl2_Input *input, struct wl_surface *surface, int hot_x, int hot_y); /** + * Set a specific cursor on a given seat + * + * @brief This function will try to find a matching cursor inside the existing + * cursor theme and set the pointer for the specified seat to be + * the specified cursor + * + * @param input The seat to set the cursor on + * @param cursor The name of the cursor to try and set + * + * @ingroup Ecore_Wl2_Input_Group + * @since 1.20 + */ +EAPI void ecore_wl2_input_cursor_from_name_set(Ecore_Wl2_Input *input, const char *cursor); + +/** + * Gets default input of a given display + * + * @param display The display + * + * @ingroup Ecore_Wl2_Input_Group + * @since 1.24 + */ +EAPI Ecore_Wl2_Input *ecore_wl2_input_default_input_get(const Ecore_Wl2_Display *ewd); + +/** * @defgroup Ecore_Wl2_Output_Group Wayland Library Output Functions * @ingroup Ecore_Wl2_Group * diff --git a/src/lib/ecore_wl2/ecore_wl2_input.c b/src/lib/ecore_wl2/ecore_wl2_input.c index 6694f3687d..75a7366f82 100644 --- a/src/lib/ecore_wl2/ecore_wl2_input.c +++ b/src/lib/ecore_wl2/ecore_wl2_input.c @@ -1173,8 +1173,11 @@ _keyboard_cb_repeat_setup(void *data, struct wl_keyboard *keyboard EINA_UNUSED, } input->repeat.enabled = EINA_TRUE; - input->repeat.rate = (1.0 / rate); - input->repeat.delay = (delay / 1000.0); + if (!input->repeat.changed) + { + input->repeat.rate = (1.0 / rate); + input->repeat.delay = (delay / 1000.0); + } ev = malloc(sizeof(Ecore_Wl2_Event_Seat_Keymap_Changed)); if (ev) { @@ -1615,6 +1618,7 @@ _ecore_wl2_input_add(Ecore_Wl2_Display *display, unsigned int id, unsigned int v input->repeat.rate = 0.025; input->repeat.delay = 0.4; input->repeat.enabled = EINA_TRUE; + input->repeat.changed = EINA_FALSE; wl_array_init(&input->data.selection.types); wl_array_init(&input->data.drag.types); @@ -1814,6 +1818,18 @@ ecore_wl2_input_keymap_get(const Ecore_Wl2_Input *input) } EAPI Eina_Bool +ecore_wl2_input_keyboard_repeat_set(Ecore_Wl2_Input *input, double rate, double delay) +{ + EINA_SAFETY_ON_NULL_RETURN_VAL(input, EINA_FALSE); + EINA_SAFETY_ON_NULL_RETURN_VAL(input->display, EINA_FALSE); + EINA_SAFETY_ON_FALSE_RETURN_VAL(input->wl.keyboard, EINA_FALSE); + input->repeat.rate = rate; + input->repeat.delay = delay; + input->repeat.changed = EINA_TRUE; + return input->repeat.enabled; +} + +EAPI Eina_Bool ecore_wl2_input_keyboard_repeat_get(const Ecore_Wl2_Input *input, double *rate, double *delay) { EINA_SAFETY_ON_NULL_RETURN_VAL(input, EINA_FALSE); @@ -1855,3 +1871,17 @@ ecore_wl2_input_pointer_xy_get(const Ecore_Wl2_Input *input, int *x, int *y) if (y) *y = input->pointer.sy; return EINA_TRUE; } + +EAPI Ecore_Wl2_Input * +ecore_wl2_input_default_input_get(const Ecore_Wl2_Display *ewd) +{ + Ecore_Wl2_Input *input; + + EINA_SAFETY_ON_NULL_RETURN_VAL(ewd, NULL); + EINA_SAFETY_ON_NULL_RETURN_VAL(ewd->inputs, NULL); + + input = ecore_wl2_display_input_find_by_name(ewd, "seat0"); + if (!input) input = ecore_wl2_display_input_find_by_name(ewd, "default"); + + return input; +} diff --git a/src/lib/ecore_wl2/ecore_wl2_internal.h b/src/lib/ecore_wl2/ecore_wl2_internal.h index 111b2cad30..98dd5c1b5a 100644 --- a/src/lib/ecore_wl2/ecore_wl2_internal.h +++ b/src/lib/ecore_wl2/ecore_wl2_internal.h @@ -126,18 +126,6 @@ EAPI void ecore_wl2_window_iconified_set(Ecore_Wl2_Window *window, Eina_Bool ico EAPI Eina_Bool ecore_wl2_window_pending_get(Ecore_Wl2_Window *window); /** - * Find the output that a given window is on - * - * @param window The window to find the output for - * - * @return An Ecore_Wl2_Output if found, or NULL otherwise - * - * @ingroup Ecore_Wl2_Window_Group - * @since 1.20 - */ -EAPI Ecore_Wl2_Output *ecore_wl2_window_output_find(Ecore_Wl2_Window *window); - -/** * @defgroup Ecore_Wl2_Dnd_Group Wayland Library Drag-n-Drop Functions * @ingroup Ecore_Wl2_Group * @@ -579,21 +567,6 @@ EAPI void ecore_wl2_window_aux_hint_del(Ecore_Wl2_Window *window, int id); */ EAPI void ecore_wl2_display_terminate(Ecore_Wl2_Display *display); -/** - * Set a specific cursor on a given seat - * - * @brief This function will try to find a matching cursor inside the existing - * cursor theme and set the pointer for the specified seat to be - * the specified cursor - * - * @param input The seat to set the cursor on - * @param cursor The name of the cursor to try and set - * - * @ingroup Ecore_Wl2_Input_Group - * @since 1.20 - */ -EAPI void ecore_wl2_input_cursor_from_name_set(Ecore_Wl2_Input *input, const char *cursor); - # undef EAPI # define EAPI diff --git a/src/lib/ecore_wl2/ecore_wl2_private.h b/src/lib/ecore_wl2/ecore_wl2_private.h index 5178e8f3ea..0f8b7ffc09 100644 --- a/src/lib/ecore_wl2/ecore_wl2_private.h +++ b/src/lib/ecore_wl2/ecore_wl2_private.h @@ -508,6 +508,7 @@ struct _Ecore_Wl2_Input double rate, delay; Eina_Bool enabled : 1; Eina_Bool repeating : 1; + Eina_Bool changed : 1; } repeat; struct diff --git a/src/lib/edje/edje_calc.c b/src/lib/edje/edje_calc.c index cad8472e1e..84d30d0fac 100644 --- a/src/lib/edje/edje_calc.c +++ b/src/lib/edje/edje_calc.c @@ -552,7 +552,7 @@ _edje_image_find(Evas_Object *obj, Edje *ed, Edje_Real_Part_Set **eps, Edje_Image_Directory_Set_Entry *entry; Edje_Image_Directory_Set *set = NULL; Eina_List *l; - int w = 0, h = 0, id; + int w = 0, h = 0, id, maxw = 0, maxh = 0; if (!st && !imid) return -1; if (st && !st->image.set) return st->image.id; @@ -581,8 +581,15 @@ _edje_image_find(Evas_Object *obj, Edje *ed, Edje_Real_Part_Set **eps, if (!set) set = ed->file->image_dir->sets + id; + if (set->entries) + evas_image_max_size_get(evas_object_evas_get(obj), &maxw, &maxh); EINA_LIST_FOREACH(set->entries, l, entry) { + // skip images that exceed max size + if ((maxw > 0) && (maxh > 0) && + (entry->size.w > 0) && (entry->size.h > 0) && + ((w > entry->size.w) || (h > entry->size.h))) + continue; if ((entry->size.min.w <= w) && (w <= entry->size.max.w)) { if ((entry->size.min.h <= h) && (h <= entry->size.max.h)) diff --git a/src/lib/edje/edje_data.c b/src/lib/edje/edje_data.c index 24619f67c9..41f73ab410 100644 --- a/src/lib/edje/edje_data.c +++ b/src/lib/edje/edje_data.c @@ -399,6 +399,8 @@ _edje_edd_init(void) eet_data_descriptor_file_new(&eddc); EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "name", name, EET_T_STRING); EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "id", id, EET_T_INT); + EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "w", size.w, EET_T_INT); + EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "h", size.h, EET_T_INT); EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "min.w", size.min.w, EET_T_INT); EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "min.h", size.min.h, EET_T_INT); EET_DATA_DESCRIPTOR_ADD_BASIC(_edje_edd_edje_image_directory_set_entry, Edje_Image_Directory_Set_Entry, "max.w", size.max.w, EET_T_INT); diff --git a/src/lib/eina/Eina.h b/src/lib/eina/Eina.h index bbf3161929..9e3345e432 100644 --- a/src/lib/eina/Eina.h +++ b/src/lib/eina/Eina.h @@ -212,6 +212,7 @@ extern "C" { #include <eina_main.h> #include <eina_fp.h> #include <eina_rectangle.h> +#include <eina_range.h> #include <eina_clist.h> #include <eina_inlist.h> #include <eina_file.h> diff --git a/src/lib/eina/eina_inline_range.x b/src/lib/eina/eina_inline_range.x new file mode 100644 index 0000000000..b5af9d7226 --- /dev/null +++ b/src/lib/eina/eina_inline_range.x @@ -0,0 +1,82 @@ +/* EINA - EFL data type library + * Copyright (C) 2020 Ali Alzyod + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; + * if not, see <http://www.gnu.org/licenses/>. + */ +#ifndef EINA_INLINE_RANGE_H_ +#define EINA_INLINE_RANGE_H_ + +/*============================================================================* + * API * + *============================================================================*/ + +static inline size_t eina_range_end(const Eina_Range *range) +{ + if (range) return range->start + range->length; + return 0; +} + +static inline Eina_Range eina_range_intersect(const Eina_Range *range, const Eina_Range *range2) +{ + Eina_Range ret_range = EINA_RANGE_EMPTY(); + size_t min, max; + + if (!range || !range2) + return ret_range; + + min = MAX(range->start, range2->start); + max = MIN(range->start + range->length, range2->start + range2->length); + + if (max > min) + { + ret_range = eina_range_from_to(min, max); + } + + return ret_range; +} + +static inline Eina_Range eina_range_union(const Eina_Range *range, const Eina_Range *range2) +{ + size_t min, max; + + if (!range || !range2) + return EINA_RANGE_EMPTY(); + + min = MIN(range->start, range2->start); + max = MAX(range->start + range->length, range2->start + range2->length); + + return eina_range_from_to(min, max); +} + +static inline Eina_Bool eina_range_contains(const Eina_Range *range, size_t value) +{ + if (!range) return EINA_FALSE; + + return value >= range->start && value < (range->start + range->length); +} + +static inline Eina_Bool eina_range_equal(const Eina_Range *range, const Eina_Range *range2) +{ + if (!range || !range2) return EINA_FALSE; + return (range->start == range2->start && range->length == range2->length); +} + +static inline Eina_Range eina_range_from_to(size_t min, size_t max) +{ + if (min < max) return EINA_RANGE(min, max - min); + return EINA_RANGE(max, min - max);; +} + +#endif // EINA_INLINE_RANGE_H_
\ No newline at end of file diff --git a/src/lib/eina/eina_range.h b/src/lib/eina/eina_range.h new file mode 100644 index 0000000000..b5ffac92f1 --- /dev/null +++ b/src/lib/eina/eina_range.h @@ -0,0 +1,116 @@ +/* EINA - EFL data type library + * Copyright (C) 2020 Ali Alzyod + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; + * if not, see <http://www.gnu.org/licenses/>. + */ + +#ifndef EINA_RANGE_H_ +#define EINA_RANGE_H_ + +#include "eina_types.h" + +#include "eina_cpu.h" + +#define EINA_RANGE(start, length) ((Eina_Range) { (start), (length) }) +#define EINA_RANGE_FROM_TO(from, to) ((Eina_Range) { MIN((from),(to)), ABS((to) - (from)) }) +#define EINA_RANGE_ZERO() EINA_RANGE(0, 0) +#define EINA_RANGE_EMPTY() ((Eina_Range) EINA_RANGE_ZERO()) + +/** @brief A Int range */ +typedef struct _Eina_Range +{ + size_t start; + size_t length; +} Eina_Range; + + +/** + * @brief convenience macro for comparing two Eina_Range structs + * @param[in] a An Eina_Range + * @param[in] b An Eina_Range + * @return 1 if the structs are equal, 0 if they are not + * @since 1.24 + */ +#define EINA_RANGE_EQ(a, b) \ + (((a).start == (b).start) && ((a).length == (b).length)) + +/** + * @brief Get end value in range (not included in range). + * + * @param[in] range The Range. + * @return The sum of end and length of the range. + * + * @since 1.24 + * */ +static inline size_t eina_range_end(const Eina_Range *range); + +/** + * @brief Intersection between two ranges. + * + * @param[in] range The first range. + * @param[in] range2 The second range. + * @return The intersection between two ranges, If ranges do not intersect return length will be 0. + * + * @since 1.24 + * */ +static inline Eina_Range eina_range_intersect(const Eina_Range *range, const Eina_Range *range2); + + +/** + * @brief Union between two ranges. + * + * @param[in] range The first range. + * @param[in] range2 The second range. + * @return The union between two ranges. + * + * @since 1.24 + * */ +static inline Eina_Range eina_range_union(const Eina_Range *range, const Eina_Range *range2); + +/** + * @brief Check if value is set in a range. + * + * @param[in] range The range. + * @return Wither value set within range. + * + * @since 1.24 + * */ +static inline Eina_Bool eina_range_contains(const Eina_Range *range, size_t value); + +/** + * @brief Check if two ranges are equal. + * + * @param[in] range The first range. + * @param[in] range2 The second range. + * @return Wither two ranges are equal. + * + * @since 1.24 + * */ +static inline Eina_Bool eina_range_equal(const Eina_Range *range, const Eina_Range *range2); + +/** + * @brief Check if two ranges are equal. + * + * @param[in] min The min value in range. + * @param[in] max The max value in range. + * @return range. + * + * @since 1.24 + * */ +static inline Eina_Range eina_range_from_to(size_t min, size_t max); + +#include "eina_inline_range.x" + +#endif /*EINA_RANGE_H_*/ diff --git a/src/lib/eina/meson.build b/src/lib/eina/meson.build index 7866323742..97e1669c4f 100644 --- a/src/lib/eina/meson.build +++ b/src/lib/eina/meson.build @@ -32,6 +32,7 @@ public_sub_headers = [ 'eina_mempool.h', 'eina_module.h', 'eina_rectangle.h', +'eina_range.h', 'eina_types.h', 'eina_array.h', 'eina_counter.h', @@ -51,6 +52,7 @@ public_sub_headers = [ 'eina_inline_rbtree.x', 'eina_inline_mempool.x', 'eina_inline_rectangle.x', +'eina_inline_range.x', 'eina_inline_trash.x', 'eina_thread.h', 'eina_trash.h', diff --git a/src/lib/elementary/efl_ui_image.c b/src/lib/elementary/efl_ui_image.c index 1f6ba219d1..1de73161c5 100644 --- a/src/lib/elementary/efl_ui_image.c +++ b/src/lib/elementary/efl_ui_image.c @@ -999,6 +999,7 @@ _efl_ui_image_smart_internal_file_set(Eo *obj, Efl_Ui_Image_Data *sd) const Eina_File *f; const char *key; const char *file = efl_file_get(obj); + efl_file_unload(obj); if (eina_str_has_extension(file, ".edj")) return _efl_ui_image_edje_file_set(obj); diff --git a/src/lib/eo/eina_types.eot b/src/lib/eo/eina_types.eot index 4cb8e9347d..d4033e26aa 100644 --- a/src/lib/eo/eina_types.eot +++ b/src/lib/eo/eina_types.eot @@ -60,6 +60,12 @@ struct @extern Eina.Matrix3 { zz: double; [[ZZ matrix value]] } +struct @extern @beta Eina.Range { + [[A range sequence of values.]] + start: size; [[Start of the range.]] + length: size; [[Length of the range.]] +} + type @extern Eina.Unicode: uint32; [[Eina unicode type. @since 1.24]] struct @extern @beta Eina.File_Direct_Info; [[Eina file direct information data structure]] diff --git a/src/lib/evas/canvas/evas_object_box.c b/src/lib/evas/canvas/evas_object_box.c index 7a7173eb25..7853ee3e10 100644 --- a/src/lib/evas/canvas/evas_object_box.c +++ b/src/lib/evas/canvas/evas_object_box.c @@ -412,18 +412,16 @@ _evas_box_efl_canvas_group_group_add(Eo *eo_obj, Evas_Object_Box_Data *priv) EOLIAN static void _evas_box_efl_canvas_group_group_del(Eo *o, Evas_Object_Box_Data *priv) { - Eina_List *l; - - l = priv->children; - while (l) + while (priv->children) { - Evas_Object_Box_Option *opt = l->data; + Evas_Object_Box_Option *opt = eina_list_data_get(priv->children); _evas_object_box_child_callbacks_unregister(opt->obj, o); evas_obj_box_internal_option_free(o, opt); - l = eina_list_remove_list(l, l); + priv->children = eina_list_remove_list(priv->children, priv->children); } + if (priv->layout.data && priv->layout.free_data) priv->layout.free_data(priv->layout.data); diff --git a/src/tests/ecore_wl2/ecore_wl2_test_input.c b/src/tests/ecore_wl2/ecore_wl2_test_input.c index 3c0330a3c8..2802ee6c00 100644 --- a/src/tests/ecore_wl2/ecore_wl2_test_input.c +++ b/src/tests/ecore_wl2/ecore_wl2_test_input.c @@ -197,6 +197,36 @@ EFL_START_TEST(wl2_input_pointer_xy) } EFL_END_TEST +EFL_START_TEST(wl2_input_keyboard_repeat) +{ + Ecore_Wl2_Display *disp; + Ecore_Wl2_Input *input; + Eina_Iterator *itr; + + disp = _display_connect(); + ck_assert(disp != NULL); + + itr = ecore_wl2_display_inputs_get(disp); + ck_assert(itr != NULL); + + EINA_ITERATOR_FOREACH(itr, input) + { + if (ecore_wl2_input_seat_capabilities_get(input) == + ECORE_WL2_SEAT_CAPABILITIES_KEYBOARD) + { + double rate = 0.0, delay = 0.0; + + ecore_wl2_input_keyboard_repeat_set(input, 2.0, 2.0); + ecore_wl2_input_keyboard_repeat_get(input, &rate, &delay); + ck_assert_double_ne(rate, 2.0); + ck_assert_double_ne(delay, 2.0); + } + } + + eina_iterator_free(itr); +} +EFL_END_TEST + void ecore_wl2_test_input(TCase *tc) { @@ -209,5 +239,6 @@ ecore_wl2_test_input(TCase *tc) tcase_add_test(tc, wl2_input_name_get); tcase_add_test(tc, wl2_input_seat_capabilities); tcase_add_test(tc, wl2_input_pointer_xy); + tcase_add_test(tc, wl2_input_keyboard_repeat); } } diff --git a/src/tests/ecore_wl2/ecore_wl2_test_window.c b/src/tests/ecore_wl2/ecore_wl2_test_window.c index b166b4ba4e..ab60ac2077 100644 --- a/src/tests/ecore_wl2/ecore_wl2_test_window.c +++ b/src/tests/ecore_wl2/ecore_wl2_test_window.c @@ -883,6 +883,57 @@ EFL_START_TEST(wl2_window_update_begin) } EFL_END_TEST +EFL_START_TEST(wl2_window_move) +{ + Ecore_Wl2_Display *disp; + Ecore_Wl2_Window *win; + + disp = _display_connect(); + ck_assert(disp != NULL); + + win = _window_create(disp); + ck_assert(win != NULL); + + //FIXME: Need some discussion about how to validate this API in TC. + ecore_wl2_window_move(NULL, NULL); + ecore_wl2_window_move(win, NULL); +} +EFL_END_TEST + +EFL_START_TEST(wl2_window_resize) +{ + Ecore_Wl2_Display *disp; + Ecore_Wl2_Window *win; + + disp = _display_connect(); + ck_assert(disp != NULL); + + win = _window_create(disp); + ck_assert(win != NULL); + + //FIXME: Need some discussion about how to validate this API in TC. + ecore_wl2_window_resize(NULL, NULL, 0); + ecore_wl2_window_resize(win, NULL, 0); +} +EFL_END_TEST + +EFL_START_TEST(wl2_window_resizing_get) +{ + Ecore_Wl2_Display *disp; + Ecore_Wl2_Window *win; + Eina_Bool ret; + + disp = _display_connect(); + ck_assert(disp != NULL); + + win = _window_create(disp); + ck_assert(win != NULL); + + ret = ecore_wl2_window_resizing_get(win); + fail_if (ret == EINA_TRUE); +} +EFL_END_TEST + void ecore_wl2_test_window(TCase *tc) { @@ -922,5 +973,8 @@ ecore_wl2_test_window(TCase *tc) tcase_add_test(tc, wl2_window_input_region); tcase_add_test(tc, wl2_window_opaque_region); tcase_add_test(tc, wl2_window_popup_input); + tcase_add_test(tc, wl2_window_move); + tcase_add_test(tc, wl2_window_resize); + tcase_add_test(tc, wl2_window_resizing_get); } } 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 class TestCsharpProperties { + + private class MyObject : Dummy.TestObject + { + public MyObject(Efl.Object parent = null) : base(parent) + { + } + private MyObject(ConstructingHandle ch) : base(ch) + { + } + } public static void test_csharp_properties() { var obj = new Dummy.TestObject(); @@ -428,6 +438,28 @@ class TestCsharpProperties iface.Dispose(); } + public static void test_iface_value_property() + { + var obj = new Dummy.TestObject(); + var prop = new MyObject(); + + obj.IfaceValueProp = prop; + Test.AssertEquals(obj.IfaceValueProp, prop); + + obj.Dispose(); + prop.Dispose(); + } + + public static void test_iface_value_from_c() + { + var obj = new Dummy.TestObject(); + + obj.SetIfaceKlassProp(typeof(MyObject)); + Test.AssertEquals(obj.IfaceValueFromC.GetType(), typeof(MyObject)); + + obj.Dispose(); + } + public static void test_csharp_multi_valued_prop() { 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 int prop1; int prop2; Eo *hidden_object; + Dummy_Test_Iface *iface_value_prop; + Efl_Class *iface_klass; // Containers passed to C# as iterator/accessors Eina_Array *out_array; @@ -4784,6 +4786,26 @@ Eo *_dummy_test_object_hidden_object_get(EINA_UNUSED const Eo *obj, Dummy_Test_O return pd->hidden_object; } +Dummy_Test_Iface *_dummy_test_object_iface_value_prop_get(EINA_UNUSED const Eo *obj, Dummy_Test_Object_Data *pd) +{ + return pd->iface_value_prop; +} + +void _dummy_test_object_iface_value_prop_set(EINA_UNUSED Eo *obj, Dummy_Test_Object_Data *pd, Dummy_Test_Iface *prop) +{ + pd->iface_value_prop = prop; +} + +void _dummy_test_object_iface_klass_prop_set(EINA_UNUSED Eo *obj, Dummy_Test_Object_Data *pd, Efl_Class *klass) +{ + pd->iface_klass = klass; +} + +Dummy_Test_Iface *_dummy_test_object_iface_value_from_c_get(const Eo *obj, Dummy_Test_Object_Data *pd) +{ + return efl_add(pd->iface_klass, (Eo*)obj); +} + // Inherit int _dummy_inherit_helper_receive_dummy_and_call_int_out(Dummy_Test_Object *x) { 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 { obj: Efl.Object; } } + @property iface_value_prop { + values { + prop: Dummy.Test_Iface; + } + } + @property iface_klass_prop { + set {} + values { + klass: Efl.Class; + } + } + @property iface_value_from_c { + get {} + values { + prop: Dummy.Test_Iface; + } + } } implements { Efl.Object.constructor; diff --git a/src/tests/eina/eina_suite.c b/src/tests/eina/eina_suite.c index dfa2bd1e5f..45316bd462 100644 --- a/src/tests/eina/eina_suite.c +++ b/src/tests/eina/eina_suite.c @@ -57,6 +57,7 @@ static const Efl_Test_Case etc[] = { { "Benchmark", eina_test_benchmark }, { "Mempool", eina_test_mempool }, { "Rectangle", eina_test_rectangle }, + { "Range", eina_test_range }, { "MatrixSparse", eina_test_matrixsparse }, { "Tiler", eina_test_tiler }, { "Strbuf", eina_test_strbuf }, diff --git a/src/tests/eina/eina_suite.h b/src/tests/eina/eina_suite.h index 5e7a1bf30f..102de63193 100644 --- a/src/tests/eina/eina_suite.h +++ b/src/tests/eina/eina_suite.h @@ -45,6 +45,7 @@ void eina_test_file(TCase *tc); void eina_test_benchmark(TCase *tc); void eina_test_mempool(TCase *tc); void eina_test_rectangle(TCase *tc); +void eina_test_range(TCase *tc); void eina_test_matrixsparse(TCase *tc); void eina_test_tiler(TCase *tc); void eina_test_strbuf(TCase *tc); diff --git a/src/tests/eina/eina_test_range.c b/src/tests/eina/eina_test_range.c new file mode 100644 index 0000000000..a1f84b8a00 --- /dev/null +++ b/src/tests/eina/eina_test_range.c @@ -0,0 +1,72 @@ +/* EINA - EFL data type library + * Copyright (C) 2020 Ali Alzyod + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; + * if not, see <http://www.gnu.org/licenses/>. + */ + +#ifdef HAVE_CONFIG_H +# include "config.h" +#endif + +#include <stdio.h> + +#include <Eina.h> + +#include "eina_suite.h" + +EFL_START_TEST(eina_range_intersect_union_test) +{ + Eina_Range r1 = EINA_RANGE(0, 10); + Eina_Range r2 = EINA_RANGE(5, 15); + + Eina_Range r_intersect = eina_range_intersect(&r1, &r2); + ck_assert_uint_eq(r_intersect.start, 5); + ck_assert_uint_eq(r_intersect.length, 5); + + Eina_Range r_union = eina_range_union(&r1, &r2); + ck_assert_uint_eq(r_union.start, 0); + ck_assert_uint_eq(r_union.length, 20); +} +EFL_END_TEST + +EFL_START_TEST(eina_range_contains_test) +{ + Eina_Range r1 = EINA_RANGE(0, 10); + + ck_assert(eina_range_contains(&r1,0)); + ck_assert(eina_range_contains(&r1,9)); + ck_assert(!eina_range_contains(&r1,10)); +} +EFL_END_TEST + +EFL_START_TEST(eina_range_equal_test) +{ + Eina_Range r1 = EINA_RANGE(0, 10); + Eina_Range r2 = EINA_RANGE(0, 10); + Eina_Range r3 = EINA_RANGE(0, 9); + + ck_assert(eina_range_equal(&r1, &r2)); + ck_assert(!eina_range_equal(&r1, &r3)); +} +EFL_END_TEST + + +void +eina_test_range(TCase *tc) +{ + tcase_add_test(tc, eina_range_intersect_union_test); + tcase_add_test(tc, eina_range_contains_test); + tcase_add_test(tc, eina_range_equal_test); +} diff --git a/src/tests/eina/meson.build b/src/tests/eina/meson.build index b6ba688e8b..f755be4c2a 100644 --- a/src/tests/eina/meson.build +++ b/src/tests/eina/meson.build @@ -29,6 +29,7 @@ eina_test_src = files( 'eina_test_benchmark.c', 'eina_test_mempool.c', 'eina_test_rectangle.c', +'eina_test_range.c', 'eina_test_list.c', 'eina_test_matrixsparse.c', 'eina_test_tiler.c', |