1 /* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */
2 
3 /* Metacity resizing-terminal-window feedback */
4 
5 /*
6  * Copyright (C) 2001 Havoc Pennington
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License as
10  * published by the Free Software Foundation; either version 2 of the
11  * License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful, but
14  * WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, see <http://www.gnu.org/licenses/>.
20  */
21 
22 #include <config.h>
23 #include "resizepopup.h"
24 #include "meta-tooltip.h"
25 #include "util.h"
26 #include <gtk/gtk.h>
27 #include <gdk/gdkx.h>
28 
29 struct _MetaResizePopup
30 {
31   GtkWidget *size_window;
32   Display *display;
33 
34   int vertical_size;
35   int horizontal_size;
36 
37   gboolean showing;
38 
39   MetaRectangle rect;
40 };
41 
42 MetaResizePopup*
meta_ui_resize_popup_new(Display * display)43 meta_ui_resize_popup_new (Display *display)
44 {
45   MetaResizePopup *popup;
46 
47   popup = g_new0 (MetaResizePopup, 1);
48 
49   popup->display = display;
50 
51   return popup;
52 }
53 
54 void
meta_ui_resize_popup_free(MetaResizePopup * popup)55 meta_ui_resize_popup_free (MetaResizePopup *popup)
56 {
57   g_return_if_fail (popup != NULL);
58 
59   if (popup->size_window)
60     gtk_widget_destroy (popup->size_window);
61 
62   g_free (popup);
63 }
64 
65 static void
ensure_size_window(MetaResizePopup * popup)66 ensure_size_window (MetaResizePopup *popup)
67 {
68   if (popup->size_window)
69     return;
70 
71   popup->size_window = meta_tooltip_new ();
72 }
73 
74 static void
update_size_window(MetaResizePopup * popup)75 update_size_window (MetaResizePopup *popup)
76 {
77   char *str;
78   int x, y;
79   int width, height;
80 
81   g_return_if_fail (popup->size_window != NULL);
82 
83   /* Translators: This represents the size of a window.  The first number is
84    * the width of the window and the second is the height.
85    */
86   str = g_strdup_printf (_("%d x %d"),
87                          popup->horizontal_size,
88                          popup->vertical_size);
89 
90   meta_tooltip_set_label_text (META_TOOLTIP (popup->size_window), str);
91   g_free (str);
92 
93   gtk_window_get_size (GTK_WINDOW (popup->size_window), &width, &height);
94 
95   x = popup->rect.x + (popup->rect.width - width) / 2;
96   y = popup->rect.y + (popup->rect.height - height) / 2;
97 
98   if (gtk_widget_get_realized (popup->size_window))
99     {
100       /* using move_resize to avoid jumpiness */
101       gdk_window_move_resize (gtk_widget_get_window (popup->size_window),
102                               x, y,
103                               width, height);
104     }
105   else
106     {
107       gtk_window_move   (GTK_WINDOW (popup->size_window),
108                          x, y);
109     }
110 }
111 
112 static void
sync_showing(MetaResizePopup * popup)113 sync_showing (MetaResizePopup *popup)
114 {
115   if (popup->showing)
116     {
117       if (popup->size_window)
118         gtk_widget_show (popup->size_window);
119 
120       if (popup->size_window && gtk_widget_get_realized (popup->size_window))
121         gdk_window_raise (gtk_widget_get_window (popup->size_window));
122     }
123   else
124     {
125       if (popup->size_window)
126         gtk_widget_hide (popup->size_window);
127     }
128 }
129 
130 void
meta_ui_resize_popup_set(MetaResizePopup * popup,MetaRectangle rect,int base_width,int base_height,int width_inc,int height_inc)131 meta_ui_resize_popup_set (MetaResizePopup *popup,
132                           MetaRectangle    rect,
133                           int              base_width,
134                           int              base_height,
135                           int              width_inc,
136                           int              height_inc)
137 {
138   gboolean need_update_size;
139   int display_w, display_h;
140 
141   g_return_if_fail (popup != NULL);
142 
143   need_update_size = FALSE;
144 
145   display_w = rect.width - base_width;
146   if (width_inc > 0)
147     display_w /= width_inc;
148 
149   display_h = rect.height - base_height;
150   if (height_inc > 0)
151     display_h /= height_inc;
152 
153   if (!meta_rectangle_equal(&popup->rect, &rect) ||
154       display_w != popup->horizontal_size ||
155       display_h != popup->vertical_size)
156     need_update_size = TRUE;
157 
158   popup->rect = rect;
159   popup->vertical_size = display_h;
160   popup->horizontal_size = display_w;
161 
162   if (need_update_size)
163     {
164       ensure_size_window (popup);
165       update_size_window (popup);
166     }
167 
168   sync_showing (popup);
169 }
170 
171 void
meta_ui_resize_popup_set_showing(MetaResizePopup * popup,gboolean showing)172 meta_ui_resize_popup_set_showing  (MetaResizePopup *popup,
173                                    gboolean         showing)
174 {
175   g_return_if_fail (popup != NULL);
176 
177   if (showing == popup->showing)
178     return;
179 
180   popup->showing = !!showing;
181 
182   if (popup->showing)
183     {
184       ensure_size_window (popup);
185       update_size_window (popup);
186     }
187 
188   sync_showing (popup);
189 }
190