Edit in JSFiddle

SS = {
 
    re: {
         signal: /SIGNAL_(.*)/
        ,slot: /SLOT_(.*)/
    }
    
    ,setup: function(target){
        
        var i, result, name;
        
        target._listeners = {};
        
        for(i in target){
            if(!target.hasOwnProperty(i)) continue;
                
            result = i.match(SS.re.signal);
            
            if(result !== null){
                // found a signal
                name = result[1];
                
                console.log('found signal', name);

                target[name] = name;
                if(!target._listeners[name]) target._listeners[name] = [];
                
                delete target[i];
            }
            
            result = i.match(SS.re.slot);
            
            if(result !== null){
                // found a slot
                name = result[1];
                
                console.log('found slot', name);
                
                // remove SLOT_ prefix
                target[name] = target[i];
                delete target[i];
            }
        }
        
        // setup helper methods
        for(i in this){
            if(this.hasOwnProperty(i) && i !== 'setup' && i !== 're'){
                target[i] = this[i];      
            }
        }
        
        console.log('target after setup', target);
        
        return target;
    }
               
               
    ,connect: function(signal, slot){
        if(typeof slot !== 'function') throw new Error('Slot must be a function');
        if(this[signal] !== signal) throw new Error('Signal not found: ' + signal);
                
        if(!this._listeners) this._listeners = {};
        if(!this._listeners[signal]) this._listeners[signal] = [];
        
        this._listeners[signal].push(slot);
    }
    ,disconnect: function(){}
    ,signal: function(sigName){
        console.log('told to fire signal: ', arguments);
        
        var args = Array.prototype.slice.call(arguments, 1);
        
        if(this._listeners[sigName])
        for(var i = 0; i < this._listeners[sigName].length; i++){
            this._listeners[sigName][i].apply(this, args);
        }
    }
    //,emit: function(sig){}
};

        
        
        
        (function(exports){
            
            function MyObj(){}
            MyObj.prototype = {
                
                
                SLOT_refresh: function(data){ console.log('told to refresh', arguments); }
                
                // neat, you can describe what the signals do here
                ,SIGNAL_READY: 'indicates that the obj is ready for battle'
                ,SIGNAL_DATA: 'the obj has data ready to dispatch'
                ,SIGNAL_DIE: 'the obj has been killed or will be killed after dispatch'
                
                ,doSomethingAsync: function(){
                    var self = this;
                    setTimeout(function(){
                        self.signal(self.READY, 'behold! i am data!', 'so am i');
                    }, 1000);
                }    
                
            };
            
            
            SS.setup(MyObj.prototype);
            window.MyObj = MyObj;
            
        })(window);

        var my = new MyObj();
        var myToo = new MyObj();
        my.doSomethingAsync();
        my.connect(my.READY, myToo.refresh);
        console.log(my, MyObj, MyObj.prototype);