XAP 800 COMM and UI Module
staticattic
Junior Member
A few months ago I asked for help parsing data from 2 XAP 800's and 1 XAP TH2. AMXJeff was kind enough to provide a Function he had written to parse the data. Using his Function as a model, I thought I would take a crack at making a UI and COMM module for those same XAP's for practice. Thought I would post what I had so far, for feedback. Everything compiles ok, but I have not tried any of it out yet. For all I know, the XAP's might burst into flames as soon as a load this. I am hoping for feedback as far as what I should change, what possibly won't work, if I'm am working in the right direction, etc. I still need to finish the TH2 portion. I am working that right now. Here's what I have so far. Any feedback would be much appreciated. Thanks.
First the delarations in the main program:
The COMM Module. If I am correct, SEND_STRING's come from the COMM and SEND_COMMAND's come from the UI. I also have a FOR loop in here that I am not 100% sure about:
And finally, the all important User Interface:
First the delarations in the main program:
DEFINE_DEVICE dvMaster = 0:1:0 //Master NetLinx // Desk Touchpanel dvTP1 = 10001:1:0 dvTP1_XAP = 10001:2:0 // Rack Touchpanel dvTP2 = 10002:1:0 dvTP2_XAP = 10002:2:0 // Podium Touchpanel dvTP3 = 10003:1:0 dvTP3_XAP = 10003:2:0 DEFINE_START // User Interface Modules DEFINE_MODULE 'XAP_Functions_UI' XAP_UI_1(vdvXAP,dvTP1_XAP,ClearOne_XAP800_BUTTONS,ClearOne_XAPTH2_BUTTONS) DEFINE_MODULE 'XAP_Functions_UI' XAP_UI_2(vdvXAP,dvTP2_XAP,ClearOne_XAP800_BUTTONS,ClearOne_XAPTH2_BUTTONS) DEFINE_MODULE 'XAP_Functions_UI' XAP_UI_3(vdvXAP,dvTP3_XAP,ClearOne_XAP800_BUTTONS,ClearOne_XAPTH2_BUTTONS) // COMM Modules DEFINE_MODULE 'XAP_Functions_COMM' XAP_COMM(vdvXAP, dvXAP)
The COMM Module. If I am correct, SEND_STRING's come from the COMM and SEND_COMMAND's come from the UI. I also have a FOR loop in here that I am not 100% sure about:
MODULE_NAME='XAP_Functions_COMM'(DEV vdvXAP, DEV dvXAP)
(***********************************************************)
(* FILE CREATED ON: 01/06/2009 AT: 11:12:18 *)
(***********************************************************)
(***********************************************************)
(***********************************************************)
(* FILE_LAST_MODIFIED_ON: 01/07/2009 AT: 10:17:16 *)
(***********************************************************)
(* System Type : NetLinx *)
(***********************************************************)
(* REV HISTORY: *)
(***********************************************************)
(*
$History: $
*)
(***********************************************************)
(* NOTES: *)
(* 1. 2 XAP 800's and 1 XAP TH2 *)
(* 2. 13 Mics total. Mics 1 - 10 are the floor mics. *)
(* 11 - 13 are the ceiling mics. *)
(* 3. The Touchpanel DOES NOT provide any funtionality *)
(* for the XAP's other than Master volume controls *)
(* and mics on or off. *)
(* 4. Only 2 mic mute buttons. 1 for all floor mics and *)
(* and 1 for all ceiling mics. No level controls. *)
(* Mics are either on or off. *)
(* *)
(* *)
(* *)
(* *)
(* *)
(* *)
(***********************************************************)
(***********************************************************)
(* DEVICE NUMBER DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_DEVICE
(***********************************************************)
(* CONSTANT DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_CONSTANT
(***********************************************************)
(* DATA TYPE DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_TYPE
STRUCTURE _XAP800 // Both XAPs
{
CHAR bMUTE_M[8];
CHAR bMUTE_P[8];
FLOAT fGAIN_P[8];
}
(***********************************************************)
(* VARIABLE DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_VARIABLE
VOLATILE FLOAT flGain
VOLATILE CHAR cXAP_BUFF[100] //Use this buffer for all XAP comms
VOLATILE INTEGER nHook //1 = On Hook, 0 =Off Hook
VOLATILE CHAR XAP800_1_ADDRESS[] = '#50';
VOLATILE CHAR XAP800_2_ADDRESS[] = '#51';
VOLATILE CHAR XAP800_3_ADDRESS[] = '#60';
VOLATILE INTEGER nFloor_Mic_Status
// XAPs
VOLATILE _XAP800 uXAP800_1;
VOLATILE _XAP800 uXAP800_2;
PERSISTENT FLOAT flLevel_Bargraph
// Telco
VOLATILE INTEGER nTelcoButtons
VOLATILE INTEGER nCOUNTER
VOLATILE INTEGER ClearOne_XAP800_BUTTONS_INDEX
VOLATILE CHAR cPHONE_NUMBER[40] // STORES THE PHONE NUMBER TO BE DIALED (CHAR FROM 0..9, #, *)
VOLATILE CHAR cLAST_NUMBER[40] // STORES THE LAST NUMBER DIALED
VOLATILE INTEGER nSPEED_DIAL // STORES THE SPEED DIAL SLOT ENTERED BY USER
PERSISTENT CHAR cNUMBER_FOR_REDIAL[40] // STORES THE LAST NUMBER DIALED
PERSISTENT CHAR cSPEED_DIAL_1[40]
PERSISTENT CHAR cSPEED_DIAL_2[40]
PERSISTENT CHAR cSPEED_DIAL_3[40]
(***********************************************************)
(* LATCHING DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_LATCHING
(***********************************************************)
(* MUTUALLY EXCLUSIVE DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_MUTUALLY_EXCLUSIVE
(***********************************************************)
(* SUBROUTINE/FUNCTION DEFINITIONS GO BELOW *)
(***********************************************************)
(* EXAMPLE: DEFINE_FUNCTION <RETURN_TYPE> <NAME> (<PARAMETERS>) *)
(* EXAMPLE: DEFINE_CALL '<NAME>' (<PARAMETERS>) *)
DEFINE_FUNCTION XAPs_ParseResponse()
{
LOCAL_VAR CHAR cMSG[50], cGroup[1], cTempChannel[2], cChannel
LOCAL_VAR INTEGER nTELE_RINGING
cMSG = REMOVE_STRING(cXAP_BUFF, "13,10",1)
IF (LENGTH_STRING(cMSG) != 0) //If anything is in string cMSG
{
SET_LENGTH_STRING(cMSG,LENGTH_STRING(cMSG) - 2) //removes the CR and LF
SELECT
{
ACTIVE(FIND_STRING(cMSG, "XAP800_1_ADDRESS,' MUTE '",1)):
{
REMOVE_STRING (cMSG,"XAP800_1_ADDRESS,' MUTE '",1)
cTempChannel = REMOVE_STRING(cMSG,' ',1)
cChannel = ATOI(cTempChannel)
cGroup = GET_BUFFER_STRING(cMSG,2)
SWITCH (cGroup)
{
CASE 'M': // Floor mics 1 - 8 are on this XAP.
{
uXAP800_1.bMUTE_M[cChannel] = cMsg = '1';
IF (FIND_STRING(uXAP800_1.bMUTE_M,'0',1))
{
}
ELSE
{
}
}
CASE 'P':
{
cChannel = cTempChannel[1] - 'A' + 1;
uXAP800_1.bMUTE_P[cChannel] = cMsg = '1';
}
}
}
ACTIVE (FIND_STRING(cMsg, "XAP800_1_ADDRESS,' GAIN '",1)): //#50 GAIN A P xx A
{
REMOVE_STRING(cMsg,"XAP800_1_ADDRESS,' GAIN '",1); // cMSG = A P xx A
IF (FIND_STRING(cMsg,'A',1)) // I don't care about Processor B. Processor B will always match A
{
cTempChannel = REMOVE_STRING(cMsg,' ',1); // cTempChannel = A
cChannel = ATOI(cTempChannel); // cChannel = A
cGroup = GET_BUFFER_STRING(cMsg,2); // cMSG = xx A cGroup = P
flGain = ATOF(cMsg); // xx (any non-numeric characters are ignored)
SWITCH (cGroup)
{
CASE 'P':
{
cChannel = cTempChannel[1] - 'A' + 1;
uXAP800_1.fGAIN_P[cChannel] = flGain;
flLevel_Bargraph = ((100*(flGain + 65)) / 85)
SEND_STRING vdvXAP, "'VOLUME=',flLevel_Bargraph"
}
}
}
}
ACTIVE(FIND_STRING(cMSG, "XAP800_2_ADDRESS,' MUTE '",1)):
{
REMOVE_STRING (cMSG,"XAP800_2_ADDRESS,' MUTE '",1)
cTempChannel = REMOVE_STRING(cMSG,' ',1)
cChannel = ATOI(cTempChannel)
cGroup = GET_BUFFER_STRING(cMSG,2)
SWITCH (cGroup)
{
CASE 'M': // Floor Mics 9 and 10 and Ceiling Mics 1 - 3 are on this XAP.
{
uXAP800_2.bMUTE_M[cChannel + 8] = cMsg = '1';
IF (FIND_STRING(uXAP800_2.bMUTE_M,'0',1))
{
}
ELSE
{
}
}
CASE 'P':
{
cChannel = cTempChannel[1] - 'A' + 1;
uXAP800_1.bMUTE_P[cChannel] = cMsg = '1';
}
}
}
ACTIVE (FIND_STRING(cMsg, "XAP800_2_ADDRESS,' GAIN '",1)): // Currently no Gain controls for this XAP.
{
REMOVE_STRING(cMsg,"XAP800_2_ADDRESS,' GAIN '",1);
cTempChannel = REMOVE_STRING(cMsg,' ',1);
cChannel = ATOI(cTempChannel);
cGroup = GET_BUFFER_STRING(cMsg,2);
flGain = ATOF(cMsg);
SWITCH (cGroup)
{
CASE 'P':
{
cChannel = cTempChannel[1] - 'A' + 1;
uXAP800_2.fGAIN_P[cChannel] = flGain;
}
}
}
ACTIVE(FIND_STRING(cMSG, "XAP800_3_ADDRESS,' TE '",1)):
{
REMOVE_STRING (cMSG,"XAP800_3_ADDRESS,' TE 1 '",1)
nHook = ATOI(RIGHT_STRING(cMSG,1))
}
ACTIVE(FIND_STRING(cMSG, "XAP800_3_ADDRESS,' RING 1'",1)):
{
REMOVE_STRING (cMSG,"XAP800_3_ADDRESS,' RING 1'",1)
nTELE_RINGING = ATOI(RIGHT_STRING(cMSG,1))
SEND_STRING vdvXAP,"'RINGING=',nTELE_RINGING"
//IF (nTELE_RINGING = 1)
// {
// //SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%CF 00'"
// //SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%J 5,%Tincoming call...'"
// }
// IF (nTELE_RINGING = 0)
// {
// //SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%CF 53'"
// //SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%J 5,%T'"
// }
}
//ACTIVE(FIND_STRING(cMSG, "XAP800_3_ADDRESS,' STOREDIAL '",1)): // Verify actual feedback from the XAP before making this section.
// {
// REMOVE_STRING (cMSG,"XAP800_3_ADDRESS,' RING 1'",1)
// nTELE_RINGING = ATOI(RIGHT_STRING(cMSG,1))
// SEND_COMMAND TOUCHPANEL,"'@PPN-IP Phone Controls'"
// IF (nTELE_RINGING = 1)
// {
// SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%CF 00'"
// SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%J 5,%Tincoming call...'"
// }
// IF (nTELE_RINGING = 0)
// {
// SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%CF 53'"
// SEND_COMMAND TOUCHPANEL,"'^BMF-8,0,%J 5,%T'"
// }
// }
}
}
}
(***********************************************************)
(* STARTUP CODE GOES BELOW *)
(***********************************************************)
DEFINE_START
CREATE_BUFFER dvXAP, cXAP_BUFF
(***********************************************************)
(* THE EVENTS GO BELOW *)
(***********************************************************)
DEFINE_EVENT
DATA_EVENT[dvXAP]
{
ONLINE:
{
SEND_COMMAND dvXAP,"'TSET BAUD 9600,N,8,1 485 DISABLE'"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 1 M 1',13" // #50 1 - 8 and #51 1 - 2 are the floor mics
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 2 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 3 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 3 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 4 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 5 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 6 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 7 M 1',13"
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE 8 M 1',13"
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 1 M 1',13"
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 2 M 1',13"
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 3 M 1',13" // #51 3 - 5 are the ceiling mics
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 4 M 1',13"
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 5 M 1',13"
SEND_STRING dvXAP,"XAP800_3_ADDRESS,' HOOKD 1 500',13" // Sets the Hook Flash duration to 500ms
SEND_STRING dvXAP,"XAP800_3_ADDRESS,' TE 1 0',13" // Places the phone on Hook
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' GAIN A P',13" // Queries the current volume
}
STRING:
{
WHILE (FIND_STRING(cXAP_BUFF,"13,10",1))
{
XAPs_ParseResponse()
}
}
}
DATA_EVENT[vdvXAP]
{
COMMAND:
{
LOCAL_VAR CHAR cCommand[30]
cCommand = REMOVE_STRING(DATA.TEXT, '=',1)
SWITCH(cCommand)
{
CASE 'Floor_Mics=': // Toggle
{
LOCAL_VAR INTEGER nXAP_1_Count
FOR(nXAP_1_Count = 1; nXAP_1_Count<=8; nXAP_1_Count++)
{
SEND_STRING dvXAP,"XAP800_1_ADDRESS,' MUTE ',ITOA(nXAP_1_Count),'1 M 2',13" // #50 1 - 8 and #51 1 - 2 are the floor mics
}
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 1 M 2',13"
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 2 M 2',13"
}
CASE 'Ceiling_Mics=': // Toggle
{
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 3 M 2',13" // #51 3 - 5 are the ceiling mics
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 4 M 2',13"
SEND_STRING dvXAP,"XAP800_2_ADDRESS,' MUTE 5 M 2',13"
}
CASE 'Gain=':
{
IF (FIND_STRING(DATA.TEXT,'UP',1))
{
flGain=flGain + 1
IF(flGain<=20)
{
SEND_STRING dvXAP,"'#50 GAIN A P ',FTOA(flGain),'A',13"
SEND_STRING dvXAP,"'#50 GAIN B P ',FTOA(flGain),'A',13"
}
ELSE
{
SEND_STRING dvXAP,"'#50 GAIN A P 20 A',13"
SEND_STRING dvXAP,"'#50 GAIN B P 20 A',13"
}
}
IF (FIND_STRING(DATA.TEXT,'DOWN',1))
{
flGain=flGain - 1
IF(flGain>=-65)
{
SEND_STRING dvXAP,"'#50 GAIN A P ',FTOA(flGain),'A',13"
SEND_STRING dvXAP,"'#50 GAIN B P ',FTOA(flGain),'A',13"
}
ELSE
{
SEND_STRING dvXAP,"'#50 GAIN A P -65 A',13"
SEND_STRING dvXAP,"'#50 GAIN B P -65 A',13"
}
}
IF (FIND_STRING(DATA.TEXT,'MUTE',1))
{
SEND_STRING dvXAP,"'#50 MUTE A P 2',13"
SEND_STRING dvXAP,"'#50 MUTE B P 2',13"
}
}
}
}
}
(***********************************************************)
(* THE ACTUAL PROGRAM GOES BELOW *)
(***********************************************************)
DEFINE_PROGRAM
(***********************************************************)
(* END OF PROGRAM *)
(* DO NOT PUT ANY CODE BELOW THIS COMMENT *)
(***********************************************************)
And finally, the all important User Interface:
MODULE_NAME='XAP_Functions_UI'(DEV vdvXAP, DEV dvTP, INTEGER ClearOne_XAP800_BUTTONS[], INTEGER ClearOne_XAPTH2_BUTTONS[])
(***********************************************************)
(* FILE CREATED ON: 12/12/2008 AT: 09:45:13 *)
(***********************************************************)
(***********************************************************)
(***********************************************************)
(* FILE_LAST_MODIFIED_ON: 01/07/2009 AT: 10:29:10 *)
(***********************************************************)
(* System Type : NetLinx *)
(***********************************************************)
(* REV HISTORY: *)
(***********************************************************)
(*
$History: $
*)
(***********************************************************)
(* DEVICE NUMBER DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_DEVICE
(***********************************************************)
(* CONSTANT DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_CONSTANT
(***********************************************************)
(* DATA TYPE DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_TYPE
(***********************************************************)
(* VARIABLE DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_VARIABLE
VOLATILE INTEGER nXAP_Level
VOLATILE INTEGER nPanelOffline = false
(***********************************************************)
(* LATCHING DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_LATCHING
(***********************************************************)
(* MUTUALLY EXCLUSIVE DEFINITIONS GO BELOW *)
(***********************************************************)
DEFINE_MUTUALLY_EXCLUSIVE
(***********************************************************)
(* SUBROUTINE/FUNCTION DEFINITIONS GO BELOW *)
(***********************************************************)
(* EXAMPLE: DEFINE_FUNCTION <RETURN_TYPE> <NAME> (<PARAMETERS>) *)
(* EXAMPLE: DEFINE_CALL '<NAME>' (<PARAMETERS>) *)
(***********************************************************)
(* STARTUP CODE GOES BELOW *)
(***********************************************************)
DEFINE_START
(***********************************************************)
(* THE EVENTS GO BELOW *)
(***********************************************************)
DEFINE_EVENT
DATA_EVENT[dvTP]
{
OFFLINE: nPanelOffline = true
ONLINE:
{
SEND_LEVEL dvTP, 1, nXAP_Level
}
}
DATA_EVENT[vdvXAP]
{
STRING:
{
SEND_STRING 0,"'UI rcvd from COMM:',DATA.TEXT"
SWITCH(REMOVE_STRING(DATA.TEXT,'=',1))
{
CASE 'VOLUME=':
{
nXAP_Level = ATOI(DATA.TEXT)
SEND_LEVEL dvTP, 1, nXAP_Level
}
CASE 'RINGING=':
{
}
CASE 'MIC_STATUS=':
{
}
CASE 'HOOK=':
{
}
CASE 'DIAL=':
{
}
CASE 'REDIAL=':
{
}
}
}
}
BUTTON_EVENT[dvTP,ClearOne_XAP800_BUTTONS]
{
PUSH:
{
SWITCH (GET_LAST(ClearOne_XAP800_BUTTONS))
{
CASE 1: // Toggle Floor Mics On / Off
{
SEND_COMMAND vdvXAP, 'Floor_Mics=TOGGLE'
}
CASE 2: // Toggle Ceiling Mics On / Off
{
SEND_COMMAND vdvXAP, 'Ceiling_Mics=TOGGLE'
}
CASE 3: // Gain Up
{
SEND_COMMAND vdvXAP, 'Gain=UP'
}
CASE 4: // Gain Down
{
SEND_COMMAND vdvXAP, 'Gain=DOWN'
}
CASE 5: // Toggle Audio Mute
{
SEND_COMMAND vdvXAP, 'Gain=MUTE'
}
}
}
HOLD[3,REPEAT]:
{
SWITCH (GET_LAST(ClearOne_XAP800_BUTTONS))
{
CASE 3: // Gain Up
{
SEND_COMMAND vdvXAP, 'Gain=UP'
}
CASE 4: // Gain Down
{
SEND_COMMAND vdvXAP, 'Gain=DOWN'
}
}
}
}
(***********************************************************)
(* THE ACTUAL PROGRAM GOES BELOW *)
(***********************************************************)
DEFINE_PROGRAM
(***********************************************************)
(* END OF PROGRAM *)
(* DO NOT PUT ANY CODE BELOW THIS COMMENT *)
(***********************************************************)
Comments
-
One thing I have already noticed, rather than 3 UI's for the XAP TP's, should I combine them? How would that work if one TP was controlling the volume while at the same time, another TP was muting the mics? Would the two have to fight for control? Should I create a command buffer that will rack and stack the incoming commands and release them one at a time?
-
staticattic wrote: »One thing I have already noticed, rather than 3 UI's for the XAP TP's, should I combine them? How would that work if one TP was controlling the volume while at the same time, another TP was muting the mics? Would the two have to fight for control? Should I create a command buffer that will rack and stack the incoming commands and release them one at a time?
the protocol probably has a section that explains the minimum time that should be between commands. you should probably queue them
Categories
- All Categories
- 2.5K AMX General Discussion
- 922 AMX Technical Discussion
- 514 AMX Hardware
- 502 AMX Control Products
- 3 AMX Video Distribution Products
- 9 AMX Networked AV (SVSI) Products
- AMX Workspace & Collaboration Products
- 3.4K AMX Software
- 151 AMX Resource Management Suite Software
- 386 AMX Design Tools
- 2.4K NetLinx Studio
- 135 Duet/Cafe Duet
- 248 NetLinx Modules & Duet Modules
- 57 AMX RPM Forum
- 228 MODPEDIA - The Public Repository of Modules for Everyone
- 943 AMX Specialty Forums
- 2.6K AMXForums Archive
- 2.6K AMXForums Archive Threads
- 1.5K AMX Hardware
- 432 AMX Applications and Solutions
- 249 Residential Forum
- 182 Tips and Tricks
- 146 AMX Website/Forums