mirror of
https://github.com/brl/mutter.git
synced 2024-12-28 05:42:14 +00:00
tests: Introduce and use a custom test shell
Except for the tests that launches `mutter`, use a custom shell implementation. It's roughly a copy of default.c with some cleanups on top. A custom shell allows for a bit more freedom when doing testy things. Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3185>
This commit is contained in:
parent
be3bca01a7
commit
524c9aa458
@ -57,7 +57,6 @@ test_env.set('G_TEST_SRCDIR', meson.current_source_dir())
|
|||||||
test_env.set('G_TEST_BUILDDIR', meson.current_build_dir())
|
test_env.set('G_TEST_BUILDDIR', meson.current_build_dir())
|
||||||
test_env.set('G_ENABLE_DIAGNOSTIC', '0')
|
test_env.set('G_ENABLE_DIAGNOSTIC', '0')
|
||||||
test_env.set('CLUTTER_ENABLE_DIAGNOSTIC', '0')
|
test_env.set('CLUTTER_ENABLE_DIAGNOSTIC', '0')
|
||||||
test_env.set('MUTTER_TEST_PLUGIN_PATH', '@0@'.format(default_plugin.full_path()))
|
|
||||||
|
|
||||||
foreach test : clutter_conform_tests
|
foreach test : clutter_conform_tests
|
||||||
test_executable = executable('@0@'.format(test),
|
test_executable = executable('@0@'.format(test),
|
||||||
|
@ -70,7 +70,6 @@ test_env = environment()
|
|||||||
test_env.set('G_TEST_SRCDIR', meson.current_source_dir())
|
test_env.set('G_TEST_SRCDIR', meson.current_source_dir())
|
||||||
test_env.set('G_TEST_BUILDDIR', meson.current_build_dir())
|
test_env.set('G_TEST_BUILDDIR', meson.current_build_dir())
|
||||||
test_env.set('G_ENABLE_DIAGNOSTIC', '0')
|
test_env.set('G_ENABLE_DIAGNOSTIC', '0')
|
||||||
test_env.set('MUTTER_TEST_PLUGIN_PATH', '@0@'.format(default_plugin.full_path()))
|
|
||||||
|
|
||||||
cogl_test_variants = [ 'gl3', 'gles2' ]
|
cogl_test_variants = [ 'gl3', 'gles2' ]
|
||||||
|
|
||||||
|
@ -14,7 +14,6 @@ test_env = environment()
|
|||||||
test_env.set('G_TEST_SRCDIR', meson.current_source_dir())
|
test_env.set('G_TEST_SRCDIR', meson.current_source_dir())
|
||||||
test_env.set('G_TEST_BUILDDIR', meson.current_build_dir())
|
test_env.set('G_TEST_BUILDDIR', meson.current_build_dir())
|
||||||
test_env.set('G_ENABLE_DIAGNOSTIC', '0')
|
test_env.set('G_ENABLE_DIAGNOSTIC', '0')
|
||||||
test_env.set('MUTTER_TEST_PLUGIN_PATH', '@0@'.format(default_plugin.full_path()))
|
|
||||||
|
|
||||||
foreach unit_test: cogl_unit_tests
|
foreach unit_test: cogl_unit_tests
|
||||||
test_name = 'cogl-' + unit_test[0]
|
test_name = 'cogl-' + unit_test[0]
|
||||||
|
@ -13,6 +13,8 @@ mutter_test_sources = [
|
|||||||
'meta-sensors-proxy-mock.c',
|
'meta-sensors-proxy-mock.c',
|
||||||
'meta-sensors-proxy-mock.h',
|
'meta-sensors-proxy-mock.h',
|
||||||
'meta-test-monitor.c',
|
'meta-test-monitor.c',
|
||||||
|
'meta-test-shell.c',
|
||||||
|
'meta-test-shell.h',
|
||||||
'meta-test-utils.c',
|
'meta-test-utils.c',
|
||||||
'meta-test-utils.h',
|
'meta-test-utils.h',
|
||||||
]
|
]
|
||||||
|
@ -29,6 +29,7 @@
|
|||||||
|
|
||||||
#include "core/meta-context-private.h"
|
#include "core/meta-context-private.h"
|
||||||
#include "tests/meta-backend-test.h"
|
#include "tests/meta-backend-test.h"
|
||||||
|
#include "tests/meta-test-shell.h"
|
||||||
#include "tests/meta-test-utils-private.h"
|
#include "tests/meta-test-utils-private.h"
|
||||||
#include "wayland/meta-wayland.h"
|
#include "wayland/meta-wayland.h"
|
||||||
#include "wayland/meta-xwayland.h"
|
#include "wayland/meta-xwayland.h"
|
||||||
@ -84,7 +85,6 @@ meta_context_test_configure (MetaContext *context,
|
|||||||
meta_context_test_get_instance_private (context_test);
|
meta_context_test_get_instance_private (context_test);
|
||||||
MetaContextClass *context_class =
|
MetaContextClass *context_class =
|
||||||
META_CONTEXT_CLASS (meta_context_test_parent_class);
|
META_CONTEXT_CLASS (meta_context_test_parent_class);
|
||||||
const char *plugin_name;
|
|
||||||
|
|
||||||
g_test_init (argc, argv, NULL);
|
g_test_init (argc, argv, NULL);
|
||||||
|
|
||||||
@ -101,10 +101,7 @@ meta_context_test_configure (MetaContext *context,
|
|||||||
meta_xwayland_override_display_number (512);
|
meta_xwayland_override_display_number (512);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
plugin_name = g_getenv ("MUTTER_TEST_PLUGIN_PATH");
|
meta_context_set_plugin_gtype (context, META_TYPE_TEST_SHELL);
|
||||||
if (!plugin_name)
|
|
||||||
plugin_name = "libdefault";
|
|
||||||
meta_context_set_plugin_name (context, plugin_name);
|
|
||||||
|
|
||||||
ensure_gsettings_memory_backend ();
|
ensure_gsettings_memory_backend ();
|
||||||
|
|
||||||
|
769
src/tests/meta-test-shell.c
Normal file
769
src/tests/meta-test-shell.c
Normal file
@ -0,0 +1,769 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2008 Intel Corp.
|
||||||
|
* Copyright (c) 2023 Red Hat
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program 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
|
||||||
|
* General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "config.h"
|
||||||
|
|
||||||
|
#include "tests/meta-test-shell.h"
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "clutter/clutter.h"
|
||||||
|
#include "meta/meta-backend.h"
|
||||||
|
#include "meta/meta-background-actor.h"
|
||||||
|
#include "meta/meta-background-content.h"
|
||||||
|
#include "meta/meta-background-group.h"
|
||||||
|
#include "meta/meta-context.h"
|
||||||
|
#include "meta/meta-monitor-manager.h"
|
||||||
|
#include "meta/meta-plugin.h"
|
||||||
|
#include "meta/util.h"
|
||||||
|
#include "meta/window.h"
|
||||||
|
|
||||||
|
typedef enum
|
||||||
|
{
|
||||||
|
ANIMATION_DESTROY,
|
||||||
|
ANIMATION_MINIMIZE,
|
||||||
|
ANIMATION_MAP,
|
||||||
|
ANIMATION_SWITCH,
|
||||||
|
} Animation;
|
||||||
|
|
||||||
|
static unsigned int animation_durations[] = {
|
||||||
|
100, /* destroy */
|
||||||
|
250, /* minimize */
|
||||||
|
250, /* map */
|
||||||
|
500, /* switch */
|
||||||
|
};
|
||||||
|
|
||||||
|
#define ACTOR_DATA_KEY "-test-shell-actor-data"
|
||||||
|
#define DISPLAY_TILE_PREVIEW_DATA_KEY "-test-shell-display-tile-preview-data"
|
||||||
|
|
||||||
|
struct _MetaTestShell
|
||||||
|
{
|
||||||
|
MetaPlugin parent;
|
||||||
|
|
||||||
|
ClutterTimeline *switch_workspace1_timeline;
|
||||||
|
ClutterTimeline *switch_workspace2_timeline;
|
||||||
|
ClutterActor *desktop1;
|
||||||
|
ClutterActor *desktop2;
|
||||||
|
|
||||||
|
ClutterActor *background_group;
|
||||||
|
|
||||||
|
MetaPluginInfo info;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct _ActorPrivate
|
||||||
|
{
|
||||||
|
ClutterActor *orig_parent;
|
||||||
|
|
||||||
|
ClutterTimeline *minimize_timeline;
|
||||||
|
ClutterTimeline *destroy_timeline;
|
||||||
|
ClutterTimeline *map_timeline;
|
||||||
|
} ActorPrivate;
|
||||||
|
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
ClutterActor *actor;
|
||||||
|
MetaPlugin *plugin;
|
||||||
|
gpointer effect_data;
|
||||||
|
} EffectCompleteData;
|
||||||
|
|
||||||
|
typedef struct _DisplayTilePreview
|
||||||
|
{
|
||||||
|
ClutterActor *actor;
|
||||||
|
|
||||||
|
MetaRectangle tile_rect;
|
||||||
|
} DisplayTilePreview;
|
||||||
|
|
||||||
|
G_DEFINE_TYPE (MetaTestShell, meta_test_shell, META_TYPE_PLUGIN)
|
||||||
|
|
||||||
|
static GQuark actor_data_quark = 0;
|
||||||
|
static GQuark display_tile_preview_data_quark = 0;
|
||||||
|
|
||||||
|
static void
|
||||||
|
free_actor_private (gpointer data)
|
||||||
|
{
|
||||||
|
g_free (data);
|
||||||
|
}
|
||||||
|
|
||||||
|
static ActorPrivate *
|
||||||
|
get_actor_private (MetaWindowActor *actor)
|
||||||
|
{
|
||||||
|
ActorPrivate *actor_priv = g_object_get_qdata (G_OBJECT (actor), actor_data_quark);
|
||||||
|
|
||||||
|
if (G_UNLIKELY (actor_data_quark == 0))
|
||||||
|
actor_data_quark = g_quark_from_static_string (ACTOR_DATA_KEY);
|
||||||
|
|
||||||
|
if (G_UNLIKELY (!actor_priv))
|
||||||
|
{
|
||||||
|
actor_priv = g_new0 (ActorPrivate, 1);
|
||||||
|
|
||||||
|
g_object_set_qdata_full (G_OBJECT (actor),
|
||||||
|
actor_data_quark, actor_priv,
|
||||||
|
free_actor_private);
|
||||||
|
}
|
||||||
|
|
||||||
|
return actor_priv;
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
is_animations_disabled (void)
|
||||||
|
{
|
||||||
|
static gboolean is_animations_disabled_set;
|
||||||
|
static gboolean is_animations_disabled;
|
||||||
|
|
||||||
|
if (!is_animations_disabled_set)
|
||||||
|
{
|
||||||
|
if (g_strcmp0 (getenv ("MUTTER_DEBUG_DISABLE_ANIMATIONS"), "1") == 0)
|
||||||
|
is_animations_disabled = TRUE;
|
||||||
|
else
|
||||||
|
is_animations_disabled = FALSE;
|
||||||
|
|
||||||
|
is_animations_disabled_set = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return is_animations_disabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
static unsigned int
|
||||||
|
get_animation_duration (Animation animation)
|
||||||
|
{
|
||||||
|
if (is_animations_disabled ())
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
return animation_durations[animation];
|
||||||
|
}
|
||||||
|
|
||||||
|
static ClutterTimeline *
|
||||||
|
actor_animate (ClutterActor *actor,
|
||||||
|
ClutterAnimationMode mode,
|
||||||
|
Animation animation,
|
||||||
|
const char *first_property,
|
||||||
|
...)
|
||||||
|
{
|
||||||
|
va_list args;
|
||||||
|
ClutterTransition *transition;
|
||||||
|
|
||||||
|
clutter_actor_save_easing_state (actor);
|
||||||
|
clutter_actor_set_easing_mode (actor, mode);
|
||||||
|
clutter_actor_set_easing_duration (actor, get_animation_duration (animation));
|
||||||
|
|
||||||
|
va_start (args, first_property);
|
||||||
|
g_object_set_valist (G_OBJECT (actor), first_property, args);
|
||||||
|
va_end (args);
|
||||||
|
|
||||||
|
transition = clutter_actor_get_transition (actor, first_property);
|
||||||
|
|
||||||
|
clutter_actor_restore_easing_state (actor);
|
||||||
|
|
||||||
|
return CLUTTER_TIMELINE (transition);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
finish_timeline (ClutterTimeline *timeline)
|
||||||
|
{
|
||||||
|
g_object_ref (timeline);
|
||||||
|
clutter_timeline_stop (timeline);
|
||||||
|
g_object_unref (timeline);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
kill_workspace_switch_animation (MetaTestShell *test_shell)
|
||||||
|
{
|
||||||
|
if (test_shell->switch_workspace1_timeline)
|
||||||
|
{
|
||||||
|
g_autoptr (ClutterTimeline) timeline1 = NULL;
|
||||||
|
g_autoptr (ClutterTimeline) timeline2 = NULL;
|
||||||
|
|
||||||
|
timeline1 = g_object_ref (test_shell->switch_workspace1_timeline);
|
||||||
|
timeline2 = g_object_ref (test_shell->switch_workspace2_timeline);
|
||||||
|
|
||||||
|
finish_timeline (timeline1);
|
||||||
|
finish_timeline (timeline2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_switch_workspace_effect_stopped (ClutterTimeline *timeline,
|
||||||
|
gboolean is_finished,
|
||||||
|
gpointer data)
|
||||||
|
{
|
||||||
|
MetaPlugin *plugin = META_PLUGIN (data);
|
||||||
|
MetaTestShell *test_shell = META_TEST_SHELL (plugin);
|
||||||
|
MetaDisplay *display = meta_plugin_get_display (plugin);
|
||||||
|
GList *l = meta_get_window_actors (display);
|
||||||
|
|
||||||
|
while (l)
|
||||||
|
{
|
||||||
|
ClutterActor *a = l->data;
|
||||||
|
MetaWindowActor *window_actor = META_WINDOW_ACTOR (a);
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
|
||||||
|
if (actor_priv->orig_parent)
|
||||||
|
{
|
||||||
|
g_object_ref (a);
|
||||||
|
clutter_actor_remove_child (clutter_actor_get_parent (a), a);
|
||||||
|
clutter_actor_add_child (actor_priv->orig_parent, a);
|
||||||
|
g_object_unref (a);
|
||||||
|
actor_priv->orig_parent = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
l = l->next;
|
||||||
|
}
|
||||||
|
|
||||||
|
clutter_actor_destroy (test_shell->desktop1);
|
||||||
|
clutter_actor_destroy (test_shell->desktop2);
|
||||||
|
|
||||||
|
test_shell->switch_workspace1_timeline = NULL;
|
||||||
|
test_shell->switch_workspace2_timeline = NULL;
|
||||||
|
test_shell->desktop1 = NULL;
|
||||||
|
test_shell->desktop2 = NULL;
|
||||||
|
|
||||||
|
meta_plugin_switch_workspace_completed (plugin);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_monitors_changed (MetaMonitorManager *monitor_manager,
|
||||||
|
MetaPlugin *plugin)
|
||||||
|
{
|
||||||
|
MetaTestShell *test_shell = META_TEST_SHELL (plugin);
|
||||||
|
MetaDisplay *display = meta_plugin_get_display (plugin);
|
||||||
|
GRand *rand;
|
||||||
|
int i, n;
|
||||||
|
|
||||||
|
rand = g_rand_new_with_seed (123456);
|
||||||
|
clutter_actor_destroy_all_children (test_shell->background_group);
|
||||||
|
|
||||||
|
n = meta_display_get_n_monitors (display);
|
||||||
|
for (i = 0; i < n; i++)
|
||||||
|
{
|
||||||
|
MetaBackgroundContent *background_content;
|
||||||
|
ClutterContent *content;
|
||||||
|
MetaRectangle rect;
|
||||||
|
ClutterActor *background_actor;
|
||||||
|
MetaBackground *background;
|
||||||
|
uint8_t red;
|
||||||
|
uint8_t green;
|
||||||
|
uint8_t blue;
|
||||||
|
ClutterColor color;
|
||||||
|
|
||||||
|
meta_display_get_monitor_geometry (display, i, &rect);
|
||||||
|
|
||||||
|
background_actor = meta_background_actor_new (display, i);
|
||||||
|
content = clutter_actor_get_content (background_actor);
|
||||||
|
background_content = META_BACKGROUND_CONTENT (content);
|
||||||
|
|
||||||
|
clutter_actor_set_position (background_actor, rect.x, rect.y);
|
||||||
|
clutter_actor_set_size (background_actor, rect.width, rect.height);
|
||||||
|
|
||||||
|
blue = g_rand_int_range (rand, 0, 255);
|
||||||
|
green = g_rand_int_range (rand, 0, 255);
|
||||||
|
red = g_rand_int_range (rand, 0, 255);
|
||||||
|
clutter_color_init (&color, red, green, blue, 255);
|
||||||
|
|
||||||
|
background = meta_background_new (display);
|
||||||
|
meta_background_set_color (background, &color);
|
||||||
|
meta_background_content_set_background (background_content, background);
|
||||||
|
g_object_unref (background);
|
||||||
|
|
||||||
|
meta_background_content_set_vignette (background_content, TRUE, 0.5, 0.5);
|
||||||
|
|
||||||
|
clutter_actor_add_child (test_shell->background_group, background_actor);
|
||||||
|
}
|
||||||
|
|
||||||
|
g_rand_free (rand);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
prepare_shutdown (MetaBackend *backend,
|
||||||
|
MetaTestShell *test_shell)
|
||||||
|
{
|
||||||
|
kill_workspace_switch_animation (test_shell);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_start (MetaPlugin *plugin)
|
||||||
|
{
|
||||||
|
MetaTestShell *test_shell = META_TEST_SHELL (plugin);
|
||||||
|
MetaDisplay *display = meta_plugin_get_display (plugin);
|
||||||
|
MetaContext *context = meta_display_get_context (display);
|
||||||
|
MetaBackend *backend = meta_context_get_backend (context);
|
||||||
|
MetaMonitorManager *monitor_manager =
|
||||||
|
meta_backend_get_monitor_manager (backend);
|
||||||
|
|
||||||
|
test_shell->background_group = meta_background_group_new ();
|
||||||
|
clutter_actor_insert_child_below (meta_get_window_group_for_display (display),
|
||||||
|
test_shell->background_group, NULL);
|
||||||
|
|
||||||
|
g_signal_connect (monitor_manager, "monitors-changed",
|
||||||
|
G_CALLBACK (on_monitors_changed), plugin);
|
||||||
|
on_monitors_changed (monitor_manager, plugin);
|
||||||
|
|
||||||
|
g_signal_connect (backend, "prepare-shutdown",
|
||||||
|
G_CALLBACK (prepare_shutdown),
|
||||||
|
test_shell);
|
||||||
|
|
||||||
|
clutter_actor_show (meta_get_stage_for_display (display));
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_switch_workspace (MetaPlugin *plugin,
|
||||||
|
int from,
|
||||||
|
int to,
|
||||||
|
MetaMotionDirection direction)
|
||||||
|
{
|
||||||
|
MetaTestShell *test_shell = META_TEST_SHELL (plugin);
|
||||||
|
MetaDisplay *display;
|
||||||
|
ClutterActor *stage;
|
||||||
|
ClutterActor *workspace1, *workspace2;
|
||||||
|
int screen_width, screen_height;
|
||||||
|
GList *l;
|
||||||
|
|
||||||
|
if (from == to)
|
||||||
|
{
|
||||||
|
meta_plugin_switch_workspace_completed (plugin);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
display = meta_plugin_get_display (plugin);
|
||||||
|
stage = meta_get_stage_for_display (display);
|
||||||
|
|
||||||
|
meta_display_get_size (display,
|
||||||
|
&screen_width,
|
||||||
|
&screen_height);
|
||||||
|
|
||||||
|
workspace1 = clutter_actor_new ();
|
||||||
|
workspace2 = clutter_actor_new ();
|
||||||
|
|
||||||
|
clutter_actor_set_pivot_point (workspace1, 1.0, 1.0);
|
||||||
|
clutter_actor_set_size (workspace1,
|
||||||
|
screen_width,
|
||||||
|
screen_height);
|
||||||
|
clutter_actor_set_size (workspace2,
|
||||||
|
screen_width,
|
||||||
|
screen_height);
|
||||||
|
|
||||||
|
clutter_actor_set_scale (workspace1, 0.0, 0.0);
|
||||||
|
|
||||||
|
clutter_actor_add_child (stage, workspace1);
|
||||||
|
clutter_actor_add_child (stage, workspace2);
|
||||||
|
|
||||||
|
for (l = g_list_last (meta_get_window_actors (display)); l; l = l->prev)
|
||||||
|
{
|
||||||
|
MetaWindowActor *window_actor = l->data;
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
ClutterActor *actor = CLUTTER_ACTOR (window_actor);
|
||||||
|
MetaWindow *window;
|
||||||
|
MetaWorkspace *workspace;
|
||||||
|
int workspace_idx;
|
||||||
|
|
||||||
|
window = meta_window_actor_get_meta_window (window_actor);
|
||||||
|
workspace = meta_window_get_workspace (window);
|
||||||
|
|
||||||
|
if (!workspace)
|
||||||
|
{
|
||||||
|
clutter_actor_hide (actor);
|
||||||
|
actor_priv->orig_parent = NULL;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (meta_window_is_on_all_workspaces (window))
|
||||||
|
{
|
||||||
|
actor_priv->orig_parent = NULL;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
workspace_idx = meta_workspace_index (workspace);
|
||||||
|
|
||||||
|
if (workspace_idx == to || workspace_idx == from)
|
||||||
|
{
|
||||||
|
ClutterActor *parent = workspace_idx == to ? workspace1
|
||||||
|
: workspace2;
|
||||||
|
actor_priv->orig_parent = clutter_actor_get_parent (actor);
|
||||||
|
|
||||||
|
g_object_ref (actor);
|
||||||
|
clutter_actor_remove_child (clutter_actor_get_parent (actor),
|
||||||
|
actor);
|
||||||
|
clutter_actor_add_child (parent, actor);
|
||||||
|
clutter_actor_set_child_below_sibling (parent, actor, NULL);
|
||||||
|
g_object_unref (actor);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
clutter_actor_hide (actor);
|
||||||
|
actor_priv->orig_parent = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
test_shell->desktop1 = workspace1;
|
||||||
|
test_shell->desktop2 = workspace2;
|
||||||
|
|
||||||
|
test_shell->switch_workspace1_timeline =
|
||||||
|
actor_animate (workspace1, CLUTTER_EASE_IN_SINE,
|
||||||
|
ANIMATION_SWITCH,
|
||||||
|
"scale-x", 1.0,
|
||||||
|
"scale-y", 1.0,
|
||||||
|
NULL);
|
||||||
|
g_signal_connect (test_shell->switch_workspace1_timeline,
|
||||||
|
"stopped",
|
||||||
|
G_CALLBACK (on_switch_workspace_effect_stopped),
|
||||||
|
plugin);
|
||||||
|
|
||||||
|
test_shell->switch_workspace2_timeline =
|
||||||
|
actor_animate (workspace2, CLUTTER_EASE_IN_SINE,
|
||||||
|
ANIMATION_SWITCH,
|
||||||
|
"scale-x", 0.0,
|
||||||
|
"scale-y", 0.0,
|
||||||
|
NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_minimize_effect_stopped (ClutterTimeline *timeline,
|
||||||
|
gboolean is_finished,
|
||||||
|
EffectCompleteData *data)
|
||||||
|
{
|
||||||
|
MetaPlugin *plugin = data->plugin;
|
||||||
|
ActorPrivate *actor_priv;
|
||||||
|
MetaWindowActor *window_actor = META_WINDOW_ACTOR (data->actor);
|
||||||
|
double original_scale = *(double *) data->effect_data;
|
||||||
|
|
||||||
|
actor_priv = get_actor_private (META_WINDOW_ACTOR (data->actor));
|
||||||
|
actor_priv->minimize_timeline = NULL;
|
||||||
|
|
||||||
|
clutter_actor_hide (data->actor);
|
||||||
|
clutter_actor_set_scale (data->actor, original_scale, original_scale);
|
||||||
|
|
||||||
|
meta_plugin_minimize_completed (plugin, window_actor);
|
||||||
|
|
||||||
|
g_free (data->effect_data);
|
||||||
|
g_free (data);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_minimize (MetaPlugin *plugin,
|
||||||
|
MetaWindowActor *window_actor)
|
||||||
|
{
|
||||||
|
MetaWindowType type;
|
||||||
|
MetaWindow *window = meta_window_actor_get_meta_window (window_actor);
|
||||||
|
ClutterTimeline *timeline = NULL;
|
||||||
|
ClutterActor *actor = CLUTTER_ACTOR (window_actor);
|
||||||
|
|
||||||
|
type = meta_window_get_window_type (window);
|
||||||
|
|
||||||
|
if (type == META_WINDOW_NORMAL)
|
||||||
|
{
|
||||||
|
timeline = actor_animate (actor,
|
||||||
|
CLUTTER_EASE_IN_SINE,
|
||||||
|
ANIMATION_MINIMIZE,
|
||||||
|
"scale-x", 0.0,
|
||||||
|
"scale-y", 0.0,
|
||||||
|
"x", (double) 0,
|
||||||
|
"y", (double) 0,
|
||||||
|
NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (timeline)
|
||||||
|
{
|
||||||
|
EffectCompleteData *data;
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
double scale_x, scale_y;
|
||||||
|
|
||||||
|
data = g_new0 (EffectCompleteData, 1);
|
||||||
|
actor_priv->minimize_timeline = timeline;
|
||||||
|
data->plugin = plugin;
|
||||||
|
data->actor = actor;
|
||||||
|
data->effect_data = g_new0 (double, 1);
|
||||||
|
clutter_actor_get_scale (actor, &scale_x, &scale_y);
|
||||||
|
g_assert (scale_x == scale_y);
|
||||||
|
*((double *) data->effect_data) = scale_x;
|
||||||
|
g_signal_connect (actor_priv->minimize_timeline, "stopped",
|
||||||
|
G_CALLBACK (on_minimize_effect_stopped),
|
||||||
|
data);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
meta_plugin_minimize_completed (plugin, window_actor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_map_effect_stopped (ClutterTimeline *timeline,
|
||||||
|
gboolean is_finished,
|
||||||
|
EffectCompleteData *data)
|
||||||
|
{
|
||||||
|
MetaPlugin *plugin = data->plugin;
|
||||||
|
MetaWindowActor *window_actor = META_WINDOW_ACTOR (data->actor);
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
|
||||||
|
actor_priv->map_timeline = NULL;
|
||||||
|
|
||||||
|
meta_plugin_map_completed (plugin, window_actor);
|
||||||
|
|
||||||
|
g_free (data);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_map (MetaPlugin *plugin,
|
||||||
|
MetaWindowActor *window_actor)
|
||||||
|
{
|
||||||
|
ClutterActor *actor = CLUTTER_ACTOR (window_actor);
|
||||||
|
MetaWindow *window = meta_window_actor_get_meta_window (window_actor);
|
||||||
|
MetaWindowType type;
|
||||||
|
|
||||||
|
type = meta_window_get_window_type (window);
|
||||||
|
|
||||||
|
if (type == META_WINDOW_NORMAL)
|
||||||
|
{
|
||||||
|
EffectCompleteData *data = g_new0 (EffectCompleteData, 1);
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
|
||||||
|
clutter_actor_set_pivot_point (actor, 0.5, 0.5);
|
||||||
|
clutter_actor_set_opacity (actor, 0);
|
||||||
|
clutter_actor_set_scale (actor, 0.5, 0.5);
|
||||||
|
clutter_actor_show (actor);
|
||||||
|
|
||||||
|
actor_priv->map_timeline = actor_animate (actor,
|
||||||
|
CLUTTER_EASE_OUT_QUAD,
|
||||||
|
ANIMATION_MAP,
|
||||||
|
"opacity", 255,
|
||||||
|
"scale-x", 1.0,
|
||||||
|
"scale-y", 1.0,
|
||||||
|
NULL);
|
||||||
|
if (actor_priv->map_timeline)
|
||||||
|
{
|
||||||
|
data->actor = actor;
|
||||||
|
data->plugin = plugin;
|
||||||
|
g_signal_connect (actor_priv->map_timeline, "stopped",
|
||||||
|
G_CALLBACK (on_map_effect_stopped),
|
||||||
|
data);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
g_free (data);
|
||||||
|
meta_plugin_map_completed (plugin, window_actor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
meta_plugin_map_completed (plugin, window_actor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_destroy_effect_stopped (ClutterTimeline *timeline,
|
||||||
|
gboolean is_finished,
|
||||||
|
EffectCompleteData *data)
|
||||||
|
{
|
||||||
|
MetaPlugin *plugin = data->plugin;
|
||||||
|
MetaWindowActor *window_actor = META_WINDOW_ACTOR (data->actor);
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
|
||||||
|
actor_priv->destroy_timeline = NULL;
|
||||||
|
|
||||||
|
meta_plugin_destroy_completed (plugin, window_actor);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_destroy (MetaPlugin *plugin,
|
||||||
|
MetaWindowActor *window_actor)
|
||||||
|
{
|
||||||
|
ClutterActor *actor = CLUTTER_ACTOR (window_actor);
|
||||||
|
MetaWindow *window = meta_window_actor_get_meta_window (window_actor);
|
||||||
|
MetaWindowType type;
|
||||||
|
ClutterTimeline *timeline = NULL;
|
||||||
|
|
||||||
|
type = meta_window_get_window_type (window);
|
||||||
|
|
||||||
|
if (type == META_WINDOW_NORMAL)
|
||||||
|
{
|
||||||
|
timeline = actor_animate (actor,
|
||||||
|
CLUTTER_EASE_OUT_QUAD,
|
||||||
|
ANIMATION_DESTROY,
|
||||||
|
"opacity", 0,
|
||||||
|
"scale-x", 0.8,
|
||||||
|
"scale-y", 0.8,
|
||||||
|
NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (timeline)
|
||||||
|
{
|
||||||
|
EffectCompleteData *data = g_new0 (EffectCompleteData, 1);
|
||||||
|
ActorPrivate *actor_priv = get_actor_private (window_actor);
|
||||||
|
|
||||||
|
actor_priv->destroy_timeline = timeline;
|
||||||
|
data->plugin = plugin;
|
||||||
|
data->actor = actor;
|
||||||
|
g_signal_connect (actor_priv->destroy_timeline, "stopped",
|
||||||
|
G_CALLBACK (on_destroy_effect_stopped),
|
||||||
|
data);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
meta_plugin_destroy_completed (plugin, window_actor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
free_display_tile_preview (DisplayTilePreview *preview)
|
||||||
|
{
|
||||||
|
|
||||||
|
if (preview)
|
||||||
|
{
|
||||||
|
clutter_actor_destroy (preview->actor);
|
||||||
|
g_free (preview);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_display_closing (MetaDisplay *display,
|
||||||
|
DisplayTilePreview *preview)
|
||||||
|
{
|
||||||
|
free_display_tile_preview (preview);
|
||||||
|
}
|
||||||
|
|
||||||
|
static DisplayTilePreview *
|
||||||
|
get_display_tile_preview (MetaDisplay *display)
|
||||||
|
{
|
||||||
|
DisplayTilePreview *preview;
|
||||||
|
|
||||||
|
if (!display_tile_preview_data_quark)
|
||||||
|
{
|
||||||
|
display_tile_preview_data_quark =
|
||||||
|
g_quark_from_static_string (DISPLAY_TILE_PREVIEW_DATA_KEY);
|
||||||
|
}
|
||||||
|
|
||||||
|
preview = g_object_get_qdata (G_OBJECT (display),
|
||||||
|
display_tile_preview_data_quark);
|
||||||
|
if (!preview)
|
||||||
|
{
|
||||||
|
preview = g_new0 (DisplayTilePreview, 1);
|
||||||
|
|
||||||
|
preview->actor = clutter_actor_new ();
|
||||||
|
clutter_actor_set_background_color (preview->actor, CLUTTER_COLOR_Blue);
|
||||||
|
clutter_actor_set_opacity (preview->actor, 100);
|
||||||
|
|
||||||
|
clutter_actor_add_child (meta_get_window_group_for_display (display),
|
||||||
|
preview->actor);
|
||||||
|
g_signal_connect (display,
|
||||||
|
"closing",
|
||||||
|
G_CALLBACK (on_display_closing),
|
||||||
|
preview);
|
||||||
|
g_object_set_qdata (G_OBJECT (display),
|
||||||
|
display_tile_preview_data_quark,
|
||||||
|
preview);
|
||||||
|
}
|
||||||
|
|
||||||
|
return preview;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_show_tile_preview (MetaPlugin *plugin,
|
||||||
|
MetaWindow *window,
|
||||||
|
MetaRectangle *tile_rect,
|
||||||
|
int tile_monitor_number)
|
||||||
|
{
|
||||||
|
MetaDisplay *display = meta_plugin_get_display (plugin);
|
||||||
|
DisplayTilePreview *preview = get_display_tile_preview (display);
|
||||||
|
ClutterActor *window_actor;
|
||||||
|
|
||||||
|
if (clutter_actor_is_visible (preview->actor) &&
|
||||||
|
preview->tile_rect.x == tile_rect->x &&
|
||||||
|
preview->tile_rect.y == tile_rect->y &&
|
||||||
|
preview->tile_rect.width == tile_rect->width &&
|
||||||
|
preview->tile_rect.height == tile_rect->height)
|
||||||
|
return;
|
||||||
|
|
||||||
|
clutter_actor_set_position (preview->actor, tile_rect->x, tile_rect->y);
|
||||||
|
clutter_actor_set_size (preview->actor, tile_rect->width, tile_rect->height);
|
||||||
|
|
||||||
|
clutter_actor_show (preview->actor);
|
||||||
|
|
||||||
|
window_actor = CLUTTER_ACTOR (meta_window_get_compositor_private (window));
|
||||||
|
clutter_actor_set_child_below_sibling (clutter_actor_get_parent (preview->actor),
|
||||||
|
preview->actor,
|
||||||
|
window_actor);
|
||||||
|
|
||||||
|
preview->tile_rect = *tile_rect;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_hide_tile_preview (MetaPlugin *plugin)
|
||||||
|
{
|
||||||
|
MetaDisplay *display = meta_plugin_get_display (plugin);
|
||||||
|
DisplayTilePreview *preview = get_display_tile_preview (display);
|
||||||
|
|
||||||
|
clutter_actor_hide (preview->actor);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_kill_switch_workspace (MetaPlugin *plugin)
|
||||||
|
{
|
||||||
|
MetaTestShell *test_shell = META_TEST_SHELL (plugin);
|
||||||
|
|
||||||
|
kill_workspace_switch_animation (test_shell);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_kill_window_effects (MetaPlugin *plugin,
|
||||||
|
MetaWindowActor *window_actor)
|
||||||
|
{
|
||||||
|
ActorPrivate *actor_priv;
|
||||||
|
|
||||||
|
actor_priv = get_actor_private (window_actor);
|
||||||
|
|
||||||
|
if (actor_priv->minimize_timeline)
|
||||||
|
finish_timeline (actor_priv->minimize_timeline);
|
||||||
|
|
||||||
|
if (actor_priv->map_timeline)
|
||||||
|
finish_timeline (actor_priv->map_timeline);
|
||||||
|
|
||||||
|
if (actor_priv->destroy_timeline)
|
||||||
|
finish_timeline (actor_priv->destroy_timeline);
|
||||||
|
}
|
||||||
|
|
||||||
|
static const MetaPluginInfo *
|
||||||
|
meta_test_shell_plugin_info (MetaPlugin *plugin)
|
||||||
|
{
|
||||||
|
MetaTestShell *test_shell = META_TEST_SHELL (plugin);
|
||||||
|
|
||||||
|
return &test_shell->info;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_class_init (MetaTestShellClass *klass)
|
||||||
|
{
|
||||||
|
MetaPluginClass *plugin_class = META_PLUGIN_CLASS (klass);
|
||||||
|
|
||||||
|
plugin_class->start = meta_test_shell_start;
|
||||||
|
plugin_class->map = meta_test_shell_map;
|
||||||
|
plugin_class->minimize = meta_test_shell_minimize;
|
||||||
|
plugin_class->destroy = meta_test_shell_destroy;
|
||||||
|
plugin_class->switch_workspace = meta_test_shell_switch_workspace;
|
||||||
|
plugin_class->show_tile_preview = meta_test_shell_show_tile_preview;
|
||||||
|
plugin_class->hide_tile_preview = meta_test_shell_hide_tile_preview;
|
||||||
|
plugin_class->kill_window_effects = meta_test_shell_kill_window_effects;
|
||||||
|
plugin_class->kill_switch_workspace = meta_test_shell_kill_switch_workspace;
|
||||||
|
plugin_class->plugin_info = meta_test_shell_plugin_info;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
meta_test_shell_init (MetaTestShell *test_shell)
|
||||||
|
{
|
||||||
|
test_shell->info.name = "Test Shell";
|
||||||
|
test_shell->info.version = VERSION;
|
||||||
|
test_shell->info.author = "Mutter developers";
|
||||||
|
test_shell->info.license = "GPL";
|
||||||
|
test_shell->info.description = "This is test shell plugin implementation.";
|
||||||
|
}
|
26
src/tests/meta-test-shell.h
Normal file
26
src/tests/meta-test-shell.h
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2023 Red Hat
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program 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
|
||||||
|
* General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "meta/meta-plugin.h"
|
||||||
|
|
||||||
|
#define META_TYPE_TEST_SHELL (meta_test_shell_get_type ())
|
||||||
|
META_EXPORT
|
||||||
|
G_DECLARE_FINAL_TYPE (MetaTestShell, meta_test_shell,
|
||||||
|
META, TEST_SHELL,
|
||||||
|
MetaPlugin)
|
@ -756,18 +756,6 @@ meta_test_client_destroy (MetaTestClient *client)
|
|||||||
g_free (client);
|
g_free (client);
|
||||||
}
|
}
|
||||||
|
|
||||||
const char *
|
|
||||||
meta_test_get_plugin_name (void)
|
|
||||||
{
|
|
||||||
const char *name;
|
|
||||||
|
|
||||||
name = g_getenv ("MUTTER_TEST_PLUGIN_PATH");
|
|
||||||
if (name)
|
|
||||||
return name;
|
|
||||||
else
|
|
||||||
return "libdefault";
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
meta_set_custom_monitor_config_full (MetaBackend *backend,
|
meta_set_custom_monitor_config_full (MetaBackend *backend,
|
||||||
const char *filename,
|
const char *filename,
|
||||||
|
@ -109,9 +109,6 @@ MetaTestClient * meta_test_client_new (MetaContext *context,
|
|||||||
META_EXPORT
|
META_EXPORT
|
||||||
void meta_test_client_destroy (MetaTestClient *client);
|
void meta_test_client_destroy (MetaTestClient *client);
|
||||||
|
|
||||||
META_EXPORT
|
|
||||||
const char * meta_test_get_plugin_name (void);
|
|
||||||
|
|
||||||
META_EXPORT
|
META_EXPORT
|
||||||
void meta_set_custom_monitor_config_full (MetaBackend *backend,
|
void meta_set_custom_monitor_config_full (MetaBackend *backend,
|
||||||
const char *filename,
|
const char *filename,
|
||||||
|
@ -24,6 +24,7 @@
|
|||||||
#include "backends/meta-monitor-manager-private.h"
|
#include "backends/meta-monitor-manager-private.h"
|
||||||
#include "meta/meta-context.h"
|
#include "meta/meta-context.h"
|
||||||
#include "meta/meta-backend.h"
|
#include "meta/meta-backend.h"
|
||||||
|
#include "tests/meta-test-shell.h"
|
||||||
#include "tests/meta-test-utils.h"
|
#include "tests/meta-test-utils.h"
|
||||||
|
|
||||||
static MetaContext *test_context;
|
static MetaContext *test_context;
|
||||||
@ -90,7 +91,7 @@ main (int argc,
|
|||||||
|
|
||||||
context = meta_create_context ("Persistent virtual monitor test");
|
context = meta_create_context ("Persistent virtual monitor test");
|
||||||
g_assert (meta_context_configure (context, &fake_argc, &fake_argv, &error));
|
g_assert (meta_context_configure (context, &fake_argc, &fake_argv, &error));
|
||||||
meta_context_set_plugin_name (context, meta_test_get_plugin_name ());
|
meta_context_set_plugin_gtype (context, META_TYPE_TEST_SHELL);
|
||||||
g_assert (meta_context_setup (context, &error));
|
g_assert (meta_context_setup (context, &error));
|
||||||
g_assert (meta_context_start (context, &error));
|
g_assert (meta_context_start (context, &error));
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user