Achieve Overlay Icon or Context Menu Option in the File Manager using Electron Js on Windows

94 Views Asked by At

We are creating a Sync Application in Electron JS which Syncs the Users Computer Data with the cloud. We are trying to achieve two functionalities, one of it is adding an overlay icon on a file or a directory(tick or cross) like Google Drive or One Drive does it. The other functionality is that we want to add a Context Menu Option in the File Manager for a directory which will allow the user to add or remove an asset from sync, from within the File Manager itself.

We tried various npm packages to try to achieve an overlay icon on the users file or directory or to Add a Context Menu option.

We also tried to add some registry values explicitly in order to achieve the overlay icon using npm winreg(^1.2.4) package, but that didn't work for us.

We even tried creating a desktop.ini file from our code itself, but still it didn't work. Attached code.

fs.writeFileSync(desktopIconPath,
                `[ViewState]
                Mode=
                FolderType=Pictures
                Vid=
                
                [.ShellClassInfo]
                IconResource=${desktopicon}
                IconIndex=103
                  `);

Finally we tried to create a C# DLL and tried accessing it through node js using npm edge-js(^19.3.0). But we got a "System.Runtime" error which we weren't able to resolve. Attached Error Below.

{ Error: Could not load file or assembly 'System.Runtime, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a' or one of its dependencies. The system cannot find the file specified. at Error (native) at Object.exports.func (D:\Kunal Someskar\Test Practice Projects\testelectronApp\node_modules\edge-js\lib\edge.js:178:17) at App.app.on.error (D:\Kunal Someskar\Test Practice Projects\testelectronApp\src\main.js:71:39) at emitTwo (events.js:111:20) at App.emit (events.js:191:7) Message: 'Could not load file or assembly \'System.Runtime, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a\' or one of its dependencies. The system cannot find the file specified.', FileName: 'System.Runtime, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a', FusionLog: 'WRN: Assembly binding logging is turned OFF.\r\nTo enable assembly bind failure logging, set the registry value [HKLM\\Software\\Microsoft\\Fusion!EnableLog] (DWORD) to 1.\r\nNote: There is some performance penalty associated with assembly bind failure logging.\r\nTo turn this feature off, remove the registry value [HKLM\\Software\\Microsoft\\Fusion!EnableLog].\r\n', Data: {}, InnerException: null, TargetSite: {}, StackTrace: ' at System.Reflection.RuntimeAssembly.GetType(RuntimeAssembly assembly, String name, Boolean throwOnError, Boolean ignoreCase, ObjectHandleOnStack type)\r\n at System.Reflection.RuntimeAssembly.GetType(String name, Boolean throwOnError, Boolean ignoreCase)\r\n at ClrFuncReflectionWrap.Create(Assembly assembly, String typeName, String methodName) in D:\\Kunal Someskar\\Test Practice Projects\\testelectronApp\\node_modules\\edge-js\\src\\dotnet\\clrfuncreflectionwrap.cpp:line 11\r\n at ClrFunc.Initialize(FunctionCallbackInfo<v8::Value>* info) in D:\\Kunal Someskar\\Test Practice Projects\\testelectronApp\\node_modules\\edge-js\\src\\dotnet\\clrfunc.cpp:line 101', HelpLink: null, Source: 'mscorlib', HResult: -2147024894, message: 'Could not load file or assembly \'System.Runtime, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a\' or one of its dependencies. The system cannot find the file specified.', name: 'System.IO.FileNotFoundException' }

Attaching the DLL File Code as well

using SharpShell.Interop;
using SharpShell.SharpIconOverlayHandler;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Runtime;

namespace ClassLibrary1
{
    /// <summary>
    /// The ReadOnlyFileIconOverlayHandler is an IconOverlayHandler that shows
    /// a padlock icon over files that are read only.
    /// </summary>
    [ComVisible(true)]
    public class ReadOnlyFileIconOverlayHandler : SharpIconOverlayHandler
    {
        /// <summary>
        /// Called by the system to get the priority, which is used to determine
        /// which icon overlay to use if there are multiple handlers. The priority
        /// must be between 0 and 100, where 0 is the highest priority.
        /// </summary>
        /// <returns>
        /// A value between 0 and 100, where 0 is the highest priority.
        /// </returns>
        protected override int GetPriority()
        {
            //  The read only icon overlay is very low priority
            return 90;
        }

        /// <summary>
        /// Determines whether an overlay should be shown for the shell item 
        /// with the path 'path' and
        /// the shell attributes 'attributes'
        /// </summary>
        ///// <param name="path">The path for the shell item. This is not necessarily the path
        /// to a physical file or folder.</param>
        /// <param name="attributes">The attributes of the shell item.</param>
        /// <returns>
        ///   <c>true</c> if this an overlay should be shown for the specified item; 
        ///  otherwise, <c>false</c>.
        /// </returns>
        protected override bool CanShowOverlay(string path, FILE_ATTRIBUTE attributes)
        {
            try
            {
                //  Get the file attributes
                var fileAttributes = new FileInfo(path);

                //  Return true if the file is read only, meaning we'll show the overlay
                return fileAttributes.IsReadOnly;
            }
            catch (Exception)
            {
                return false;
            }
        }

        /// <summary>
        /// Called to get the icon to show as the overlay icon
        /// </summary>
        /// <returns>
        /// The overlay icon
        /// </returns>
        protected override System.Drawing.Icon GetOverlayIcon()
        {
            //  Return the read only icon
            Icon icon = new Icon("Resources/correct.ico");
            return icon;
        }

    }

    public class test
    {
        public static int Add(int a, int b)
        {
            return a + b;
        }
    }
}

Trying to access the Class Test as for now

Edge-JS Code

try {
    var helloDll = require('edge-js').func({
      assemblyFile: "src/ClassLibrary1.dll",
      typeName: "ClassLibrary1.test",
      methodName: "Add"
    });
    console.log(helloDll);
  } catch (error) {
    console.log(error)
  }
1

There are 1 best solutions below

1
nyconing On

The error means System.Runtime.dll cant be load, but I dont know EdgeJs. Can you place System.Runtime.dll as dependencies?

According to github readme, you should add #r "System.Runtime.dll" and also SharpShell.dll I believe...