Home AMX User Forum NetLinx Studio
Options

Active bargraph synchronization solution, and a question

Everybody runs into the problem with trying to make active bargraphs work with multiple panels. The age-old problem is you have the same active bargraph on both panels, and when you change the level on one (by sliding or touching the bargraph), you want the bargraph on the other panel to change accordingly.

THEN, we all run into the problem that actually doing a SEND_LEVEL to the second panel generates a LEVEL_EVENT. Something like this happens:

... person changes level on panel 1 from 40 to 50, then 40 (finger slip?)
... LEVEL_EVENT from panel 1 value 50
... SEND_LEVEL 50 to panel 2
... LEVEL_EVENT from panel 1 value 40
... LEVEL_EVENT from panel 2 value 50
... SEND_LEVEL 40 to panel 2
... SEND_LEVEL 50 to panel 1
... continue to bounce these values around and watch the happy jumping bargraphs!

If these levels correspond to light or volume levels, you get some pretty crazy effects!

SO, many people implement the two bargraph option. Meaning they create one transparent bargraph on top of the other. The top one is for adjusting values, and the bottom one is for feedback. Solves the problem, but this is a huge pain in the but for panel design, especially if you have a lot of bargraphs. I'm not so sure AMX intended this.

The overall problem in it's simple form is you can't tell if a LEVEL_EVENT came from a user changing the bargraph, or from your program having sent a previous SEND_LEVEL.

Other people suggest that if you set a program flag (per panel), saying 'Hey, I sent a SEND_LEVEL', then when you get a LEVEL_EVENT from that same panel with the flag set, you can simply ignore the LEVEL_EVENT. This works 'most of the time', but fails when some of the events stack up.

Seemingly the best solution I've found is to define a channel code for the bargraph, along with the level code you already defined. When you get a PUSH for the specified channel code, you set a flag in your code that says 'Somebodys sliding the bargraph'. On the RELEASE, you simply turn that flag off. Then you only act on the LEVEL_EVENTS from your bargraph IF your flag is set. Any LEVEL_EVENTS that don't have PUSH and RELEASE around them are simply a result of SEND_LEVEL(s), and can be ignored.

Here's the question..... this solution relies on the fact that when a person is sliding their finger over a bargraph, that it will generate the events in this order:

PUSH
LEVEL_EVENT
LEVEL_EVENT
.
.
.
LEVEL_EVENT
RELEASE

Is this the case? If so, this is a simple solution to the active bargraph synchronization problem.

I can provide a snippet if anybody would like.

Chuck

Comments

  • Options
    chuckdchuckd Posts: 26
    Well shoot, if I had just checked out AMXJeff's post earlier, I would have seen that the PUSH and RELEASE does indeed happen around the LEVEL_EVENTS, and problem solved!

    Good job Jeff!
  • Options
    kbeattyAMXkbeattyAMX Posts: 358
    Why aren't you using define_connect_level?
  • Options
    kbeattyAMXkbeattyAMX Posts: 358
    All 4 bar graphs move asynchronously using the code below. It should work between panels also.
    define_connect_level
    (dvTP,4,dvTP,2,dvTP,1,dvTP,3)
    //level 4 is not actually on any tp.  It could be a virtual level
    (***********************************************************)
    (*                STARTUP CODE GOES BELOW                  *)
    (***********************************************************)
    DEFINE_START
    
    send_level dvTP,4,100
    
    (***********************************************************)
    (*                THE EVENTS GO BELOW                      *)
    (***********************************************************)
    DEFINE_EVENT
    
    level_event[dvTP,5]
    {
      send_level dvTP,4,level.value
    }
    
    level_event[dvTP,4]
    {
      send_level dvTP,5,level.value
    }
    
    
    
  • Options
    chuckdchuckd Posts: 26
    Are you saying that by using DEFINE_CONNECT_LEVEL, that changing the level on one panel will NOT generate LEVEL_EVENTs from the other panels, yet their levels will be updated appropriately?
  • Options
    kbeattyAMXkbeattyAMX Posts: 358
    chuckd wrote: »
    Are you saying that by using DEFINE_CONNECT_LEVEL, that changing the level on one panel will NOT generate LEVEL_EVENTs from the other panels, yet their levels will be updated appropriately?

    I didn't define level events for the other bar graphs. All of the bar graphs are tied through one level event. Bar graph 5 is acting as any type of device that an analog value needs to be changed and updated. When 5 changes 1,2,3 are updated through the send level to 4 because they are connected to 4. when 1,2,3 is changed 4 is changed and 1,2,3 are synced generating a level event on 4 that sends a value to 5 to control it. Try it out and see if it works for you. I don't have multiple TPs here but I think it would work fine between panels.
  • Options
    yuriyuri Posts: 861
    You should use COMBINE_LEVEL, so you can also use UNCOMBINE_LEVEL when needed.

    Worked for me in a situation where a control room was in control of 2 touchpanels, but only have one slider on the touchpanel :)
    Using COMBINE_LEVEL and UNCOMBINE_LEVEL to toggle between the two different touchpanel sliders on the control room touchpanels.

    Some code to explain it a bit more :p
    nTPSelected = 1;
    		
    (* uncombine single touchpanel *)
    UNCOMBINE_LEVELS(vdvVolume1,1)
    
    WAIT 5
    {
          (* combine again, but include the control room touchpanel *)
          COMBINE_LEVELS(vdvVolume1,1,dlVolume1,dlVolumeR)
    }
    

    dlVolume1 and dlVolumeR are 2 DEVLEVs
    DEVLEV dlVolume1[]=
    {
        {dvTP_Aula1_L, 1}
    }
    
    DEVLEV dlVolumeR[]= 
    {
        {dvTP_Regie_L, 1}
    }
    

    works like a charm!

    now every time one of the 2 sliders is touched, only one LEVEL_EVENT is triggered, and you can do your thing...
    LEVEL_EVENT[vdvVolume1,1]
    {
        IF(nVolumeEnable1)
        {
    	VOLUME1[1] = (LEVEL.VALUE / (2.28)) - 100
    	SEND_STRING dvNexia, "'SET 1 FDRLVL 38 1 ' , ITOA(VOLUME1[1]), $0D";
        }
    }
    

    Both sliders are updated one both touchpanels, without triggering another LEVEL_EVENT

    The COMBINE_LEVEL help file is a bit vague, so good luck! ;)
Sign In or Register to comment.