EverythingFolderSize (Use Everything to calculate folder sizes)

Well, it was fun while it lasted :slight_smile:
Opus v13 has native support for Everything, so this add-in can happily be retired.


Edit:

  • 2023-05-02: Consolidated postings and comments
  • 2023-08-20: Added some info for portable installations

This add-in generates a custom column EverythingFolderSize which leverages voidtools' Everything to display folder sizes. The advantage of an Everything column is its faster performance compared to Opus' built-in column.

Upon execution, the script stores the data from Everything in variables that remain accessible until Opus is closed. Opus receives an update on every folder change if the EverythingFolderSize column is displayed in the file display.

This update feature can be disabled using the button provided below. Useful, if you experience decreased performance when opening many tabs via Layouts or Tabgroups. If disabled, the column will continue to display the last received values, and changes will not be reflected. It's worth noting that if the column doesn't receive valid data from Everything, it will remain empty.

:warning: Keep in mind that both the script and Everything use caches for the folder sizes. While refreshing these caches is typically fast, it's crucial to check with Opus' internal functions before performing any critical actions, such as deletion, based on the values in the column.

How to setup and use

:one: Save

ColumnEverythingFolderSize.js.txt
EventUpdateEverythingFolderSize.js.txt

to

%appdata%\GPSoftware\Directory Opus\Script AddIns

:two: Download both Everything and Everything Command-line Interface.

:three: Install Everything and unpack es.zip. Portable installations are ok, simply use your own path instead of /programfiles in the next steps (What are aliases?)

:four: If you run Everything 1.4

  • Copy es.exe to /programfiles\Everything
  • Check Index folder size in Everything Options

:five: If you run Everything 1.5a

  • Copy es.exe to /programfiles\Everything 1.5a
  • Add a line (or change) alpha_instance=0 in Everything-1.5a.ini.

:six: If you run Everything 1.5a or a Portable Installation

  • Pick the right var exeES = ... line in EventUpdateEverythingFolderSize.js.txt or insert the path to your portable installation.

:seven: Add a button to toggle the column. After turning the column on in the file display, refresh the lister (typically F5). This wakes up the script and needs to be done only once.

Button
Set COLUMNSTOGGLE="scp:EverythingFolderSize/EverythingFolderSize(!,a,0)"
<?xml version="1.0"?>
<button backcol="none" display="label" label_pos="right" textcol="none">
	<label>EverythingFolderSize</label>
	<icon1>#newcommand</icon1>
	<function type="normal">
		<instruction>Set COLUMNSTOGGLE=&quot;scp:EverythingFolderSize/EverythingFolderSize(!,a,0)&quot;</instruction>
	</function>
</button>

:eight: Optional: Add a button to toggle the event that updates the folder size cache. Only needed if you run into problems. Or if you like the visual confirmation that the script is enabled.

Button
@toggle:invert
Prefs SCRIPTDISABLE="EventUpdateEverythingFolderSize.js*,toggle"
<?xml version="1.0"?>
<button backcol="none" display="both" label_pos="right" textcol="none">
	<label>UpdateEverythingFolderSize</label>
	<icon1>#filterfolder</icon1>
	<function type="normal">
		<instruction>@toggle:invert</instruction>
		<instruction>Prefs SCRIPTDISABLE=&quot;EventUpdateEverythingFolderSize.js*,toggle&quot;</instruction>
	</function>
</button>

:nine: The EFS column remains empty? Check the log panel for error messages.

In a nutshell:

  • Are es.exe and Everything.exe (Everything64.exe) in the same folder?
  • Does var exeES point to es.exe?

Older versions

Unless you are the forum historian... don't bother

2023-04-25

EventUpdateEverythingFolderSize.js.txt
ColumnEverythingFolderSizeVars.js.txt

works in Flatview, but much slower:
ColumnEverythingFolderSize.js.txt

Things you might enjoy reading

How to use buttons and scripts from this forum

The scripts' inner workings

JScript
function OnInit(initData) {
    initData.name = 'EverythingFolderSize';
    initData.version = '2023-05-02';
    initData.copyright = '';
    initData.url = 'https://resource.dopus.com/t/everythingfoldersize-use-everything-to-calculate-folder-sizes/44281';
    initData.desc = '';
    initData.default_enable = true;
    initData.min_version = '12.0';
}

function OnAddColumns(addColData) {
    var col = addColData.AddColumn();
    col.name = 'EverythingFolderSize';
    col.header = 'EFS';
    // col.label = 'EverythingFolderSize';
    col.method = 'OnColumn';
    col.justify = 'right';
    col.type = 'size';
}

function OnColumn(scriptColData) {
    var item = scriptColData.item;
    if (!item.is_dir) return;
    if (item.path.drive == 0) return;

    var dirVar = 'EFS"' + item + '"';
    if (!DOpus.vars.Exists(dirVar)) return;

    scriptColData.value = DOpus.vars.Get(dirVar);
}
function OnInit(initData) {
    initData.name = 'UpdateEverythingFolderSize';
    initData.version = '2023-05-02b';
    initData.copyright = '';
    initData.url = 'https://resource.dopus.com/t/everythingfoldersize-use-everything-to-calculate-folder-sizes/44281';
    initData.desc = '';
    initData.default_enable = true;
    initData.min_version = '12.0';
}

var cmd = DOpus.Create().Command();
var stt = DOpus.Create().StringTools();
var fsu = DOpus.FSUtil();
var wsh = new ActiveXObject('WScript.Shell');

var exeES = fsu.Resolve('/programfiles\\Everything\\es.exe'); // Check "Index folder size" in Tools-Options-Indexes
// var exeES = fsu.Resolve('/programfiles\\Everything 1.5a\\es.exe'); // Everything-1.5a.ini needs to contain this line: alpha_instance=0

if (!fsu.Exists(exeES)) {
    DOpus.Output('"' + exeES + '" not found!');
}

function OnBeforeFolderChange(beforeFolderChangeData) {
    cmd.SetSourceTab(beforeFolderChangeData.tab);
    if (!cmd.IsSet('Set COLUMNSTOGGLE=scp:EverythingFolderSize/EverythingFolderSize')) return;

    if (!fsu.Exists(exeES)) return;

    var exportFile = fsu.GetTempFilePath();

    var cmdLine = '"' + exeES + '"' +
        ' -size' +
        ' -no-header' +
        ' -export-csv "' + exportFile + '"' +
        ' -parent "' + beforeFolderChangeData.path + '"' +
        ' /ad';

    // DOpus.Output(cmdLine);
    wsh.Run(cmdLine, 0, true);

    var vec = DOpus.Create().Vector(stt.Decode(fsu.GetItem(exportFile).Open().Read(), 'utf8').split('\r\n'));

    var re = /(\d+),(.*)/;

    for (var e = new Enumerator(vec); !e.atEnd(); e.moveNext()) {
        var line = re.exec(e.item());
        if (line == null) continue;
        if (line.length != 3) continue;
        var size = line[1];
        var dirVar = 'EFS' + line[2];
        DOpus.vars.Set(dirVar, size);
    }
}
12 Likes

Thank you ever so much, Ixp, your efforts are greatly appreciated! This isn't so common these days.

It does work and I really love to be able to have the persistent column that auto-calculates vs. having to trigger it, but unfortunately, it is very clunky in so far as it takes a lot of CPU time (and I have a 13th Gen Intel), so the CPU is pretty much fully occupied all the time if I keep moving through folders. Also, it takes significantly longer as with the TC Everything integration, which also needs no CPU at all and it really works instantaneously. I've tested it with both 1.4 and 1.5 alpha, so it shouldn't be related to that. I suspect it has to do with the CLI es.exe. I've tried both versions of your code btw., I noticed your edit.

If you wanna take a look at the TC implementation, you just have to add alpha_instance=0 to the Everything.ini and add the path to Everything.exe into the wincmd.ini (Everything=), tick 'Index folder size' in Everything options under 'Indexes' and tick 'Everything' in TC in configuration under 'Operation' and 'Calculate space occupied by subdirectories' close to the bottom of the dialog. Also, Everything has to be running before you fire up TC.

See these two forum threads if you're interested and want some more context:
https://ghisler.ch/board/viewtopic.php?t=51534
https://www.ghisler.ch/board/viewtopic.php?p=344501#p344501

It works flawlessly, but DOpus is so much better than TC in almost every other regard. I will still be using TC for that single feature, though, since it is invaluable for me.

Yes. es.exe gets called once per folder. Calling it once per tab and storing the results in variables should be faster. I'll check how fast TC is - nothing beats a good benchmark :slight_smile:

You can get the information you need in one ES.exe call.

Haven't looked at your script/ plugin/?, so this might be a mismatch, but the following will report the sizes of all folders directly under "C:\Program Files":

es.exe   folder:parent:"C:\Program Files"   -name   -size   -sizeformat 1   -csv

Example output:

Name,Size
"7-Zip",5735904
"Common Files",43432000
"CONEXANT",320477376
"Directory Opus",114135935
"Dolby",27502975
"Everything 1.5a",9622508
"Internet Explorer",2538218
"LinkShellExtension",511152
"Microsoft Update Health Tools",1936112
"ModifiableWindowsApps",0
"Mozilla Firefox",227615557
"MSBuild",25757
"Reference Assemblies",36844201
[...]

There are more options for finetuning -- let me know if you need more info -- but this should get you close.

Note: For "flat folders" [1] (EDIT: it is called: ) Flat View you need a differrent search syntax. Something like:

es.exe   folder:"c:\program files\"   -full-path-and-name   -size   -sizeformat 1   -csv

Note the \ at the end of the foldername; this prevents the "Program Files (x86)" to be caught too.



[1] Probably called different; Total Commander calls it Branch View; XYplorer calls it Branch View/ Flat View.
It is the content of a folder and its subfolders in one flat list.

1 Like

Yes. But Opus calls the script once per item in the tab.

Improved version that only makes one call per tab. Slightly faster :wink:

Content consolidated in first posting

The script stores the data from Everything in variables remaining available until Opus is shut down. Opus will get an update on every folder change. This can be turned off with the button below. Note that the columns will still display the last received values and that any changes will not be reflected! Folders read for the first time with the update mechanism turned off will be shown with size zero. As I mentioned in the intro: please double-check!

function OnInit(initData) {
    initData.name = 'UpdateEverythingFolderSize';
    initData.version = '2023-04-25';
    initData.copyright = '';
    initData.url = 'https://resource.dopus.com/t/everythingfoldersize-use-everything-to-calculate-folder-sizes/44281';
    initData.desc = '';
    initData.default_enable = true;
    initData.min_version = '12.0';
}

function OnBeforeFolderChange(beforeFolderChangeData) {
    var fsu = DOpus.FSUtil();
    var exeES = fsu.Resolve('/programfiles\\Everything\\es.exe');
    var wsh = new ActiveXObject('WScript.Shell');
    var stt = DOpus.Create().StringTools();

    var exportFile = fsu.GetTempFilePath();

    var cmdLine = '"' + exeES + '"' +
        ' -size' +
        ' -no-header' +
        ' -export-csv "' + exportFile + '"' +
        ' -parent "' + beforeFolderChangeData.path + '"' +
        ' /ad';

    // DOpus.Output(cmdLine);
    wsh.Run(cmdLine, 0, true);

    var vec = DOpus.Create().Vector(stt.Decode(fsu.GetItem(exportFile).Open().Read(), 'utf8').split('\r\n'));

    for (var e = new Enumerator(vec); !e.atEnd(); e.moveNext()) {
        var line = e.item().split(',');
        if (line.length != 2) continue;
        var size = line[0];
        var dirVar = 'EFS' + line[1];
        DOpus.vars.Set(dirVar, size);
    }
}
function OnInit(initData) {
    initData.name = 'EverythingFolderSizeVars';
    initData.version = '2023-04-25';
    initData.copyright = '';
    initData.url = 'https://resource.dopus.com/t/everythingfoldersize-use-everything-to-calculate-folder-sizes/44281';
    initData.desc = '';
    initData.default_enable = true;
    initData.min_version = '12.0';
}

function OnAddColumns(addColData) {
    var col = addColData.AddColumn();
    col.name = 'EverythingFolderSizeVars';
    col.header = 'EverythingFolderSizeVars';
    col.label = 'EverythingFolderSizeVars';
    col.method = 'OnColumn';
    col.justify = 'right';
    col.type = 'size';
}

function OnColumn(scriptColData) {
    var item = scriptColData.item;
    if (!item.is_dir) return;
    if (item.path.drive == 0) return;

    var dirVar = 'EFS"' + item + '"';
    scriptColData.value = DOpus.vars.Exists(dirVar) ? DOpus.vars.Get(dirVar) : 0;
}

Save these

EventUpdateEverythingFolderSize.js.txt
ColumnEverythingFolderSizeVars.js.txt

to

%appdata%\GPSoftware\Directory Opus\Script AddIns

Toggle the column with

Set COLUMNSTOGGLE="scp:EverythingFolderSizeVars/EverythingFolderSizeVars(!,a,0)"
Button as XML
<?xml version="1.0"?>
<button backcol="none" display="label" label_pos="right" textcol="none">
	<label>EverythingFolderSizeVars</label>
	<icon1>#newcommand</icon1>
	<function type="normal">
		<instruction>Set COLUMNSTOGGLE=&quot;scp:EverythingFolderSizeVars/EverythingFolderSizeVars(!,a,0)&quot;</instruction>
	</function>
</button>

Toggle the event that updates the folder sizes with

@toggle:invert
Prefs SCRIPTDISABLE="EventUpdateEverythingFolderSize.js*,toggle"
Button as XML
<?xml version="1.0"?>
<button backcol="none" display="both" label_pos="right" textcol="none">
	<label>UpdateEverythingFolderSize</label>
	<icon1>#filterfolder</icon1>
	<function type="normal">
		<instruction>@toggle:invert</instruction>
		<instruction>Prefs SCRIPTDISABLE=&quot;EventUpdateEverythingFolderSize.js*,toggle&quot;</instruction>
	</function>
</button>
3 Likes

Masterful, Ixp, now it's as speedy and resource-friendly as in TC. Thanks so much, one app less to worry about! :smiley:

Yes, it really is a difference like day and night. Didn't see that coming, honestly. But a nice surprise once in a while is ok :slight_smile:

hmm. I can't get this to work. I installed the 64-bit version of Everything and I noticed the filename is:
C:\Program Files\Everything\Everything.exe

So I replaced:

var exeES = fsu.Resolve('/programfiles\\Everything\\es.exe');

with

    var exeES = fsu.Resolve('c:\\program files\\Everything\\Everything.exe');

but the EverythingFolderSizeVars column still shows 0 bytes :man_shrugging:

What am I doing wrong?

Everything.exe and es.exe are not the same. See Command Line Interface - voidtools which also links to where you can download es.exe near the top.

1 Like

Furthermore: Everything itself must be running in the background when using EverythingFolderSize:
ES.exe sends the search-query to Everything, which looks in its database and sends the matching results back to ES.

1 Like

It looks like this hyperlink does not contain an url?

Ah ok. That makes sense.
Except it's still not working for me. 'Everything' is installed and works as it should. But the EverythingFolderSizeVars column stays blank.

I've tried:

    var exeES = fsu.Resolve('/programfiles\\Everything\\es.exe');
    var exeES = fsu.Resolve('/program files\\Everything\\es.exe');

and

    var exeES = fsu.Resolve('C:\\Program Files\\Everything\\es.exe');

Not sure what the correct syntax is. I'm a bit new to scripts and buttons as you might be able to tell...

Oops. Yes. Fixed!

1 Like

The process is quite intransparent, let me try and help you. First, you open this post as reference:

What you do (as far as I understand it and it's working flawlessly for me now) is the following:

You download the item under 'Download Everything Command-line Interface', this gives you the es.exe you need to then put into Program Files/Everything:
https://www.voidtools.com/downloads/#cli

You make sure Everything is running, I suggest you activate Everything as a service if you haven't already (you can use this method with either 1.4 or 1.5 alpha, you just have to make sure only one instance is running and you have alpha_instance=0 set in everything.ini.

Now you download the two text files Ixp attached above and put them in the posted folder 'Script AddIns'.

Then right click on DOpus title par and activate customize mode through 'Customize...'.

Righ-click on the toolbar and select either 'New -> New Button' or 'Insert New -> New Button' depending on where you click.

Create two different buttons. Right-click on each button and click 'Edit...', click 'Advanced...', pick 'Script Function' under 'Function', select 'JScript' under 'Script Type' and replace the text below with the content of the two green code boxes above. Then you can remove the buttons from the toolbar (I clicked them once, but I don't think you have to do that, it's just to add the code to DOpus' DB). Deactivate customize mode.

Now you can right-click on the columns and tick 'EverythingFolderSizeVars' under 'Columns -> Script' and voilà (I changed the label of EverythingFolderSizeVars, so the column isn't too wide). Now you can optionally add the XML buttons to toggle visibility and refresh or you just leave the column activated permanently.

2 Likes

Thank you for trying to help me.

I have Everything 64-bit installed and running as a service. It works fine as I am able to use the Everything GUI to filter the file list as expected.

I have copied the es.exe file into the Program Files\Everything folder.

There is no alpha_instance=0 present in the everything.ini file.
I see only
allow_multiple_instances=0

I added alpha_instance=0 also, but it made no difference.

I have downloaded and put the scripts into the
\AppData\Roaming\GPSoftware\Directory Opus\Script AddIns folder.
I noticed they have a .js.txt extension, I even tried changing the extension to just .js, but still no go.

I have created the buttons by pasting in the XML shown above.
The show/hide column button works as expected.

The UpdateEverythingFolderSize button however does nothing.

As an aside, after installing Everything last night, my machine hung instead of going to sleep like it normally does when I finished for the day... It normally never does this. Everything is the only new software I installed yesterday.

Both are ok

Is the column empty or are the values zero?

All it does is toggle this check box:

Before, when I mistakenly had
var exeES = fsu.Resolve('c:\program files\Everything\Everything.exe');
it was zeros.
When I corrected it to
var exeES = fsu.Resolve('/programfiles\Everything\es.exe');
it's empty

You are looking at the correct column EverythingFolderSizeVars, right?

Please uncomment line 26 in EventUpdateEverythingFolderSize.js

// DOpus.Output(cmdLine);

You should then see something in the logs when changing or refreshing the tab.

Oh, I'm sorry, you only need the alpha_instance=0 if you're using 1.5 alpha of Everything. You have to copy the cli.c with the es.exe, you probably forgot that. When I rename cli.c, I also get 0s as a result. EDIT: Never mind, I had the Refresh button disabled, that's why it didn't work without cli.c. :stuck_out_tongue: Maybe you have that disabled somehow?