• 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.

SOLUTION; Looped key framed animation of an rotating disk, with on/off swith now WORKING...

claus kludder

Resource contributor
Messages
16
Country
denmark
SOLUTION; Looped key framed animation of an rotating disk, with on/off swith now WORKING...

I tryed out this for a key framed animation ( An Ventilation rotor in the VC Roof, with an on/off switch on the Dashboard ) for FSX & P3D modeldef.xml, and it did not Work for Me even seach and try out many suggestions...

But I wanted it to Work as I did not like the TicK18/Ambient Params. You cannot create a working switch ( At least I could not ) for the Ambient animation, and the rotation speed is also to slow for a Ventilator Rotor after My opinion.

After working hard 3 very long days 15-16 hours each ( Even thought about create the rotor objeckt as an effect ) I had My Heruka :)

Because of all the help I found here on this forum from both Arno and other users, I decided to share this XML code here free to use both for freeware as well as commersial use.

The Switch code is quite simple and can be used for any kind of switches ( Actualle I spend a lot of time on that get it working, before I found an almost identically code here.

Because its only the switch wich has an "Lag" parameter, not the actual rotating object, Theres a small delay in the retracting of the switch, maybee anyone here can improve the XML code? But feel free to use it, just credit Me as I credit for the help I get, especially Bill Leaming, from wich's "3 Speed Wiper" animation XML souce code, I got the inspiration to the finally solution ;-)

The looping code of the rotating objeckt can be used to loop any key framed animation as well...

Code:
    <Animation name="Ventilation_Switch" guid="80AAE78A-E159-463b-A9EC-6672BA0ED196" length="100" type="Sim" typeParam2="Ventilation_Switch" typeParam="AutoPlay" />

  <PartInfo>
    <Name>Ventilation_Switch</Name>
    <AnimLength>100</AnimLength>
    <Animation>
      <Parameter>
        <Code>
          (L:Ventilation_Switch,number) 100 *
        </Code>
        <Lag>400</Lag>
      </Parameter>
    </Animation>
    <MouseRect>
      <Cursor>Hand</Cursor>
      <MouseFlags>LeftSingle</MouseFlags>
    <TooltipText>Ventilation Switch</TooltipText>
      <CallbackCode>
        (L:Ventilation_Switch) ! (&gt;L:Ventilation_Switch)
      </CallbackCode>
    </MouseRect>
  </PartInfo>

      <Animation name="ventilation_Anim" guid="A958CDE7-9FFE-4c33-A5EC-605563F5025F" length="100" type="Sim" typeParam2="ventilation_Anim" typeParam="AutoPlay" />

<PartInfo>
  <Name>ventilation_Anim</Name>
    <AnimLength>100</AnimLength>
      <Animation>
        <Parameter>
         <Code>
        (L:Ventilation_Switch,number) 100 *
          if{ (L:Ventilation_Switch) 100 * != (L:Ventilation_Switch) 1 &gt; or
             if{ (L:Ventilation_Switch) (L:Ventilation_Switch) 0.75 * + 100 % d (&gt;L:Ventilation_Switch) }
          els{ (&gt;L:Ventilation_Switch) }   
          </Code>
      </Parameter>
  </Animation>
</PartInfo>

If You just want an keyframed animtion for and objeckt as well as the on/off switch without looping, heres another example wich can be used for any animated object with a switch to start and stop the animation...

Code:
    <Animation name="switch_cabin_heat" guid="BC4DDB66-F7AB-4eb3-8CCE-43DD216DE7A8" length="50" type="Sim" typeParam2="switch_cabin_heat" typeParam="AutoPlay" />

  <PartInfo>
    <Name>switch_cabin_heat</Name>
    <AnimLength>50</AnimLength>
    <Animation>
      <Parameter>
        <Code>
          (L:switch_cabin_heat,number) 50 *
        </Code>
        <Lag>400</Lag>
      </Parameter>
    </Animation>
    <MouseRect>
      <Cursor>Hand</Cursor>
      <MouseFlags>LeftSingle</MouseFlags>
      <CallbackCode>
        (L:switch_cabin_heat) ! (&gt;L:switch_cabin_heat)
      </CallbackCode>
    </MouseRect>
  </PartInfo>

    <Animation name="cabin_heat_Disk" guid="3F965545-01BF-418d-A8D3-B42AAB283DB2" length="100" type="Sim" typeParam2="cabin_heat_Disk" typeParam="AutoPlay" />

  <PartInfo>
    <Name>cabin_heat_Disk</Name>
    <AnimLength>100</AnimLength>
    <Animation>
      <Parameter>
        <Code>
          (L:switch_cabin_heat) 100 *
        </Code>
        <Lag>400</Lag>
      </Parameter>
    </Animation>
  </PartInfo>

Images from ongoing update of the Piper Pa28-140

Ventilator off FSX

Ventilator on FSX

Ventilator_0ff P3D

Ventilator_on P3D




Sincerely Regards
Claus V. Holmberg / SCANSIM Flightsimulation
 
Last edited:

n4gix

Resource contributor
Messages
11,674
Country
unitedstates
Nice! I'm happy that you found what you needed. Might I suggest though that you "wrap" your XML in the {CODE} box? There's a little icon in the editor's top line just to the left of the "floppy disk" icon, with a popup that reads "Insert".

When you click on that icon, you can paste your XML script there and it will be nicely formatted when you save your reply...

...something like this:
Code:
    <!-- WIPER CONTROL LOGIC -->
    (A:ELECTRICAL MASTER BATTERY,bool) 0 !=
      if{ (L:WIPER_SPEED,number) 0 &gt;
        if{ (L:WIPER_POS, enum) 2 + 100 % (>L:WIPER_POS, enum) } }

    (L:WIPER_SPEED,number) -1 ==
    (L:WIPER_POS,number) 0 &gt; and
      if{ (L:WIPER_POS,number) -- (>L:WIPER_POS,number) }
 

claus kludder

Resource contributor
Messages
16
Country
denmark
Like this ;-) Thanks, Im very happy that I found that "Wiper" code, I thought I was going crazy after three days trying to loop that rotor...

Tomorrow I will attach a sound of the ventilator, Im too tired now since been working 14 houers on this crazy Microsoft XML ;-)

Have a nice day Bill

Claus
 

claus kludder

Resource contributor
Messages
16
Country
denmark
Heres the Gmax file ( FSX Gamepack ) of the Switch and the Ventilator with rotor, both with animated dummy's and UW mapped, bot no textures.

Because its only the switch that has an "Lag" parameter, not the actual rotating rotor in the Ventilator, Theres a small delay ( a few seconds ) in the retracting of the switch when turning the Ventilator "Off", maybee anyone here can improve the XML code, so the speed off the Switch turning On/Off gets equal?

I dont think its the "Callback Code" in the Switch animation, wich contains the <Lag>400</Lag>, that causes this delay when turning the Ventilator "Off", but simply because the Rotor Animation has no "Lag" in the code.

Feel free to test and also use the Model and the Model's Animations if You like, but if You can Improve the code, I would like to use the edited code as well. Offcause I will credit for any help, as well You will credit Me if using the Model's or animation's and code...

Claus / SCANSIM Flightsimulation
 

Attachments

  • Switch+Ventilator.zip
    112.3 KB · Views: 215

taguilo

Resource contributor
Messages
1,585
Country
argentina
Hi Claus, I'm trying to understand your code. So far I see two parts, ventilation_switch and ventilation_anim. Ventilation_switch is the push-pull knob that turns on-off the ventilator, and I see ventilation_anim is the rotating disk that has to rotate synchronized with the movement of the switch, until it stops on either end.

The "problem" I notice is that you are using the same LVar (L:Ventilation_Switch) in both animations, which should contain 0 or 1 (OFF-ON), but in the ventilation_anim part you are updating its value, then affecting the animation of ventilation_switch. A second variable ie (L:Ventilation_status) to control the rotation loop would be preferable, like (not tested!):

Code:
<PartInfo>
   <Name>ventilation_Anim</Name>
   <AnimLength>100</AnimLength>
   <Animation>
         <Parameter>
             <Code>
                 (L:Ventilation_Switch,number)  (L:Ventilation_status,number)  1 &gt; or
                 if{ (L:Ventilation_status,number) (L:Ventilation_Switch) 0.75 * + 100 % d (&gt;L:Ventilation_status,number) }
                 els{ 0 (&gt;L:Ventilation_status,number) }
             </Code>
        </Parameter>
   </Animation>
</PartInfo>

Tom
 

tgibson

Resource contributor
Messages
11,327
Country
us-california
Hi,

I am guessing the Lag in the switch code avoids that problem?
 

claus kludder

Resource contributor
Messages
16
Country
denmark
Hi Claus, I'm trying to understand your code. So far I see two parts, ventilation_switch and ventilation_anim. Ventilation_switch is the push-pull knob that turns on-off the ventilator, and I see ventilation_anim is the rotating disk that has to rotate synchronized with the movement of the switch, until it stops on either end.

The "problem" I notice is that you are using the same LVar (L:Ventilation_Switch) in both animations, which should contain 0 or 1 (OFF-ON), but in the ventilation_anim part you are updating its value, then affecting the animation of ventilation_switch. A second variable ie (L:Ventilation_status) to control the rotation loop would be preferable, like (not tested!):

Code:
<PartInfo>
   <Name>ventilation_Anim</Name>
   <AnimLength>100</AnimLength>
   <Animation>
         <Parameter>
             <Code>
                 (L:Ventilation_Switch,number)  (L:Ventilation_status,number)  1 &gt; or
                 if{ (L:Ventilation_status,number) (L:Ventilation_Switch) 0.75 * + 100 % d (&gt;L:Ventilation_status,number) }
                 els{ 0 (&gt;L:Ventilation_status,number) }
             </Code>
        </Parameter>
   </Animation>
</PartInfo>

Tom

This is great, thanks a lot :) The (L:Ventilation_status) was just what was needed as well as the 0 - 1 &gt; ...

Actually I thought it was something like this, when using "&gt" instead og "Lag", there has to be a code for both positions. Now the switch "lever" moves with identically speed both way, and just like the other push-pull switches with the "Lag" variable to control the animation speed.

Only thing I had to do was increasing the rotation speed of the rotor from "0.75" to "2.0" to get it look more realistic. I will credit both You Taguilo and Bill Leaming in the upcoming update of the Piper Pa28-140...

After testing the code now looks like this, and can be used to any kind of looping an animation in FSX/P3D with the "Sim" variable instead of "Ambient"...

Code:
    <Animation name="Ventilation_Switch" guid="80AAE78A-E159-463b-A9EC-6672BA0ED196" length="100" type="Sim" typeParam2="Ventilation_Switch" typeParam="AutoPlay" />

  <PartInfo>
    <Name>Ventilation_Switch</Name>
    <AnimLength>100</AnimLength>
    <Animation>
      <Parameter>
        <Code>
          (L:Ventilation_Switch,number) 100 *
        </Code>
        <Lag>400</Lag>
      </Parameter>
    </Animation>
    <MouseRect>
      <Cursor>Hand</Cursor>
      <MouseFlags>LeftSingle</MouseFlags>
    <TooltipText>Ventilation Switch</TooltipText>
      <CallbackCode>
        (L:Ventilation_Switch) ! (&gt;L:Ventilation_Switch)
      </CallbackCode>
    </MouseRect>
  </PartInfo>

      <Animation name="ventilation_Anim" guid="A958CDE7-9FFE-4c33-A5EC-605563F5025F" length="100" type="Sim" typeParam2="ventilation_Anim" typeParam="AutoPlay" />

<PartInfo>
   <Name>ventilation_Anim</Name>
   <AnimLength>100</AnimLength>
   <Animation>
         <Parameter>
             <Code>
                 (L:Ventilation_Switch,number)  (L:Ventilation_status,number)  1 &gt; or
                 if{ (L:Ventilation_status,number) (L:Ventilation_Switch) 2.0 * + 100 % d (&gt;L:Ventilation_status,number) }
                 els{ 0 (&gt;L:Ventilation_status,number) }
             </Code>
        </Parameter>
   </Animation>
</PartInfo>

Thanks Again for the help Taguilo and Bill, now I understand the XML language much better...

Claus / SCANSIM Flightsimulation
 

claus kludder

Resource contributor
Messages
16
Country
denmark
Hi,

I am guessing the Lag in the switch code avoids that problem?

Hi Tom

Actually both yes and no, The "Lag" variable is used to control the speed of the animation used to the push-pull switch / lever, and is used for most simple non looping animation like door opening ect. ect.

The problem here is its two different type of codes. The first is non looped and the second looped. As Taguilo so nicely explained I did not include the retract code / variable &gt; 0, only the &gt; 1, and more important the "Status". So this is why the switch was a Little delayed when turned off - the rotor stopped immediately...

Actually You can delete the "Number" or "Enum" and it should still Work, but I leave the edition of Taguilo as it is, just with the speed of the rotation changed...

Another solution could have been using the <Sim> Parameter instead of the <Code> in the switch animation and edited the callback code, but this Works much better and easier to control...

/Claus V. Holmberg
 
Last edited:

n4gix

Resource contributor
Messages
11,674
Country
unitedstates
Actually, <Sim> may only be used with stock sim variables (A:var,unit). It will not work with custom (L:var,unit) types at all.
 

claus kludder

Resource contributor
Messages
16
Country
denmark
You're right Bill ;) Because Im curius learning the XML, I spend a few hour's testing it. How ever I could get the Switch activate the Ventilator with the (L:var,unit and the <sim> variable, but the Switch wont move at all no matter what <CallbackCode> is used... So now Im that clever :)
 

n4gix

Resource contributor
Messages
11,674
Country
unitedstates
Claus, that's because that variable is only used for the switch animation...
 

dave hoeffgen

Resource contributor
Messages
1,439
Country
germany
Is there any possibility to make the animation finish before it stops after it has been switched off?
For Example when using it for a wiper I don't want it to stop in the middle of my windshield.
But I also don't want it to spawn back to zero.

Is it possible to just copy the value of L:Ventilation_Switch to another variable (e.g. L:Ventilation_Running) each time L:Ventilation_status is at zero and this variable is actually controlling if the animation keeps going?

Sorry in case I'm asking something obvious but I'm completely new to Xml coding
 

n4gix

Resource contributor
Messages
11,674
Country
unitedstates
Here is my 'solution' for parking the wipers after shutdown. Note that my switch has a 'Park' position that sets a value for the L:var as -1, which triggers the second bit of logic script.
Code:
    <!-- WIPER CONTROL LOGIC -->
    (A:ELECTRICAL MASTER BATTERY,bool) 0 !=
    if{ (L:WIPER_SPEED,number) 0 &gt;
    if{ (L:WIPER_POS, enum) 2 + 100 % (>L:WIPER_POS, enum) } }

    (L:WIPER_SPEED,number) -1 ==
    (L:WIPER_POS,number) 0 &gt; and
    if{ (L:WIPER_POS,number) -- (>L:WIPER_POS,number) }

    (L:WIPER_SPEED,number) -1 ==
    (L:WIPER_POS,number) 0 == and
    if{ 0 (>L:WIPER_SPEED,number) }
When the switch is turned to "Park" a test is made to see if the (L:var) is greater than 0. If so, then the (L:var) is decremented by -1 until it reaches 0.

The last script then sets the knob back to the "Off" position.
 
Last edited:

dave hoeffgen

Resource contributor
Messages
1,439
Country
germany
How exactly does the callback code of the switch have to look if it should just toggle the wiper (single speed)?
I tried this with the switch only moving in the second half of its animation:
Code:
<CallbackCode>
        (L:WIPER_SPEED,number) 0 == if{ (L:WIPER_SPEED,number) 1 (>L:WIPER_SPEED,number)}
        (L:WIPER_SPEED,number) 1 == if{ (L:WIPER_SPEED,number) -1 (>L:WIPER_SPEED,number)}
      </CallbackCode>
But this does not work :(
 

tgibson

Resource contributor
Messages
11,327
Country
us-california
(L:WIPER_SPEED,number) ! (>L:WIPER_SPEED,number)

To make it clearer, you could also change the units of the variable:

(L:WIPER_SPEED,bool) ! (>L:WIPER_SPEED,bool)
 

n4gix

Resource contributor
Messages
11,674
Country
unitedstates
This is my entire <MouseRect> for my three position switch: Park - Off - On
Code:
    <MouseRect>
      <Cursor>Hand</Cursor>
      <MouseFlags>LeftSingle+RightSingle+Wheel+DownRepeat</MouseFlags>
      <CallbackCode>
        (M:Event) 'LeftSingle' scmp 0 ==
        (M:Event) 'WheelDown' scmp 0 == or
        if{ (L:WIPER_SPEED, enum) -- -1 max (>L:WIPER_SPEED, enum) }
        (M:Event) 'RightSingle' scmp 0 ==
        (M:Event) 'WheelUp' scmp 0 == or
        if{ (L:WIPER_SPEED, enum) ++  1 min (>L:WIPER_SPEED, enum) }
      </CallbackCode>
    </MouseRect>
By the way, the missing space between the closing parenthesis and the curlybrace in your example would prevent the if statement from working.
 
Last edited:

dave hoeffgen

Resource contributor
Messages
1,439
Country
germany
Thanks very much for all the help!:)
This is my final wiper logic which works best for me:
Code:
(L:l_wiper_pos,number) 0 !=  (L:l_wiper_on, number)  0 != ||
if{ (L:l_wiper_pos,number) (A:CIRCUIT GENERAL PANEL ON,bool) 2.0 * + 100 % d (>L:l_wiper_pos,number) }

Basically it is the ventilation code by Claus with renamed variables.
Removing the multiplication with the switch position makes the animation finish before stopping. Inserting the A:CIRCUIT GENERAL PANEL ON instead makes the wiper get stuck when the electrical power fails.

Thanks again for helping me to understand the xml language a little bit better.;)
 
Top