sliding panel

This commit is contained in:
Tomas Frydrych 2008-10-16 15:50:03 +01:00
parent d185a84140
commit b5414c27a3
3 changed files with 109 additions and 70 deletions

View File

@ -30,6 +30,7 @@
#define N_(x) x
#include <clutter/clutter.h>
#include <clutter/x11/clutter-x11.h>
#include <gmodule.h>
#include <string.h>
@ -40,7 +41,7 @@
#define SWITCH_TIMEOUT 500
#define PANEL_SLIDE_TIMEOUT 250; \
#define PANEL_SLIDE_THRESHOLD 3
#define PANEL_SLIDE_THRESHOLD 2
#define PANEL_HEIGHT 40
#define ACTOR_DATA_KEY "MCCP-Moblin-actor-data"
@ -98,6 +99,7 @@ MetaCompositorClutterPlugin META_COMPOSITOR_CLUTTER_PLUGIN_STRUCT =
.unmaximize = unmaximize,
.switch_workspace = switch_workspace,
.kill_effect = kill_effect,
.xevent_filter = xevent_filter,
/* The reload handler */
.reload = reload
@ -126,6 +128,8 @@ struct PluginPrivate
gboolean debug_mode : 1;
gboolean panel_out : 1;
gboolean panel_out_in_progress : 1;
gboolean panel_back_in_progress : 1;
};
/*
@ -612,58 +616,30 @@ on_panel_effect_complete (ClutterActor *panel, gpointer data)
{
gboolean reactive = GPOINTER_TO_INT (data);
MetaCompositorClutterPlugin *plugin = get_plugin ();
PluginPrivate *priv = plugin->plugin_private;
if (reactive)
meta_comp_clutter_plugin_set_stage_reactive (plugin, reactive);
{
priv->panel_out_in_progress = FALSE;
meta_comp_clutter_plugin_set_stage_reactive (plugin, reactive);
}
else
meta_comp_clutter_plugin_set_stage_input_area (plugin, 0, 0,
{
priv->panel_back_in_progress = FALSE;
meta_comp_clutter_plugin_set_stage_input_area (plugin, 0, 0,
plugin->screen_width, 1);
}
}
static gboolean
xevent_filter (XEvent *xev)
{
MetaCompositorClutterPlugin *plugin = get_plugin ();
PluginPrivate *priv = plugin->plugin_private;
ClutterActor *stage;
if (xev->type != MotionNotify)
return FALSE;
stage = meta_comp_clutter_plugin_get_stage (plugin);
printf ("got xevent type %d on 0x%x @ y %d\n",
xev->type,
(gint) xev->xmotion.window,
xev->xmotion.y_root);
if (priv->panel_out)
{
guint height = clutter_actor_get_height (priv->panel);
gint x = clutter_actor_get_x (priv->panel);
if (xev->xmotion.y_root > (gint)height)
{
clutter_effect_move (priv->panel_slide_effect,
priv->panel, x, -height,
on_panel_effect_complete,
GINT_TO_POINTER (FALSE));
}
priv->panel_out = FALSE;
return TRUE;
}
else if (xev->xmotion.y_root < PANEL_SLIDE_THRESHOLD)
{
gint x = clutter_actor_get_x (priv->panel);
clutter_effect_move (priv->panel_slide_effect,
priv->panel, x, 0,
on_panel_effect_complete,
GINT_TO_POINTER (TRUE ));
priv->panel_out = TRUE;
return TRUE;
}
clutter_x11_handle_event (xev);
return FALSE;
}
@ -746,15 +722,14 @@ g_module_check_init (GModule *module)
static gboolean
stage_input_cb (ClutterActor *stage, ClutterEvent *event, gpointer data)
{
printf ("Got event, type %d\n", event->type);
if (event->type == CLUTTER_MOTION)
{
ClutterMotionEvent *mev = (ClutterMotionEvent *) event;
MetaCompositorClutterPlugin *plugin = get_plugin ();
PluginPrivate *priv = plugin->plugin_private;
printf ("got stage motion event at y %d\n", mev->y);
if (priv->panel_out_in_progress || priv->panel_back_in_progress)
return FALSE;
if (priv->panel_out)
{
@ -763,24 +738,25 @@ stage_input_cb (ClutterActor *stage, ClutterEvent *event, gpointer data)
if (mev->y > (gint)height)
{
priv->panel_back_in_progress = TRUE;
clutter_effect_move (priv->panel_slide_effect,
priv->panel, x, -height,
on_panel_effect_complete,
GINT_TO_POINTER (FALSE));
priv->panel_out = FALSE;
}
priv->panel_out = FALSE;
return TRUE;
}
else if (mev->y < PANEL_SLIDE_THRESHOLD)
{
gint x = clutter_actor_get_x (priv->panel);
priv->panel_out_in_progress = TRUE;
clutter_effect_move (priv->panel_slide_effect,
priv->panel, x, 0,
on_panel_effect_complete,
GINT_TO_POINTER (TRUE ));
GINT_TO_POINTER (TRUE));
priv->panel_out = TRUE;
@ -793,6 +769,23 @@ stage_input_cb (ClutterActor *stage, ClutterEvent *event, gpointer data)
return FALSE;
}
static ClutterActor *
make_panel (gint width)
{
ClutterActor *panel;
ClutterActor *background;
ClutterColor clr = {0xff, 0, 0, 0xff};
panel = clutter_group_new ();
/* FIME -- size and color */
background = clutter_rectangle_new_with_color (&clr);
clutter_container_add_actor (CLUTTER_CONTAINER (panel), background);
clutter_actor_set_size (background, width, PANEL_HEIGHT);
return panel;
}
/*
* Core of the plugin init function, called for initial initialization and
* by the reload() function. Returns TRUE on success.
@ -811,8 +804,8 @@ do_init ()
guint switch_timeout = SWITCH_TIMEOUT;
guint panel_slide_timeout = PANEL_SLIDE_TIMEOUT;
const gchar *name;
ClutterActor *overlay, *background;
ClutterColor clr = {0xff, 0, 0, 0xff};
ClutterActor *overlay;
ClutterActor *panel;
plugin->plugin_private = priv;
@ -901,30 +894,22 @@ do_init ()
overlay = meta_comp_clutter_plugin_get_overlay_group (plugin);
priv->panel = clutter_group_new ();
clutter_container_add_actor (CLUTTER_CONTAINER (overlay), priv->panel);
panel = priv->panel = make_panel (plugin->screen_width);
clutter_container_add_actor (CLUTTER_CONTAINER (overlay), panel);
priv->panel_slide_effect
= clutter_effect_template_new (clutter_timeline_new_for_duration (
panel_slide_timeout),
CLUTTER_ALPHA_SINE_INC);
/* FIME -- size and color */
background = clutter_rectangle_new_with_color (&clr);
clutter_container_add_actor (CLUTTER_CONTAINER (priv->panel), background);
clutter_actor_set_size (background, plugin->screen_width, PANEL_HEIGHT);
clutter_actor_set_position (background, 0,
-clutter_actor_get_height (background));
clutter_actor_set_position (panel, 0,
-clutter_actor_get_height (panel));
g_signal_connect (meta_comp_clutter_plugin_get_stage (plugin),
"motion-event", G_CALLBACK (stage_input_cb), NULL);
g_signal_connect (meta_comp_clutter_plugin_get_stage (plugin),
"button-press-event", G_CALLBACK (stage_input_cb), NULL);
meta_comp_clutter_plugin_set_stage_input_area (plugin, 0, 0,
plugin->screen_width, 60);
plugin->screen_width, 1);
clutter_set_motion_events_enabled (TRUE);

View File

@ -32,6 +32,7 @@
#include <X11/Xlib.h>
#include <X11/extensions/Xfixes.h>
#include <X11/extensions/shape.h>
#include <clutter/x11/clutter-x11.h>
static gboolean meta_compositor_clutter_plugin_manager_reload (MetaCompositorClutterPluginManager *mgr);
@ -722,9 +723,12 @@ meta_comp_clutter_plugin_set_stage_reactive (MetaCompositorClutterPlugin *plugin
MetaCompositorClutterPluginManager *mgr = priv->self;
MetaDisplay *display = meta_screen_get_display (mgr->screen);
Display *xdpy = meta_display_get_xdisplay (display);
Window overlay;
Window xstage, xoverlay;
ClutterActor *stage;
overlay = meta_compositor_clutter_get_overlay_window (mgr->screen);
stage = meta_compositor_clutter_get_stage_for_screen (mgr->screen);
xstage = clutter_x11_get_stage_window (CLUTTER_STAGE (stage));
xoverlay = meta_compositor_clutter_get_overlay_window (mgr->screen);
static XserverRegion region = None;
@ -733,12 +737,16 @@ meta_comp_clutter_plugin_set_stage_reactive (MetaCompositorClutterPlugin *plugin
if (reactive)
{
XFixesSetWindowShapeRegion (xdpy, overlay,
XFixesSetWindowShapeRegion (xdpy, xstage,
ShapeInput, 0, 0, None);
XFixesSetWindowShapeRegion (xdpy, xoverlay,
ShapeInput, 0, 0, None);
}
else
{
XFixesSetWindowShapeRegion (xdpy, overlay,
XFixesSetWindowShapeRegion (xdpy, xstage,
ShapeInput, 0, 0, region);
XFixesSetWindowShapeRegion (xdpy, xoverlay,
ShapeInput, 0, 0, region);
}
}
@ -751,11 +759,14 @@ meta_comp_clutter_plugin_set_stage_input_area (MetaCompositorClutterPlugin *plug
MetaCompositorClutterPluginManager *mgr = priv->self;
MetaDisplay *display = meta_screen_get_display (mgr->screen);
Display *xdpy = meta_display_get_xdisplay (display);
Window overlay;
Window xstage, xoverlay;
ClutterActor *stage;
XRectangle rect;
XserverRegion region;
overlay = meta_compositor_clutter_get_overlay_window (mgr->screen);
stage = meta_compositor_clutter_get_stage_for_screen (mgr->screen);
xstage = clutter_x11_get_stage_window (CLUTTER_STAGE (stage));
xoverlay = meta_compositor_clutter_get_overlay_window (mgr->screen);
rect.x = x;
rect.y = y;
@ -764,5 +775,6 @@ meta_comp_clutter_plugin_set_stage_input_area (MetaCompositorClutterPlugin *plug
region = XFixesCreateRegion (xdpy, &rect, 1);
XFixesSetWindowShapeRegion (xdpy, overlay, ShapeInput, 0, 0, region);
XFixesSetWindowShapeRegion (xdpy, xstage, ShapeInput, 0, 0, region);
XFixesSetWindowShapeRegion (xdpy, xoverlay, ShapeInput, 0, 0, region);
}

View File

@ -1646,6 +1646,7 @@ process_property_notify (MetaCompositorClutter *compositor,
static void
show_overlay_window (MetaScreen *screen, Window cow)
{
#if 0
MetaDisplay *display = meta_screen_get_display (screen);
Display *xdisplay = meta_display_get_xdisplay (display);
XserverRegion region;
@ -1656,6 +1657,7 @@ show_overlay_window (MetaScreen *screen, Window cow)
XFixesSetWindowShapeRegion (xdisplay, cow, ShapeInput, 0, 0, region);
XFixesDestroyRegion (xdisplay, region);
#endif
}
static Window
@ -1668,7 +1670,14 @@ get_output_window (MetaScreen *screen)
xroot = meta_screen_get_xroot (screen);
output = XCompositeGetOverlayWindow (xdisplay, xroot);
XSelectInput (xdisplay, output, ExposureMask);
XSelectInput (xdisplay,
output,
FocusChangeMask |
ExposureMask |
PointerMotionMask |
PropertyChangeMask |
ButtonPressMask | ButtonReleaseMask |
KeyPressMask | KeyReleaseMask);
return output;
}
@ -1749,6 +1758,15 @@ clutter_cmp_manage_screen (MetaCompositor *compositor,
XReparentWindow (xdisplay, xwin, info->output, 0, 0);
XSelectInput (xdisplay,
xwin,
FocusChangeMask |
ExposureMask |
PointerMotionMask |
PropertyChangeMask |
ButtonPressMask | ButtonReleaseMask |
KeyPressMask | KeyReleaseMask);
info->window_group = clutter_group_new ();
info->overlay_group = clutter_group_new ();
@ -1843,6 +1861,30 @@ clutter_cmp_process_event (MetaCompositor *compositor,
event) == TRUE)
return;
}
else
{
GSList *l;
MetaCompositorClutter *clc = (MetaCompositorClutter*)compositor;
l = meta_display_get_screens (clc->display);
while (l)
{
MetaScreen *screen = l->data;
MetaCompScreen *info;
info = meta_screen_get_compositor_data (screen);
if (meta_compositor_clutter_plugin_manager_xevent_filter
(info->plugin_mgr,
event) == TRUE)
{
return;
}
l = l->next;
}
}
/*
* This trap is so that none of the compositor functions cause