• Which the release of FS2020 we see an explosition of activity on the forun and of course we are very happy to see this. But having all questions about FS2020 in one forum becomes a bit messy. So therefore we would like to ask you all to use the following guidelines when posting your questions:

    • Tag FS2020 specific questions with the MSFS2020 tag.
    • Questions about making 3D assets can be posted in the 3D asset design forum. Either post them in the subforum of the modelling tool you use or in the general forum if they are general.
    • Questions about aircraft design can be posted in the Aircraft design forum
    • Questions about airport design can be posted in the FS2020 airport design forum. Once airport development tools have been updated for FS2020 you can post tool speciifc questions in the subforums of those tools as well of course.
    • Questions about terrain design can be posted in the FS2020 terrain design forum.
    • Questions about SimConnect can be posted in the SimConnect forum.

    Any other question that is not specific to an aspect of development or tool can be posted in the General chat forum.

    By following these guidelines we make sure that the forums remain easy to read for everybody and also that the right people can find your post to answer it.

FS2004 XML flap handle sound gauge issues

Messages
242
Country
unitedstates
Okiedoke, I am going to preface this by saying that I am a total novice outside of programming some basic XML animations for models in the past, but I will note that I have read the Panels SDK, Doug's documentation for dsd_fsx_xml_sound.gau, and have studied several similar gauges, along with the excellent documentation here, and I've also reviewed several previous threads here including this one. So, I have enough of a basic understanding to know that I should have the basic syntax right, but I am clearly missing something.

The intent is to create a flap handle gauge that plays one of eight samples (in a OneShot fashion) at each flap notch, so that if you were to advance the flaps all the way, for a 737, you would hear eight clicks in sequence. My thought was that this would be a simple matter of creating an element for each notch and telling the sim to play the samples as FLAPS HANDLE PERCENT becomes greater than some value (e.g., 12.5% for the first notch) for each element. I came up with this:

Code:
<Gauge Name="NAVS_JT8D_Universal" Version="1.0">
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_00.wav when flaps handle percent passes 12% -->
                (A:FLAPS HANDLE PERCENT,percent) 12 &gt;
                if{ 1(&gt;L:Boeing_Flap_00, number) }
                (A:FLAPS HANDLE PERCENT,percent)    (&gt;A:TRAILING EDGE FLAPS0 RIGHT PERCENT,percent)
            </Value>
        </Select>
    </Element>
</Gauge>

This did not work. I wanted to eliminate the possibility that something was wrong with the INI file, the paths to the samples, or just the way I put things in panel.cfg, so I created a duplicate version of the gauge using the altitude alert code from this thread. The result was this:

Code:
 <Gauge Name="Altitude" Version="1.0">
    <Element>
        <Select>
            <Value>
                (* Play the sound when reaching 2000 feet *)
                (A:Radio Height, feet) 2000 &gt;= (L:Altitude, number) 2000 &lt; &amp;&amp;
                if{ 1 (>L:Boeing_Flap_00,number) }
                (A:Radio Height, feet)  (>L:Altitude, number)
            </Value>
        </Select>
    </Element>
</Gauge>

This worked perfectly, playing the indicated sample at 2,000 feet on the radar altimeter. When I use Doug's debug and LVars gauges, I can see that all variables specified in my INI file are accounted for in the list, along with all of the associated audio samples. To me, this indicates that the problem is solely in the gauge code. I tried several other iterations, such as just asking it to play when the trailing edge flap percentage passed a certain point:

Code:
<Gauge Name="NAVS_JT8D_Universal" Version="1.0">
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_00.wav when trailing edge flaps percent passes 12% -->
                (A:TRAILING EDGE FLAPS0 RIGHT PERCENT,percent) 12 &gt;
                if{ 1(&gt;L:Boeing_Flap_00, number) }
            </Value>
        </Select>
    </Element>
</Gauge>

This did not work either. This tells me that there is something wrong in my syntax at a foundational level. So, my questions are:

  1. What is preventing my code from working? My read of the code, as I wrote it originally, is that when FLAPS HANDLE PERCENT greater than 12 is TRUE ((A:FLAPS HANDLE PERCENT,percent) 12 &gt;), the audio sample should play once (if{ 1(&gt;L:Boeing_Flap_00, number) }).
  2. Is my basic idea of creating an element for each flap notch a valid one if my goal is to play a sample at each notch, including multiple samples in sequence when skipping notches? If not, what approach should I take?

I also have plans for a few more gauges, so I might as well ask the big questions for those as well:

How would I go about multiplying volume of a looped sample by some variable? I want to create the following gauges that will require this:

  1. Gear aerodynamic noise, with volume a function of percentage of extension
  2. Flap aerodynamic noise, with volume as a function of trailing edge flap position*speed*G-force
  3. Slat aerodynamic noise, with volume as a function of leading edge flap position*speed*G-force
  4. Jet exhaust, with volume as a function of throttle lever percent (when the engine is active, which seems like a simple boolean operation to me?)

My first instinct is that I would multiply the integer percentages together, one after another, in the stack, then divide by some value to convert the result to a decimal, then multiply this by 10,000, and store it as the VolumeVarIn variable somehow. Is this the right line of thinking? What's the most efficient way to operationalize this? Am I completely off my head on everything?
 
Oh my goodness, that worked! It loops instead of playing once, but I can't believe it was that simple (especially since the code without the space was copied from Doug's documentation). Now I will need to figure out how to keep it from looping...
 
Create a flag variable that allows the sound to play if 0, then set the variable to 1 to prevent looping.
 
That sounds logical; a bit like a relay. I've used a similar approach in Open Rails SMS code. How would I implement this in an XML gauge? I did some Googling and wasn't able to find much - also, remember that I am daft as a bottle of Tomato Soup!
 
Something like:

XML:
<Gauge Name="NAVS_JT8D_Universal" Version="1.0">
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_00.wav when trailing edge flaps percent passes 12% -->
                (A:TRAILING EDGE FLAPS0 RIGHT PERCENT,percent) 12 &gt; (L:Sound Test, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_00, number) 1 (&gt;L:Sound Test, bool) }
            </Value>
        </Select>
    </Element>
</Gauge>

Then you would need code to reset the L: variable to 0 before you can trigger the sound again.

Hope this helps,
 
Ahhhhh - so, the way to read the second line is, "if prior conditions (flap handle percent at desired value and L:Sound Test is 0) are BOTH met, set L:Boeing_Flap_00 to TRUE (write "1" to L:Boeing_Flap_00), then set L:Sound Test to TRUE." This works because, if my interpretation of the references I have been reading is correct, the default value for an L: variable is 0 without a value being stored by the code. Am I reading this correctly? Then, if I needed to perform a reset, I could add another line in the same element that stores a value of 0 to L:Sound Test, bool when, for example, flap handle percent != the value at the given notch. Am I thinking along the right track? This is very similar to the "relay-type" code I use in OR to compound more variables in sound engine code than the sim actually allows for:

Code:
                Triggers ( 13
                    Initial_Trigger  ( DisableTrigger ( 5 ) )
                    Initial_Trigger  ( DisableTrigger ( 7 ) )
                    Initial_Trigger  ( DisableTrigger ( 8 ) )
                    Variable_Trigger ( WheelRpM_Inc_Past   1     EnableTrigger    ( 5 ) )
                    Variable_Trigger ( Distance_Dec_Past 200     EnableTrigger    ( 8 ) )
                    Variable_Trigger ( Distance_Dec_Past 200    EnableTrigger    ( 7 ) )
                    Variable_Trigger ( WheelRpM_Inc_Past   1     EnableTrigger    ( 8 ) )
                    Random_Trigger     ( Delay_Min_Max ( 0 0 )     Volume_Min_Max ( 0.75 1.25 )
                        StartLoop ( 10
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-0.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-1.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-2.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_null.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-3.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-4.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-5.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_null.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-6.wav" -1 )
                            File ( "AudioSamples/RollingStock/flatspots/flatspot_LD-7.wav" -1 )
                            SelectionMethod ( RandomSelection )
                        )
                    )
                    Random_Trigger      ( Delay_Min_Max ( 1 1 )     DisableTrigger    ( 8 ) )
                    Variable_Trigger ( WheelRpM_Dec_Past   1     DisableTrigger    ( 5 ) )
                    Variable_Trigger ( Distance_Inc_Past 200     DisableTrigger    ( 7 ) )
                    Variable_Trigger ( WheelRpM_Dec_Past   1    ReleaseLoopRelease () )
                    Variable_Trigger ( Distance_Inc_Past 200    ReleaseLoopRelease () )
                )

This code allows me to disable and enable a stream with both distance and wheel RPM by controlling the true/false condition of the distance triggers with wheel RPM, then controlling the true/false condition of the wheel RPM triggers with distance, effectively creating a "&&" operation for a random trigger that starts the loop of the randomized flat spot samples, with a second "random" trigger (actually a fixed 1-second delay due to the Delay_Min_Max parameter being set to 1 1) deactivating the random trigger to prevent the sim from playing a new sample after each sample finishes. The code then deactivates the loop when distance or wheel RPM becomes out of bounds.

EDIT: I did a literal "LOL." I'll be damned, it works! I came up with this:

Code:
<Gauge Name="NAVS_JT8D_Universal" Version="1.0">
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_00.wav once at when the flap handle is all the way up -->
                (A:FLAPS HANDLE INDEX, number) 0 == (L:Sound Test 0, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_00, number)  1 (&gt;L:Sound Test 0, bool) }
                (A:FLAPS HANDLE INDEX, number) 0 !=
                if{ 0 (&gt;L:Sound Test 0, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_01.wav once at the first flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 1 == (L:Sound Test 1, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_01, number)  1 (&gt;L:Sound Test 1, bool) }
                (A:FLAPS HANDLE INDEX, number) 1 !=
                if{ 0 (&gt;L:Sound Test 1, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_02.wav once at the second flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 2 == (L:Sound Test 2, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_02, number)  1 (&gt;L:Sound Test 2, bool) }
                (A:FLAPS HANDLE INDEX, number) 2 !=
                if{ 0 (&gt;L:Sound Test 2, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_03.wav once at the third flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 3 == (L:Sound Test 3, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_03, number)  1 (&gt;L:Sound Test 3, bool) }
                (A:FLAPS HANDLE INDEX, number) 3 !=
                if{ 0 (&gt;L:Sound Test 3, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_04.wav once at the fourth flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 4 == (L:Sound Test 4, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_04, number)  1 (&gt;L:Sound Test 4, bool) }
                (A:FLAPS HANDLE INDEX, number) 4 !=
                if{ 0 (&gt;L:Sound Test 4, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_05.wav once at the fifth flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 5 == (L:Sound Test 5, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_05, number)  1 (&gt;L:Sound Test 5, bool) }
                (A:FLAPS HANDLE INDEX, number) 5 !=
                if{ 0 (&gt;L:Sound Test 5, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_06.wav once at the sixth flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 6 == (L:Sound Test 6, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_06, number)  1 (&gt;L:Sound Test 6, bool) }
                (A:FLAPS HANDLE INDEX, number) 6 !=
                if{ 0 (&gt;L:Sound Test 6, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_07.wav once at the seventh flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 7 == (L:Sound Test 7, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_07, number)  1 (&gt;L:Sound Test 7, bool) }
                (A:FLAPS HANDLE INDEX, number) 7 !=
                if{ 0 (&gt;L:Sound Test 7, bool) }
            </Value>
        </Select>
    </Element>
    <Element>
        <Select>
            <Value>
                <!-- This code plays Boeing_Flap_08.wav once at the eighth flap handle position -->
                (A:FLAPS HANDLE INDEX, number) 8 == (L:Sound Test 8, bool) 0 == &amp;&amp;
                if{ 1 (&gt;L:Boeing_Flap_08, number)  1 (&gt;L:Sound Test 8, bool) }
                (A:FLAPS HANDLE INDEX, number) 8 !=
                if{ 0 (&gt;L:Sound Test 8, bool) }
            </Value>
        </Select>
    </Element>
</Gauge>

And here's the end result.
 
Last edited:
Hmm. What is the best way to have the XML code apply the value stored in the associated volume LVar? I've been working on the speedbrake code, and I've gotten the code to do two of the three things I need:

  1. It reads the indicated airspeed and left spoiler percent and spits out a value based on the product of these values, with a value of 10,000 (unity volume) at 300 KIAS and 100% spoiler deflection, and then sends this value to the volume control LVar (confirmed working correctly in-sim with the debug gauge)
  2. It reads the indicated airspeed and left spoiler percent, then begins the loop when both are nonzero, terminating the loop when either value is zero (confirmed functional in-sim)
It does not, however, perform the third function: apply the volume variable to the sound loop.

I had assumed, based on the documentation with Doug's module, that setting the value of the control variable for the sound file to 8, and setting a value for the associated volume control LVar, that the volume control LVar would modulate the value every time the gauge updates (i.e., at a value of 18Hz). This is evidently not the case and I need to put in more code. Here's what I have so far:

Code:
<Gauge Name="NAVS_Aerodynamic_Noise" Version="1.0">
    <Element>
        <Select>
            <Value>
                <!-- This code modulates volume by speed and extension percent, with a value of 10,000 at 100% spoiler extension and 300 KIAS -->
                (A:SPOILERS LEFT POSITION, percent) (A:AIRSPEED INDICATED, knots) * 0.33 * (&gt;L:Volume_Speedbrake, number)

                <!-- This code starts the speedbrake sample loop when left spoiler position and indicated airspeed are both greater than zero, terminating it when either is false -->
                (A:SPOILERS LEFT POSITION, percent) 0 != (A:AIRSPEED INDICATED, knots) 0 != &amp;&amp;
                if{ 8 (&gt;L:Speedbrake, number) }
                els{ 0 (&gt;L:Speedbrake, number) }

            </Value>
        </Select>
    </Element>
</Gauge>

The associated INI file contains the following:

Code:
[Config]
MaxSounds=100
ErrorFlag=-1

[Sounds]
Sound00=./Sound/AudioSamples/FlightControls/Boeing_Flap_00.wav
Sound01=./Sound/AudioSamples/FlightControls/Boeing_Flap_01.wav
Sound02=./Sound/AudioSamples/FlightControls/Boeing_Flap_02.wav
Sound03=./Sound/AudioSamples/FlightControls/Boeing_Flap_03.wav
Sound04=./Sound/AudioSamples/FlightControls/Boeing_Flap_04.wav
Sound05=./Sound/AudioSamples/FlightControls/Boeing_Flap_05.wav
Sound06=./Sound/AudioSamples/FlightControls/Boeing_Flap_06.wav
Sound07=./Sound/AudioSamples/FlightControls/Boeing_Flap_07.wav
Sound08=./Sound/AudioSamples/FlightControls/Boeing_Flap_08.wav
Sound09=./Sound/AudioSamples/AerodynamicNoise/Flaps.wav
Sound10=./Sound/AudioSamples/AerodynamicNoise/Speedbrake.wav
Sound11=./Sound/AudioSamples/AerodynamicNoise/Gear.wav

[LVars]
Lvar00=Boeing_Flap_00
Lvar01=Boeing_Flap_01
Lvar02=Boeing_Flap_02
Lvar03=Boeing_Flap_03
Lvar04=Boeing_Flap_04
Lvar05=Boeing_Flap_05
Lvar06=Boeing_Flap_06
Lvar07=Boeing_Flap_07
Lvar08=Boeing_Flap_08
Lvar09=Flaps
Lvar10=Speedbrake
Lvar11=Gear

[Volume_Variables]
Lvar10=Volume_Speedbrake

How do you apply the volume control LVar to the sound loop? The documentation for dsd_fsx_xml_sound.gau is not clear on this.
 
Code:
Gear aerodynamic noise, with volume a function of percentage of extension
Flap aerodynamic noise, with volume as a function of trailing edge flap position*speed*G-force
Slat aerodynamic noise, with volume as a function of leading edge flap position*speed*G-force
Jet exhaust, with volume as a function of throttle lever percent (when the engine is active, which seems like a simple boolean operation to me?
nice idea!


I use dsd_fsx_xml_sound_v532.zip

Code:
from dsd_fsx_xml_sound.txt

use the actual DirectSound range, which is -10000 for fully muted, to 0, which represents full volume.

I use the volume_variable for my APU and GPU sound.

XML:
  -3000 (L:APU_Eng_N1_Part,percent) 25 * + -1800  min (&gt;L:DSD_TECH_APU_Run_VOL,number)

for my soundfile:
-3000 means No Sound
-1800 means desired soundvolume
you have define this values by yourself for your soundfile!

25 is only a factor defined by yourself
(L:APU_Eng_N1_Part,percent) is to be replaced by airspeed and speedbrake

[Volume_Variables]
Lvar254=DSD_TECH_APU_Run_VOL

I hope i'm clear enough:)

Btw i loved you B727 and DC10-30 so very much😍
 
Last edited:
Ahhh, I think I see the problem, I am setting max volume at 10,000 instead of 0. I misread the documentation and implemented it as it's done in sound.cfg! It works fine now. :)

Here is the end result. This is a reduction in speed with the speedbrakes from 300 KIAS to 200, then extension of slats and flaps 2, slowing to 180 and extending the gear, then continuing to extend flaps as speed drops to 160. Then I apply go-around power, retract to flaps 15 and raise the gear, then retract slats around 200-210-ish, with power reduction around 250.
 
Last edited:
Good old Directsound. Just on the offchance be aware that when panning, -10000 is full left. In actual fact there is no 'panning' at all; Directsound simply increases the righthand channel 'volume value' to 10000 (fully attenuated).
 
Back
Top