A Math Question

Cyberen

L3: Member
Mar 30, 2021
143
30
Say I want to create a vehicle with speeds and gears.

Speeds is represented by S. It has six values: 0, 25, 40, 55, 70, 85
Gears is represented by G. It has four values: 1, 1.41, 1.83, 2.25

If I want to output a value based on S multiplied by G, with both variables changing based on hitting triggers, how would I do it?

I already had a series of math_counters and logic_case set up to do this, but I don't know how to make S and G change independently without erasing the other value's input and affecting the result.

For instance, if I am on gear 2, and my speed changes from 40 to 25, how do I reflect that in another math counter (or another entity) without overwriting the multiplication of G? If I make the math_counter result fire an output to make G re-fire its output, won't that make an endless loop and crash the game?

S x G = V, but how?
 

Tiftid

the Embodiment of Scarlet Devil
aa
Sep 10, 2016
602
465
Create a new counter - we'll call this D, for "Dummy". Give counter G an OutValue output, targeting counter D, with the sent input being SetValue. This basically means that whenever the value of G changes, the value of D will become equal to the new value of G.
Now, give counter S an OutValue output, targeting counter D, with the sent input being Multiply.

Then, you need to give G an "OnGetValue D SetValue" output, and give S an "OutValue G GetValue" output, ensuring via delays that it goes off before the "OutValue D Multiply" output that we gave to counter S earlier.
That way, whenever the speed changes, it'll automatically set D equal to G, then multiply D by itself, creating a velocity value.

Finally, if you give S an "OnGetValue D Multiply" output, and give G an "OutValue S GetValue" output, whenever G changes it'll automatically multiply itself by the current S value.

This got a bit complicated, so I'll use your example of being on gear 2 and speed changing from 40 to 25 in hopes of helping to explain it.

The value of G is 1.41. It doesn't change, so G's OutValue outputs don't fire.
However, earlier G had to change from something to 1.41, so its OutValue outputs would have fired, so it would have:
1) Set D's value to 1.41
2) Grabbed the value of S, which was 40 at the time.

This would have in turn fired the OnGetValue outputs of S, so S would have multiplied the value of D by its own value, resulting in the new value of D being 56.4.
So we know D's value at this time is 56.4.

But it actually doesn't matter what D's value is, because S changing from 40 to 25 fires S's OutValue outputs, so it will:
1) Grab the value of G, which is 1.41; this causes G to reset D's value to 1.41
2) Multiply D's value by its own new value, which is 25; so the new value of D is 35.25.

Using the inverse example, where S stays at 40 but G goes from 1.41 to 1:
-G sets D to its new value, so D goes from 56.4 to 1.
-G grabs the value of S.
-S multiplies D by its current value, which is 40, so the new value of D is 40.
 

Box Of Paper

L3: Member
Jul 15, 2019
121
148
Hopefully I got your question right, if I didn't at least I hope these can guide you:

These don't use logic_case, they work with any number that you assign to S and G.

I've attached two simple system to output (OutValue) a number (V) equal to the product of two other numbers (S e G) whenever one of these two changes.

Two versions:
- The 1st instantly changes V but doesn't work if both S and G change at the same time;
- The 2nd does work, but there is a slight delay between S and G chaning and V changing.

The trick is to reset to 1 the number V and then multiply both S and G.
I've used an OnHitMax trick so that the OutValue happens only when V is ready.
 

Attachments

  • Math 1st Ver.vmf
    2.7 KB · Views: 130
  • Math 2nd Ver.vmf
    3.3 KB · Views: 88

Cyberen

L3: Member
Mar 30, 2021
143
30
Thanks Box, but what does the output OnGetValue with all the dashes do?
 

Box Of Paper

L3: Member
Jul 15, 2019
121
148
Oh, it does nothing at all, you should remove it since the game processes it anyway.

I just used it to separate the OnGetValue and OutValue outputs so that it was easier to read.
 

Cyberen

L3: Member
Mar 30, 2021
143
30
@Box Of Paper Well I'm a bit of a dimwit because I tried inputting the precise values that I wanted and it didn't make the train move. Please see the attached vmf to see what I'm talking about. The leftmost math_counters and logic_cases hold the precise speed and gear values I wanted, activated by the trigger and buttons on the floor.
 

Attachments

  • traincontrolshared.vmf
    1.7 MB · Views: 125

Box Of Paper

L3: Member
Jul 15, 2019
121
148
"velocity_change_counter" 's maximum legal value has to be at 3.

(
When you change either Speed or Gear, "velocity_temp" will be set to the real Velocity after exactly 3 operations:
- set to 1
- multiply speed
- multiply gear

Every time "velocity_temp" changes it adds 1 to "velocity_change_counter", and when that reaches 3 it means that all operations are done and the Velocity value is ready.

"velocity_change_counter" will then ask (getValue) "velocity_temp" to copy it's value in "velocity".

Thanks to this the math_counter "velocity" outputs with OutValue only once (and it's the correct value).
)