//-----------------------------------------------------------------------------
//-------- Copyright (c)2003-2013. All Rights Reserved. -----------------------
//-----------------------------------------------------------------------------
// file implementing MIDI controller 'Denon DN-MC6000'
//Author: Brandon James
//revision 2013 08 09
//----------------------------------------------------------------------------- 
function getLanguageVersion()
{
	return 1;// do not modify this, this should be 1 for all scripts
}
//----------------------------------------------------------------------------- 
function getFileVersion()
{
	return 1;// update this as needed
}
//----------------------------------------------------------------------------- 
// return a user friendly name for the controller supported
function getControllerUserFriendlyName()
{
	return "Denon DN-MC6000_MK2";
}
//----------------------------------------------------------------------------- 
// return the communication type that the controller supports 
// this can be either 'midi' or 'hid' (please return only one of them in case the controller supports both)
function getControllerType()
{
	return 'midi';
}
//----------------------------------------------------------------------------- 
//----------------------------------------------------------------------------- 
//----------------------------------------------------------------------------- 
// preferred way to identify the controller (using the USB device VID and PID -- vendor and product id)
// return false if the controller does not support this kind of identification
// osId -- 0 Windows; 1 MacOSX; 2 Linux; -1 unknown
function getSupportedHidDeviceVID(osId)
{
	return false;
}
//----------------------------------------------------------------------------- 
function getSupportedHidDevicePID(osId)
{
	return false;
}
//----------------------------------------------------------------------------- 
// this is NOT the preferred way to identify the controller but you should use
// it if the controller does not support standard USB VID and PID identification
// return false if the controller does not support this kind of identification
// osId -- 0 Windows; 1 MacOSX; 2 Linux; -1 unknown
function getSupportedHidDeviceName(osId)
{
	return false;
}
//----------------------------------------------------------------------------- 
//----------------------------------------------------------------------------- 
//----------------------------------------------------------------------------- 
// preferred way to identify the controller (if it supports MIDI SysEx)
// return false if the controller does not support this kind of identification
function getSupportedMidiSysExIdString(osId)
{
	// sysex response to 'F0 7E 7F 06 01 F7' (identification request sysex)
	// please note that the response contains 5 bytes in hex format containing
	// the Manufacturer ID (3 bytes) and Model Number (2 bytes)
	// ATTN: the returned value should omit the standard 'F0 7E 00 06 02' message start
	//if(osId==1) return false;
	
	return "004003154E5021";
	// F07E??0602004003154E5015????????F7 -- MC3000 (vid 0x154E pid 0x5015)
	// F07E??060200400303006100????????F7 -- MC6000 (vid 0x154E pid 0x5013)
	// F07E7F0602004003154E502131363032F7 -- MC6000 MK2 (vid 0x154E pid 0x5021)
}
//----------------------------------------------------------------------------- 
// this is NOT the preferred way to identify the controller but you should use
// it if the controller does not support standard MIDI SysEx identification
// return false if the controller does not support this kind of identification
// osId -- 0 Windows; 1 MacOSX; 2 Linux; -1 unknown
function getSupportedMidiDeviceNameForInput(osId)
{
	//return "DN-MC6000";// not working
	//return "DENON DJ Controller Midi";// Windows 7
	return false;
}
//----------------------------------------------------------------------------- 
function getSupportedMidiDeviceNameForOutput(osId)
{
	//return "DN-MC6000";// not working
	//return "DENON DJ Controller Midi";// Windows 7
	return false;
}
//----------------------------------------------------------------------------- 
//----------------------------------------------------------------------------- 
// some variables necessary only for this particular script
var jogWheelsInScratchMode=[0,0,0,0];
var jogWheelsWasDeckPlaying=[0,0,0,0];
var shiftKeyPressed=[0,0,0,0];
//----------------------------------------------------------------------------- 
var autoDjState=0;

// this is called when the controller is initialized and the control is passed to this script
// use this to initialize any variables you might need, the controller' leds, etc
// uniqueId is a unique integer between 0..15 that is guaranteed not to change for 
// a certain opened controller -- please note that there can be many controllers
// of the same type in use at the same time ! Use uniqueId to identify between them
//autoDjState = getValue('autoDj');

function controllerInit(uniqueId)
{
	debug('controllerInit MC6000 MK2 ['+uniqueId+']');// this outputs a string to DebugView app on Win
	//------------------------------------
	callSendAllNotifications(uniqueId, true);// send all notifications to the controller (so that we don't have to manually init all leds/lcd screens)
}
//----------------------------------------------------------------------------- 
// called just before the controller will be deinitialized and the control will go away from the script
// use to power off any powered leds, etc
function controllerDeinit(uniqueId)
{
	debug('controllerDeinit MC6000 MK2 ['+uniqueId+']');
	/*
	for(var i=0; i<4; i++)
	{		
		sendMidi(uniqueId,0xB0,i,0x4B,0x26);// cue
		sendMidi(uniqueId,0xB0,i,0x4B,0x27);// play-pause
	}
	*/
	//------------------------------------
	callSendAllNotifications(uniqueId, false);// send all notifications to the controller (so that we don't have to manually de-init all leds/lcd screens)
}
//----------------------------------------------------------------------------- 
// this is your main target function to implement the controller -- this is called 
// for each and every MIDI message that comes from the controller itself
// return true if the message was processed by the script and false to let it 
// pass thru the software (eg. so it can be assigned by the user using the LEARN function)

function messageReceived(uniqueId,status,channel,data1,data2)
{
	var messageNotProcessed=false;
	
	
    if(channel==2) channel = 1;else if(channel==1) channel = 2;  // use this to switch channel; 2 and 3 instead of multiple if's
	switch(status)
	{
	//-----------------------------------------------
	// controllers: sliders, knobs, jog-wheels, encoders ('moving' things)
		
	case 0xE0: //pitch sliders decks 1-4  
		if(shiftKeyPressed[channel]) // change the musical KEY while Shift key is kept pressed
			call('setDeckPitchKey', channel, 0x7F - data2); 
		else // otherwise just modify the pitch value (normal mode)
			call('setDeckPitch', channel, data2); 
		break;
		break;
		case 0xB0:
			switch(data1)
			{
			// global
			case 0x54: if(data2==0) call('lbMoveCursor', 1);else call('lbMoveCursor', -1); break;
			case 0x97: call('setCfVideo', data2); break;   // cfLink
			case 0x98: call('setCfAudio', data2); break;   // cfLink
			case 0x16: call('setCrossfader', data2); break;   // Audio crossfader
			case 0x17: call('setCFVideo', data2); break;   //Video crossfader
			case 0x19: call('setMasterGain', data2); break;   //master out
			case 0x44: call('setMonitorGain', data2); break;   //headphone level
			case 0x43: call('setCuePgmMix', data2); break;   //headphone Mix
			case 0x45: call('setCFCurve', data2); break;   //cross fader curve
			case 0x22: call('setMicEqLow', data2); break;   //mic eq low
			case 0x23: call('setMicEqMid', data2); break;   //mic eq mid
			case 0x21: call('setMicEqHigh', data2); break;   //mic eq high
			
			case 0x1C: 
					if (getValue('sampler1loaded'))
						call('samplerVolume', 1, data2);
					if (getValue('sampler2loaded'))
						call('samplerVolume', 2, data2);
					if (getValue('sampler3loaded'))
						call('samplerVolume', 3, data2);
					if (getValue('sampler4loaded'))
						call('samplerVolume', 4, data2);
					if (getValue('sampler5loaded'))
						call('samplerVolume', 5, data2);
					if (getValue('sampler6loaded'))
						call('samplerVolume', 6, data2);
					if (getValue('sampler7loaded'))
						call('samplerVolume', 7, data2);
					if (getValue('sampler8loaded'))
						call('samplerVolume', 8, data2);
					
			break; //sampler 1-4 volume
			
		// decks		
		
		//vol sliders
		case 0x05: call('setDeckVolume', 0, data2); break; // deck 1
		case 0x15: call('setDeckVolume', 3, data2); break; // deck 2
		case 0x0B: call('setDeckVolume', 1, data2); break; // deck 3
		case 0x10: call('setDeckVolume', 2, data2); break; // deck 4
		
		// deck gain
		case 0x01: call('setDeckGain', 0, data2); break; // deck 1
		case 0x11: call('setDeckGain', 3, data2); break; // deck 2
		case 0x07: call('setDeckGain', 1, data2); break; // deck 3
		case 0x0C: call('setDeckGain', 2, data2); break; // deck 4
		
		//eq knob high
		case 0x02: call('setDeckEqHigh', 0, data2); break; // deck 1
		case 0x12: call('setDeckEqHigh', 3, data2); break; // deck 2
		case 0x08: call('setDeckEqHigh', 1, data2); break; // deck 3
		case 0x0D: call('setDeckEqHigh', 2, data2); break; // deck 4
		
		//eq knob mid
		case 0x03: call('setDeckEqMid', 0, data2); break; // deck 1
		case 0x13: call('setDeckEqMid', 3, data2); break; // deck 2
		case 0x09: call('setDeckEqMid', 1, data2); break; // deck 3
		case 0x0E: call('setDeckEqMid', 2, data2); break; // deck 4
		
		//eq knob low
		case 0x04: call('setDeckEqLow', 0, data2); break; // deck 1
		case 0x14: call('setDeckEqLow', 3, data2); break; // deck 2
		case 0x0A: call('setDeckEqLow', 1, data2); break; // deck 3
		case 0x0F: call('setDeckEqLow', 2, data2); break; // deck 4
		
		// Deck FX
		case 0x55: call('deckFxFlangerDW', 0, data2); break; // Flanger DW 1
		case 0x56: call('deckFxEchoDW', 0, data2); break; // Echo DW 1
		case 0x57: call('deckFxPanDW', 0, data2); break; // AutoPan DW 1 
		case 0x58: call('deckFxBeatwawDW', 0, data2); break; // beatwaw DW 1 // ENCODER

		case 0x59: call('deckFxFlangerDW', 1, data2); break; // Flanger DW 2 
		case 0x5A: call('deckFxEchoDW', 1, data2); break; // Echo DW 2 
		case 0x5B: call('deckFxPanDW', 1, data2); break; // AutoPan DW 2 
		case 0x5C: call('deckFxBeatwawDW', 1, data2); break; // beatwaw DW 2 // ENCODER
	
		case 0x67: call('setDeckCutoff', 1, data2); break; // cutoff filter
	    case 0x66: call('setDeckCutoff', 0, data2); break; // cutoff filter
	    //case 0x66: call('setDeckCutoff', 2, data2); break; // cutoff filter
		//case 0x67: ('setDeckCutoff', 3, data2); break; // cutoff filter
	
	
		
		//platters
			case 0x51: // params: (deck, increment, total positions per complete revolution) 
			var val1 = data2-0x40;
			if(jogWheelsInScratchMode[channel]) call('scratchDeckJW', channel, val1, 512);else call('moveDeckJogWheel', channel, val1, 512);
			break;	
		
		default: messageNotProcessed = true;
		}
		break;
	//-----------------------------------------------
	// note on/off: buttons, switches ('pressing' things)
	case 0x80:
	case 0x90:
		if(data2==0x40) data2 = 0x7F;
		switch(data1)
		{
		// global
		case 0x47: call('phonesSplit', data2); break; //cue split
		case 0x26: call('micOnAir', data2); break;   //mic eq high
		case 0x2A: call('micTalkOver', data2); break; //ducking
		case 0x4D: call('setAutoDj', data2); break; //Auto DJ
 		case 0x4C: call('showCfg', data2); break; //Preferences window
		case 0x30: if(data2>0x3F) call('lbBrowserSelect', data2); break; //back button
        case 0x29: if(data2>0x3F) call('lbListSelect', data2); break; //forward button
        case 0x64: if(data2>0x3F) call('mixNext', data2); break; //Panel button
		case 0x28: if(data2>0x3F) call('lbToggleSelect', data2); break; //Knob press
		
		
		// decks
		case 0x60: shiftKeyPressed[channel] = data2; break;// Shift for deck 1, 3 (channels 0,1)
		case 0x61: shiftKeyPressed[channel] = data2; break;// Shift for deck 2, 4 (channels 2,3)
		
		case 0x62: call('deckLBLoad', channel, data2); break; //load deck 1, 3 
		case 0x63: call('deckLBLoad', channel, data2); break; //load deck 2, 4
		case 0x01: call('deckMonitor', 0, data2); break; //deck 1 pfl
		case 0x02: call('deckMonitor', 1, data2); break; //deck 2 pfl
		case 0x05: call('deckMonitor', 2, data2); break; //deck 3 pfl
		case 0x07: call('deckMonitor', 3, data2); break; //deck 4 pfl
		//case 0x42: call('deckCue', channel, data2); break; //cue decks 1-4		   
		case 0x11: call('deckSkipBeatPrev', channel, data2); break; //beat skip back decks 1-4				   
		case 0x10: call('deckSkipBeatNext', channel, data2); break; //beat skip back decks 1-4				
		case 0x37: call('deckLoopInEnd', channel, data2); break; //loop in / end decks 1-4					   
		case 0x39: if(!getValue('looping', channel)) call('deckLoopInEnd', channel, data2);else call('deckLoopExit', channel, data2); break; //loop out or exit
		case 0x1D: call('deckLoop4', channel, data2); break; //auto 4 beat loop / end decks 1-4				   
		case 0x69: call('deckLoopLess', channel, data2); break; //loop less  decks 1-4
		case 0x6A: call('deckLoopMore', channel, data2); break; //loop more decks 1-4					   
		case 0x15: call('deckFxFlanger', 0, data2); break; //decks flanger 1/3
		case 0x55: call('deckFxFlanger', 1, data2); break; //decks flanger 2/4
		case 0x13: call('deckFxPan', 0, data2); break; //decks pan 1/3
		case 0x53: call('deckFxPan', 1, data2); break; //decks pan 2/4
		case 0x12: call('deckFxEcho', 0, data2); break; //decks echo 1/3
		case 0x52: call('deckFxEcho', 1, data2); break; //decks echo 2/4
		case 0x14: call('deckFxBeatwaw', 1, data2); break; //decks beatwaw 1/3
		case 0x54: call('deckFxBeatwaw', 0, data2); break; //decks beatwaw 2/41
		// samplers (left side 1-4; right side 5-8;)
		case 0x21: 
			if(channel==0) call('samplerInstant', 1, data2);else call('samplerInstant', 5, data2); 
			//sendMidi(uniqueId,0xB0,0,(data2 ? 0x4A : 0x4B),0x19);
			break; //sampler 1/5 plays while holding the button
		case 0x22: 
			if(channel==0) call('samplerInstant', 2, data2);else call('samplerInstant', 6, data2); 
			//sendMidi(uniqueId,0xB0,0,(data2 ? 0x4A : 0x4B),0x1B);
			break; //sampler 2/6 plays while holding the button
		case 0x23: 
			if(channel==0) call('samplerInstant', 3, data2);else call('samplerInstant', 7, data2); 
			//sendMidi(uniqueId,0xB0,0,(data2 ? 0x4A : 0x4B),0x1D);
			break; //sampler 3/7 plays while holding the button
		case 0x24: 
			if(channel==0) call('samplerInstant', 4, data2);else call('samplerInstant', 8, data2); 
			//sendMidi(uniqueId,0xB0,0,(data2 ? 0x4A : 0x4B),0x20);
			break; //sampler 4/8 plays while holding the button

		//dual functions bend down / search left		
		case 0x0D:
		if(shiftKeyPressed[channel])
			call('deckSearchLeft', channel, data2); //Search left deck 1-4
		else 
			call('deckBendDown', channel, data2); //bend down deck 1-4
			break;
		break;
		
		//dual functions bend up / search right
		case 0x0C:
		if(shiftKeyPressed[channel])
			call('deckSearchRight', channel, data2); //Search right deck 1-4
		else 
			call('deckBendUp', channel, data2); //bend up deck 1-4
			break;
		break;
		
		//dual functions match / sync
		case 0x6B:
		if(shiftKeyPressed[channel])
			call('deckMatch', channel, data2); //match deck 1 - 4
		else
			call('deckSync' ,channel, data2); //sync deck 1 - 4
			break;
		break;
		
		//dual functions key lock / pitch reset
		case 0x06:
		if(shiftKeyPressed[channel])
			call('deckResetPitch', channel, data2); //reset Pitch deck 1 - 4
		else
			call('deckKeyLock', channel, data2); //key lock deck 1 - 4
			break;
		break;
		
		//dual functions set cue1 / clear cue1 deck 1 - 4
		case 0x17:
		if(shiftKeyPressed[channel])
			call('deckCuePos1Clear', channel, data2);
		else 
			call('deckCuePos1', channel, data2);
			break;
		break;
		
		//dual functions set cue2 / clear cue2 deck 1 - 4
		case 0x18:
		if(shiftKeyPressed[channel])
			call('deckCuePos2Clear', channel, data2);
		else 
			call('deckCuePos2', channel, data2);
			break;
		break;
		
		//dual functions set cue3 / clear cue3 deck 1 - 4
		case 0x19:
		if(shiftKeyPressed[channel])
			call('deckCuePos3Clear', channel, data2);
		else 
			call('deckCuePos3', channel, data2);
			break;
		break;
		
		//dual functions set cue4 / clear cue4 deck 1 - 4
		case 0x20:
		if(shiftKeyPressed[channel])
			call('deckCuePos4Clear', channel, data2);
		else 
			call('deckCuePos4', channel, data2);
			break;
		break;

		//dual functions play pause / play reverse
		case 0x43:
		if(shiftKeyPressed[channel])
			call('deckReverse', channel, data2); //reverse deck 1-4
		else
			call('deckPlayPause', channel, data2); //play pause
			break;
		break;
		
		//dual functions cue / break
		case 0x42:
		if(shiftKeyPressed[channel])
			call('deckBrake', channel, data2); //break deck 1-4
		else
			call('deckCue', channel, data2); break; //cue decks 1-4
			break;
		break;
		
		//Jog wheels
		case 0x51: 
			jogWheelsInScratchMode[channel] = (jogWheelsInScratchMode[channel]+1) % 2; // keep the remainder to toggle between scratch mode "0" or jog bend mode "1"
			call('holdDeckJogWheel', channel, jogWheelsInScratchMode[channel]);
			

		default: messageNotProcessed = true;
		}
		break;
	//-----------------------------------------------
	default: messageNotProcessed = true;
	}
	if(messageNotProcessed) debug('messageReceived ['+uniqueId+'] - status:'+status+' channel:'+channel+' data1:'+data1+' data2:'+data2);
	return !messageNotProcessed;
}
//----------------------------------------------------------------------------- 
// this is called by the software whenever something important changes (eg. play status, song changed, etc)
// depending on the notification type it may refer to a global event (deck is -1) or a specific deck (deck >= 0)
// and can contain any/all of the parameters: param 1 is an integer, param 2 is a float, param 3 is a string
function notificationReceived(uniqueId,name,deck,param1,param2,param3)
{
	//debug('notif ['+uniqueId+'] name='+name + ' deck='+deck + ' p1(int)='+param1 + ' p2(float)='+param2 + ' p3(str)='+param3);
	if(deck<4)
	{
		
		/*if(getValue('sampler1playing'))
					sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x19); //lights the sampler1 button while playing
		//else if (getValue('sampler1loaded'))  
					//sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1A); //dimmers the sampler1 button if sample is loaded
		if(getValue('sampler2playing'))
					sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1B); //lights the sampler2 button while playing
		//else if (getValue('sampler2loaded'))
			//		sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1C); //dimmers the sampler2 button if sample is loaded
		if(getValue('sampler3playing'))
					sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1D); //lights the sampler3 button while playing
		//else if (getValue('sampler3loaded'))
			//		sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1F); //dimmers the sampler3 button if sample is loaded
		if(getValue('sampler4playing'))
					sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x20); //lights the sampler4 button while playing
		//else if (getValue('sampler4loaded'))
			//		sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x21); //dimmers the sampler4 button if sample is loaded
	*/
		/*if(name=='sampler1') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x19); //sampler1
		if(name=='sampler2') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1B); //sampler2
		if(name=='sampler3') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1D); //sampler3
		if(name=='sampler4') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x20); //sampler4
		if(name=='sampler5') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x19); //sampler5
		if(name=='sampler6') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x1B); //sampler6
		if(name=='sampler7') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x1D); //sampler7
		if(name=='sampler8') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x20); //sampler8
		*/
		if(name=='sampler1') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1A); //sampler1
		if(name=='sampler2') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1C); //sampler2
		if(name=='sampler3') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x1F); //sampler3
		if(name=='sampler4') sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x21); //sampler4
		if(name=='sampler5') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x1A); //sampler5
		if(name=='sampler6') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x1C); //sampler6
		if(name=='sampler7') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x1F); //sampler7
		if(name=='sampler8') sendMidi(uniqueId,0xB0,2,(param1 ? 0x4A : 0x4B),0x21); //sampler8
		
			
		if(name=='monitor')
				{
					if(deck==0)	sendMidi(uniqueId,0xB0,0,(param1 ? 0x50 : 0x51),0x45);	
					if(deck==1)	sendMidi(uniqueId,0xB0,0,(param1 ? 0x50 : 0x51),0x4B);
					if(deck==2)	sendMidi(uniqueId,0xB0,0,(param1 ? 0x50 : 0x51),0x51);
					if(deck==3)	sendMidi(uniqueId,0xB0,0,(param1 ? 0x50 : 0x51),0x57);
				}
		
		if(name=='fxFlanger') 
			{
				if(deck==0) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x5C);
				if(deck==1) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x60);
			}
		
		if(name=='fxEcho') 
			{
				if(deck==0) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x5D);
				if(deck==1) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x61);
			}
		
		if(name=='fxPan') 
			{
				if(deck==0) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x5E);
				if(deck==1) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x62);
			}
		
		if(name=='fxBeatwaw') 
			{
				if(deck==0) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x5F);
				if(deck==1) sendMidi(uniqueId,0xB0,0,(param1 ? 0x4A : 0x4B),0x63);
			}
			
					
		if(deck==2) deck = 1;else if(deck==1) deck = 2; // switch to deck specific channels
			{
			if(name=='cue') 		 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x26); // cue
			if(name=='play') 		 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x27); //play
			if(name=='brake')		 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x26); //brake
			if(name=='cuepos1') 	 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x11); //cue 1
			if(name=='cuepos2') 	 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x13); //cue 2
			if(name=='cuepos3') 	 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x15); //cue 3
			if(name=='cuepos4') 	 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x17); //cue 3
			if(name=='loopIn') 	 	 sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x24); //loop in
		if(name=='looping') 	 
				{
				sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4C : 0x4B),0x24); //loop in led
				sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4C : 0x4B),0x40); //loop out led
				sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x2B); //loop out led
				}
			if(name=='onbeat') 		sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x09);
			if(name=='keyLock') 	sendMidi(uniqueId,0xB0,deck,(param1 ? 0x4A : 0x4B),0x08);
			}
	}
}
//----------------------------------------------------------------------------- 
var vuStatus=[[0,0,0,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,0,0,0]];
var vuCurrent=[-36,-28,-20,-16,-12,-8,-6,-4,-2,-1];
function setVUValueForDeck(uniqueId, deck, dbValue)
{
	var baseLed = 0x07;// deck 1
	if(deck==1) baseLed = 0x37;// deck 2
	if(deck==2) baseLed = 0x17;// deck 3
	if(deck==3) baseLed = 0x27;// deck 4
	var param1=0;
	for(var i=0; i<10; i++)
	{
		if(dbValue>=vuCurrent[i]) param1 = 1;else param1 = 0;
		if(param1 != vuStatus[deck][i])
		{
			vuStatus[deck][i] = param1;
			sendMidi(uniqueId,0xB0,0,(param1 ? 0x50 : 0x51), baseLed + i);// VU Led
		}
	}
}
//----------------------------------------------------------------------------- 
// this is called from time to time by the software (several times per second)
// (it is guaranteed that 'timerTick' will get executed ALWAYS right after notificationReceived)
function timerTick(uniqueId)
{
	//debug('timerTick ['+uniqueId+']');
	for(var deck=0; deck<4; deck++)
	{
		var dbValue = getValue('vumeterDeck', deck);// float dB
		setVUValueForDeck(uniqueId, deck, dbValue);
	}
}
//----------------------------------------------------------------------------- 
//  		var vuDeck = getValue('vumeterDeck', i);// float dB
	//	sendMidi(uniqueId,0xB0,i+2,17,getMIDIValueForVU(vuDeck));
	// sendMidi(uniqueId,0xB0,0,(getValue('monitor', 0) ? 0x50 : 0x51),0x45);
	
	
	
	