~and471/+junk/do-with-docky

« back to all changes in this revision

Viewing changes to Do.Interface.Linux.Docky/src/Docky.Interface/Docky.Interface.Items/WnckDockItem.cs

  • Committer: rugby471 at gmail
  • Date: 2010-10-15 16:08:38 UTC
  • Revision ID: rugby471@gmail.com-20101015160838-z9m3utbf7bxzb5ty
reverted to before docky removal

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
//  
 
2
//  Copyright (C) 2009 GNOME Do
 
3
// 
 
4
//  This program is free software: you can redistribute it and/or modify
 
5
//  it under the terms of the GNU General Public License as published by
 
6
//  the Free Software Foundation, either version 3 of the License, or
 
7
//  (at your option) any later version.
 
8
// 
 
9
//  This program is distributed in the hope that it will be useful,
 
10
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
 
11
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
12
//  GNU General Public License for more details.
 
13
// 
 
14
//  You should have received a copy of the GNU General Public License
 
15
//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
16
// 
 
17
 
 
18
using System;
 
19
using System.Collections.Generic;
 
20
using System.IO;
 
21
using System.Linq;
 
22
 
 
23
using Gdk;
 
24
using Cairo;
 
25
using Mono.Unix;
 
26
 
 
27
using Do.Platform;
 
28
using Do.Universe;
 
29
using Do.Interface.Wink;
 
30
using Do.Universe.Common;
 
31
using Do.Interface;
 
32
using Do.Interface.CairoUtils;
 
33
 
 
34
using Docky.Core;
 
35
using Docky.Interface.Menus;
 
36
using Docky.Utilities;
 
37
 
 
38
using Wnck;
 
39
 
 
40
namespace Docky.Interface
 
41
{
 
42
        
 
43
        
 
44
        public abstract class WnckDockItem : AbstractDockItem
 
45
        {
 
46
                const string ErrorMessage = "Docky could not move the file to the requested Directory.  " + 
 
47
                        "Please check file name and permissions and try again";
 
48
                
 
49
                // a bad hack, but it works
 
50
                static string [] blacklist = new [] {
 
51
                        "CopyToClipboardAction", 
 
52
                        "WindowFocusAction",
 
53
                };
 
54
                
 
55
                int last_raised;
 
56
                bool? accepting_drops;
 
57
                Gdk.Rectangle icon_region;
 
58
                
 
59
                DateTime last_scroll = new DateTime (0);
 
60
                TimeSpan scroll_rate = new TimeSpan (0, 0, 0, 0, 200);
 
61
                
 
62
                public abstract IEnumerable<Wnck.Window> Windows { get; }
 
63
                
 
64
                public abstract Item Item { get; }
 
65
                
 
66
                protected IEnumerable<Wnck.Window> VisibleWindows {
 
67
                        get { return Windows.Where (w => !w.IsSkipTasklist); }
 
68
                }
 
69
                
 
70
                protected bool HasVisibleApps {
 
71
                        get {
 
72
                                if (Windows == null)
 
73
                                        return false;
 
74
                                return VisibleWindows.Any ();
 
75
                        }
 
76
                }       
 
77
                
 
78
                public override bool ContainsFocusedWindow {
 
79
                        get { 
 
80
                                return Windows.Any (w => w.IsActive && (!w.IsSkipTasklist || w.WindowType != Wnck.WindowType.Desktop));
 
81
                        }
 
82
                }
 
83
                
 
84
                public override bool ContainsMinimizedWindow {
 
85
                        get {
 
86
                                return Windows.Any (w => w.IsMinimized && (!w.IsSkipTasklist));
 
87
                        }
 
88
                }
 
89
 
 
90
                
 
91
                public override bool IsAcceptingDrops {
 
92
                        get {
 
93
                                if (!accepting_drops.HasValue) {
 
94
                                        accepting_drops = (Item is IFileItem && Directory.Exists ((Item as IFileItem).Path)) || (Item is IApplicationItem);
 
95
                                }
 
96
                                return accepting_drops.Value;
 
97
                        }
 
98
                }
 
99
                
 
100
                public WnckDockItem() : base ()
 
101
                {
 
102
                        last_raised = 0;
 
103
                        RegisterEvents ();
 
104
                }
 
105
 
 
106
                void RegisterEvents ()
 
107
                {
 
108
                        DockServices.PainterService.PainterShowRequest += HandleShowRequest;
 
109
                        DockServices.PainterService.PainterHideRequest += HandleHideRequest;
 
110
                }
 
111
 
 
112
                void UnregisterEvents ()
 
113
                {
 
114
                        DockServices.PainterService.PainterShowRequest -= HandleShowRequest;
 
115
                        DockServices.PainterService.PainterHideRequest -= HandleHideRequest;
 
116
                }
 
117
                
 
118
                public override void SetIconRegion (Gdk.Rectangle region)
 
119
                {
 
120
                        if (icon_region == region) return;
 
121
                        icon_region = region;
 
122
                        SetIconRegionFromCache ();
 
123
                }
 
124
                
 
125
                protected void SetIconRegionFromCache ()
 
126
                {
 
127
                        VisibleWindows.ForEach (w => w.SetIconGeometry (icon_region.X, icon_region.Y, icon_region.Width, icon_region.Height));
 
128
                }
 
129
                
 
130
                protected IEnumerable<Act> ActionsForItem (Item item) 
 
131
                {
 
132
                        return Services.Core.GetActionsForItemOrderedByRelevance (item, false)
 
133
                                    .Where (act => !blacklist.Contains (act.GetType ().Name))
 
134
                                        .OrderByDescending (act => act.GetType ().Name != "WindowCloseAction")
 
135
                                        .ThenByDescending (act => act.GetType ().Name != "WindowMaximizeAction")
 
136
                                        .ThenByDescending (act => act.GetType ().Name != "WindowMinimizeAction")
 
137
                                        .ThenBy (act => act.Name.Length)
 
138
                                        .ThenBy (act => act.Name);
 
139
                }
 
140
                
 
141
                protected abstract void Launch ();
 
142
                
 
143
                public override void Scrolled (Gdk.ScrollDirection direction)
 
144
                {
 
145
                        if (WindowCount < 1 || (DateTime.UtcNow - last_scroll) < scroll_rate) return;
 
146
                        
 
147
                        last_scroll = DateTime.UtcNow;
 
148
                        
 
149
                        // This block will make sure that if we're scrolling on an app that is already active
 
150
                        // that when we scroll we move on the next window instead of appearing to do nothing
 
151
                        Wnck.Window focused = VisibleWindows.Where (w => w.IsActive).FirstOrDefault ();
 
152
                        if (focused != null) {
 
153
                                for (; last_raised < WindowCount - 1; last_raised++) {
 
154
                                        if (VisibleWindows.ElementAt (last_raised).Pid == focused.Pid)
 
155
                                                break;
 
156
                                }
 
157
                        }
 
158
                        
 
159
                        switch (direction) {
 
160
                        case ScrollDirection.Up:
 
161
                        case ScrollDirection.Right: 
 
162
                                last_raised++; 
 
163
                                break;
 
164
                        case ScrollDirection.Down:
 
165
                        case ScrollDirection.Left: 
 
166
                                last_raised--; 
 
167
                                break;
 
168
                        }
 
169
                        
 
170
                        KeepLastRaiseInBounds ();
 
171
                        VisibleWindows.ElementAt (last_raised).CenterAndFocusWindow ();
 
172
                }
 
173
                
 
174
                public override void Clicked (uint button, Gdk.ModifierType state, PointD position)
 
175
                {
 
176
                        if (!Windows.Any () || !HasVisibleApps || button == 2) {
 
177
                                AnimationType = ClickAnimationType.Bounce;
 
178
                                Launch ();
 
179
                        } else if (button == 1) {
 
180
                                AnimationType = ClickAnimationType.Darken;
 
181
                                WindowUtils.PerformLogicalClick (Windows);
 
182
                        } else {
 
183
                                AnimationType = ClickAnimationType.None;
 
184
                        }
 
185
                
 
186
                        base.Clicked (button, state, position);
 
187
                }
 
188
 
 
189
                public void HandleShowRequest (object sender, EventArgs e)
 
190
                {
 
191
                        VisibleWindows.ForEach (w => w.SetIconGeometry (0, 0, 0, 0));
 
192
                }
 
193
 
 
194
                public void HandleHideRequest (object sender, EventArgs e)
 
195
                {
 
196
                        SetIconRegionFromCache ();
 
197
                }
 
198
 
 
199
                protected bool DetermineUrgencyStatus  ()
 
200
                {
 
201
                        return VisibleWindows.Any (w => !w.IsSkipTasklist && w.NeedsAttention ());
 
202
                }
 
203
                
 
204
                void KeepLastRaiseInBounds ()
 
205
                {
 
206
                        if (WindowCount <= last_raised)
 
207
                                last_raised = 0;
 
208
                        else if (last_raised < 0)
 
209
                                last_raised = WindowCount - 1;
 
210
                }
 
211
                
 
212
                public override bool ReceiveItem (string item)
 
213
                {
 
214
                        bool result = false;
 
215
                        if (!IsAcceptingDrops)
 
216
                                return result;
 
217
                        
 
218
                        if (item.StartsWith ("file://"))
 
219
                                item = item.Substring ("file://".Length);
 
220
                        
 
221
                        if (File.Exists (item)) {
 
222
                                if (Item is IApplicationItem) {
 
223
                                        try {
 
224
                                                (Item as IApplicationItem).LaunchWithFiles (Do.Platform.Services.UniverseFactory.NewFileItem (item).Cons (null));
 
225
                                                SetLastClick ();
 
226
                                                AnimationType = ClickAnimationType.Bounce;
 
227
                                                result = true;
 
228
                                        } catch {
 
229
                                                Services.Notifications.Notify ("Docky Error", "Docky could not launch application");
 
230
                                        }
 
231
                                } else {
 
232
                                        try {
 
233
                                                File.Move (item, System.IO.Path.Combine ((Item as IFileItem).Path, System.IO.Path.GetFileName (item)));
 
234
                                                result = true;
 
235
                                        } catch { 
 
236
                                                Services.Notifications.Notify ("Docky Error", ErrorMessage);
 
237
                                        }
 
238
                                }
 
239
                        } else if (Directory.Exists (item)) {
 
240
                                try {
 
241
                                        Directory.Move (item, System.IO.Path.Combine ((Item as IFileItem).Path, System.IO.Path.GetFileName (item)));
 
242
                                        result = true;
 
243
                                } catch { 
 
244
                                        Services.Notifications.Notify ("Docky Error", ErrorMessage);
 
245
                                }
 
246
                        }
 
247
                        return result;
 
248
                }
 
249
 
 
250
                public override void Dispose ()
 
251
                {
 
252
                        UnregisterEvents ();
 
253
                        base.Dispose ();
 
254
                }
 
255
        }
 
256
}