Statistics
| Branch: | Revision:

root / trunk / Pithos.ShellExtensions / Overlays / IconOverlayBase.cs @ 255f5f86

History | View | Annotate | Download (8 kB)

1
#region
2
/* -----------------------------------------------------------------------
3
 * <copyright file="IconOverlayBase.cs" company="GRNet">
4
 * 
5
 * Copyright 2011-2012 GRNET S.A. All rights reserved.
6
 *
7
 * Redistribution and use in source and binary forms, with or
8
 * without modification, are permitted provided that the following
9
 * conditions are met:
10
 *
11
 *   1. Redistributions of source code must retain the above
12
 *      copyright notice, this list of conditions and the following
13
 *      disclaimer.
14
 *
15
 *   2. Redistributions in binary form must reproduce the above
16
 *      copyright notice, this list of conditions and the following
17
 *      disclaimer in the documentation and/or other materials
18
 *      provided with the distribution.
19
 *
20
 *
21
 * THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
22
 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
23
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
24
 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
25
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
28
 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29
 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
31
 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32
 * POSSIBILITY OF SUCH DAMAGE.
33
 *
34
 * The views and conclusions contained in the software and
35
 * documentation are those of the authors and should not be
36
 * interpreted as representing official policies, either expressed
37
 * or implied, of GRNET S.A.
38
 * </copyright>
39
 * -----------------------------------------------------------------------
40
 */
41
#endregion
42
using System;
43
using System.Diagnostics;
44
using System.Diagnostics.Contracts;
45
using System.IO;
46

    
47
using System.ComponentModel.Composition;
48
using System.Linq;
49
using Microsoft.Win32;
50
using Pithos.Interfaces;
51

    
52
namespace Pithos.ShellExtensions.Overlays
53
{
54

    
55
    public class IconOverlayBase : IShellIconOverlayIdentifier
56
    {
57
        private static readonly log4net.ILog Log = log4net.LogManager.GetLogger("Pithos.IconOverlay");
58

    
59
        protected static string PithosPrefix = "0Pithos";
60

    
61
        public string OverlayName { get; private set; }
62
        public string IconPath { get; private set; }
63

    
64
        [Import(typeof (IStatusChecker))] 
65
        public IStatusChecker StatusChecker;
66
        [Import(typeof (IPithosSettings))] 
67
        public IPithosSettings Settings;
68

    
69

    
70

    
71
        public IconOverlayBase(string iconName)
72
        {
73
            if (String.IsNullOrWhiteSpace(iconName))
74
                throw new ArgumentNullException("iconName","Empty iconName");
75

    
76
            Debug.WriteLine("Icon Overlay Instance created", LogCategories.ShellOverlays);
77
            IoC.Current.Compose(this);
78
            
79

    
80
            string overlayName=PithosPrefix + iconName;
81
            string iconFile = iconName + "Icon.ico";
82

    
83

    
84
            var iconsFolder = Settings.IconsPath;
85
            var fullPath = Path.Combine(iconsFolder, iconFile);
86

    
87
            OverlayName = overlayName;
88
            IconPath = fullPath;
89

    
90
            
91
        }
92

    
93

    
94
        private static bool? _isExplorer = false;
95

    
96

    
97
        private bool IsExplorer
98
        {
99
            get
100
            {
101
                if (!_isExplorer.HasValue)
102
                {
103
                    var moduleName = Process.GetCurrentProcess().MainModule.ModuleName;
104
                    _isExplorer = (moduleName == "explorer.exe");
105
                }
106
                return _isExplorer.Value;
107
            }
108
        }
109

    
110
        public int IsMemberOf(string path, uint attributes)
111
        {
112
            var showOnlyInExplorer=(int)Registry.LocalMachine.GetValue(@"SOFTWARE\GRNet\Pithos\ShowOnlyInExplorer", 0);
113
            if (showOnlyInExplorer!=0 && !IsExplorer)
114
                return WinError.S_FALSE;
115

    
116

    
117
            if (String.IsNullOrWhiteSpace(path))
118
                throw new ArgumentNullException("path","Empty path");
119

    
120
            Debug.WriteLine(String.Format("ICON Status check for {0} - {1}", path, GetType().Name), LogCategories.ShellOverlays);
121
            
122
            if (!Settings.Accounts.Any(account=>account.RootPath!=null && path.StartsWith(account.RootPath,StringComparison.InvariantCultureIgnoreCase)))
123
                return WinError.S_FALSE;
124

    
125
            var status=StatusChecker.GetFileOverlayStatus(path);
126
            var isMember = (PithosPrefix + status == OverlayName);
127
            Debug.WriteLine(String.Format("[STATUS] Was {0}, expected {1} for {2}", status, OverlayName,path ), LogCategories.ShellOverlays);
128
            return isMember ? WinError.S_OK : WinError.S_FALSE;
129
        }
130

    
131
        public int GetOverlayInfo(
132
            IntPtr iconFileBuffer,
133
            int iconFileBufferSize,
134
            out int iconIndex,
135
            out uint flags)
136
        {
137
            Contract.Requires(iconFileBuffer!=IntPtr.Zero);
138
            Contract.Requires(iconFileBufferSize>0);
139

    
140
            if (iconFileBuffer == IntPtr.Zero)
141
                throw new ArgumentNullException("iconFileBuffer","iconFileBuffer not initialized");
142
            if (iconFileBufferSize<=0)
143
                throw new ArgumentException("iconFileBufferSize", "iconFileBufferSize must be greatere than 0");
144
            Debug.WriteLine("Looking for icons", LogCategories.ShellOverlays);
145
            Debug.WriteLine(string.Format("ICON file {0}", IconPath), LogCategories.ShellOverlays);
146
            
147
            int bytesCount = System.Text.Encoding.Unicode.GetByteCount(IconPath);
148
            Debug.WriteLine(string.Format(" GetOverlayInfo::{0}", bytesCount), LogCategories.ShellOverlays);
149

    
150
            MarshalHelpers.CopyToBuffer(IconPath, iconFileBuffer, iconFileBufferSize);
151

    
152
            flags = (uint)(ISIOI.ISIOI_ICONFILE);// | ISIOI.ISIOI_ICONINDEX);
153
            iconIndex = 0;
154
            return WinError.S_OK;
155
        }
156

    
157
        public int  GetPriority(out int priority)
158
        {
159
            Debug.WriteLine("Checking for priority");
160
            priority = 0;
161
            return WinError.S_OK;
162
        }
163

    
164
        
165
        public static void RegisterOverlay(Type type,string iconName)
166
        {
167
            Contract.Requires(type != null);
168
            Contract.Requires(!String.IsNullOrWhiteSpace(iconName));
169

    
170
            if (type == null)
171
                throw new ArgumentNullException("type", "type can't be null");
172
            if (String.IsNullOrWhiteSpace(iconName))
173
                throw new ArgumentNullException("iconName", "iconName can't be null");
174

    
175
            try
176
            {
177
                
178
                ShellExtReg.RegisterIconOverlayIdentifier(type.GUID, iconName);
179

    
180
                NativeMethods.SHChangeNotify(HChangeNotifyEventID.SHCNE_ASSOCCHANGED, HChangeNotifyFlags.SHCNF_IDLIST,
181
                                             IntPtr.Zero, IntPtr.Zero);
182
                Debug.WriteLine("Registered icon handler");
183
            }
184
            catch (Exception ex)
185
            {
186
                Debug.WriteLine(ex.Message); // Log the error
187
                throw;  // Re-throw the exception
188
            }
189
        }
190

    
191
        
192
        public static void UnregisterOverlay(Type type,string iconName)
193
        {
194
            Contract.Requires(type!=null);
195
            Contract.Requires(!String.IsNullOrWhiteSpace(iconName));
196

    
197
            if (type==null)
198
                throw new ArgumentNullException("type","type can't be null");
199
            if (String.IsNullOrWhiteSpace(iconName))
200
                throw new ArgumentNullException("iconName","iconName can't be null");
201
            try
202
            {                
203
                ShellExtReg.UnregisterIconOverlayIdentifier(type.GUID, iconName);
204
                Debug.WriteLine(String.Format("UnRegistered icon handler {0}:{1}",iconName,type.GUID), LogCategories.ShellOverlays);
205
            }
206
            catch (Exception ex)
207
            {
208
                //Log and rethrow
209
                Log.ErrorFormat("Failed to unregister overlay {0}:{1} with error {2}",iconName,type.GUID,ex.Message); 
210
                throw;  
211
            }
212
        }
213
    }
214

    
215
}