Legacy GM Large Number Abbreviations (1500 to 1.5k)

matharoo

Udemy Instructor
GM Version: GameMaker 8 - GameMaker: Studio 1.x. May work on GameMaker Studio 2.
Target Platform: ALL
Download: Test project download
Links: Original blog post on GameDev Palace

Summary:
In this tutorial you're going to learn how to write 10000 as 10K, 1500 as 1.5k, 1500000 as 1.5m and so on. This can be useful in games where there isn't much space to write the exact numbers, and this may look much cooler. So, let's get going!

Tutorial:
Test Project
For demonstrating this, I have created a test project where the numbers I type will appear with notations. It has just one object and a small room.

Create Event:
Code:
number = 0;
number_prefix = 0;
number_suffix = "";
number_output = "";
Here I'm just initializing the variables that I'm going to use. Two numeric variables and two strings. number will read the numbers I type, from the keyboard_string variable (the variable which stores whatever I type). number_prefix will store the prefix of the notated number (for example, 2, 1.5, 100 and so on) and number_suffix will store the notation (K or M or B). Then number_output will combine those who and show us the final number.

Draw Event:
Code:
draw_text(5, 5, keyboard_string);

draw_text(5, 37, number_output);
The first line will show me what I've typed and the second will show me the notated number.

The Main Part
Getting to the main part - this is where our number notations will be calculated.

Step Event:
Code:
number = real(keyboard_string);
number_prefix = number;
number_suffix = "";
Here I'm converting keyboard_string (what I type) into a real number using real() and then assigning the value to number. In your case you can just use your variable which you want to be notated (like number = score or number = money).

Then I'm assigning the number value to number_prefix, in case the number doesn't turn out large enough for a notation, it must have some value to show. Same goes for number_suffix, which can stay empty if there's no notation to be done.

Step Event: (Add the code)
Code:
if (number > 999 && number < 1000000){
number_prefix = number/1000;
number_suffix = "K";
}
This is pretty simple. If the number is greater than 999 (which means it is a thousand or more) and if it is lower than 1,000,000 (which means smaller than a million), it will set number_prefix to number divided by 1000 and set the number suffix to "K" - denoting a thousand.

Step Event: (Add the code)
Code:
if (number > 999999 && number < 1000000000){
number_prefix = number/1000000;
number_suffix = "M";
}
Similarly, here it checks if it is in the range of a million or more and less than a billion, and then sets the prefix and suffix accordingly.

Step Event: (Add the code)
Code:
if (number > 999999999){
number_prefix = number/1000000000;
number_suffix = "B";
}
Same goes for a billion, this one just doesn't have a limit. Any number a billion or beyond will be notated as B.

Step Event: (Add the code)
Code:
number_output = string(number_prefix) + number_suffix;
Here I'm converting number_prefix, which is a numeric variable, to a string using string(), adding number_suffix to it, and assigning the result to number_output.

Execute!


Works so well!

This gives us a number rounded off to two decimal digits. If you want to change this or have more control over the output (i.e., the number of digits/decimals), you can use string_format() instead of string() while converting number_prefix in the last line. Read about the function here.

Conclusion
It just became easier for you to show large values. It looks cool, too!


Thanks for being here, and have a great day!
 

FrostyCat

Member
There's a reason why experienced coders don't like manually negated conditions next to each other --- people inexperienced enough to like it almost never do it right. Pass 999999 or 999999999 to your code and see what I mean by this.

Had you used an else like you should have, this bug would not have been possible.
Code:
if (number >= 1000000000) {
  number_prefix = number/1000000000;
  number_suffix = "G";
}
else if (number >= 1000000) {
  number_prefix = number/1000000;
  number_suffix = "M";
}
else if (number >= 1000) {
  number_prefix = number/1000;
  number_suffix = "k";
}
 

matharoo

Udemy Instructor
There's a reason why experienced coders don't like manually negated conditions next to each other --- people inexperienced enough to like it almost never do it right. Pass 999999 or 999999999 to your code and see what I mean by this.

Had you used an else like you should have, this bug would not have been possible.
Code:
if (number >= 1000000000) {
  number_prefix = number/1000000000;
  number_suffix = "G";
}
else if (number >= 1000000) {
  number_prefix = number/1000000;
  number_suffix = "M";
}
else if (number >= 1000) {
  number_prefix = number/1000;
  number_suffix = "k";
}
That code does look better, but I don't get what bug you're talking about. :) Sorry
 

matharoo

Udemy Instructor
I'm talking about the bug in the code demonstrated in your screen capture GIF, see for yourself.
Sorry, I don't get what bug you're talking about. Could you please mention what the bug is about? I may be viewing this situation from a different point of view so I'm not seeing the bug, sorry. I may be just missing out something I don't know about.
 

FrostyCat

Member
Sorry, I don't get what bug you're talking about. Could you please mention what the bug is about? I may be viewing this situation from a different point of view so I'm not seeing the bug, sorry. I may be just missing out something I don't know about.
You should know what I mean by "your screen capture GIF", it's the one you have just under the header "Execute!".

This is what the code depicted on it reads:
Code:
if (number > 999 && number < 999999){
    number_prefix = number/1000;
    number_suffix = "K";
}
if (number > 999999 && number < 999999999) {
    number_prefix = number/1000000;
    number_suffix = "M";
}
if (number > 999999999) {
    number_prefix = number/1000000000;
    number_suffix = "G";
}
999999 and 999999999 are clearly not properly handled by this version of your code.
 

YellowAfterlife

ᴏɴʟɪɴᴇ ᴍᴜʟᴛɪᴘʟᴀʏᴇʀ
Forum Staff
Moderator
Sorry, I don't get what bug you're talking about. Could you please mention what the bug is about? I may be viewing this situation from a different point of view so I'm not seeing the bug, sorry. I may be just missing out something I don't know about.
In the code shown on the gif (rather than fixed-up snippets), entering "999999" would have shown "999999", because it's not covered by either of adjacent conditions.

On the general matter of topic, I usually approach this slightly differently,
Code:
/// string_format_short(number)
/// @author YellowAfterlife
var i = round(argument0);
var u = "";
if (i >= 10000) {
    i /= 1000;
    u = "K";
    if (i >= 10000) {
        i /= 1000;
        u = "M";
        if (i >= 10000) {
            i /= 1000;
            u = "B";
            if (i >= 10000) {
                i /= 1000;
                u = "T";
            }
        }
    }
    return string_format(i, 0, 1) + u;
} else return string(i);
Which moves on to the next unit only once the quantity in the current unit surpasses 4 digits.
 

matharoo

Udemy Instructor
Oh that! Yes, the GIF does show that bugged version, but the code as shown in the actual post is different - the fixed one. I think I need to remove the GIF then? Thanks for pointing out.
On the general matter of topic, I usually approach this slightly differently,
Thanks for the code, but I made this easy version so that it's easy for beginners. :)
 
Top