Codebox Software

UltraEdit Block Comment Script

Published:

This script adds language-sensitive block commenting functionality to the UltraEdit text editor. For details of how to install and use UltraEdit scripts see the UltraEdit Scripting Tutorial. You can download the script here.

The script comments out all selected lines of code within the active document, using comment symbols appropriate to the type of file being edited. If the selected text is already commented out, then the comment symbols will be removed allowing comments to be toggled on/off with a single key combination.

/*
    This script adds language-sensitive block commenting functionality to the UltraEdit text editor. 
    For details of how to install and use UltraEdit scripts see here:

    http://www.ultraedit.com/support/tutorials_power_tips/ultraedit/scripting_engine_tutorial.html
    
    The script comments out all selected lines of code within the active document, using comment 
    symbols appropriate to the type of file being edited. If the selected text is already commented 
    out, then the comment symbols will be removed.
    
    For the latest version of this script visit:
        http://codebox.org.uk/pages/ultraedit-scripts/block-comments
    
    For licensing information go to: 
        http://codebox.org.uk/pages/about
    
 */
 
if (CODEBOX === undefined){
    var CODEBOX = {}; 
}

CODEBOX.blockComment = function(){
    var doc = UltraEdit.activeDocument;
    var whitespaceRegex = /^\s+|\s+$/g;

 // Some string-processing functions...    
    function trim(txt){
        return txt.replace(whitespaceRegex, '');
    }
    function startsWith(str, start){
        return (str.substring(0, start.length) === start);
    }
    function endsWith(str, end){
        return (str.substring(str.length - end.length) === end);
    }
    
 // An array of 'commenter' objects for handling various different types of file
    var commenterList = [
        { 
            'types' : ['js','java', 'cs', 'php'], 
            'isCommented' : function(txt){
                return startsWith(trim(txt), '\/\/');
            },
            'fnComment' : function(txt){
                return txt.replace(new RegExp("(^|\r\n|\r|\n)", "g"), "$1\/\/");
            },
            'fnUnComment' : function(txt){
                return txt.replace(new RegExp("(^|\r\n|\r|\n)?(\s*)\/\/", "g"), "$1$2");
            }        
        }, { 
            'types' : ['sh', 'pl', 'rb'], 
            'isCommented' : function(txt){
                return startsWith(trim(txt), '#');
            },
            'fnComment' : function(txt){
                return txt.replace(new RegExp("(^|\r\n|\r|\n)", "g"), "$1#");
            },
            'fnUnComment' : function(txt){
                return txt.replace(new RegExp("(^|\r\n|\r|\n)?(\s*)#", "g"), "$1$2");
            }        
        }, { 
            'types' : ['bas', 'frm', 'cls', 'vb', 'vbs', 'vba', 'ctl'], 
            'isCommented' : function(txt){
                return startsWith(trim(txt), '\'');
            },
            'fnComment' : function(txt){
                return txt.replace(new RegExp("(^|\r\n|\r|\n)", "g"), '$1\'');
            },
            'fnUnComment' : function(txt){
                return txt.replace(new RegExp('(^|\r\n|\r|\n)?(\s*)\'', "g"), "$1$2");
            }        
        }, { 
            'types' : ['xml', 'html', 'htm', 'xhtml', 'jsp', 'jspx'], 
            'isCommented' : function(txt){
                var trimmedTxt = trim(txt);
                return startsWith(trimmedTxt, '<!--') && endsWith(trimmedTxt, '-->');
            },
            'fnComment' : function(txt){
                return '<!--' + txt + '-->';
            },
            'fnUnComment' : function(txt){
                return txt.replace(new RegExp("(<!--)((.|\r\n)*)(-->)"), "$2");
            }        
        }
    ]; // commenterList
    
    var commenter = null;
    
 // A utility function - runs fnDoThis() against each element in the array
    function forEach(arr, fnDoThis){
        var l = arr.length, stopNow = false;
        for(var i=0; i<l; i++){
            stopNow = fnDoThis(arr[i], i);
            if (stopNow){
                break;    
            }
        }
    }

 // Check each of the commenter objects to see if it supports the type of file we are editing...
    forEach(commenterList, function(obj){
        forEach(obj.types, function(fileType){
            if (doc.isExt(fileType)){
                commenter = obj;
                return true;    
            }
        });
        return commenter !== null;
    });
    
 // Use the Java style commenter as the default
    commenter = commenter || commenterList[0];
    
    var selection = doc.selection;
    var replacementText;
    
    if ( commenter.isCommented(selection) ){
     // The selected text is already commented, so uncomment it
        replacementText = commenter.fnUnComment(selection);
    } else {
     // The selected text isn't commented already, so comment it out
        replacementText = commenter.fnComment(selection);
    }
    
    doc.deleteText();
    doc.write(replacementText);

};

CODEBOX.blockComment();