TheExDeus
|
|
Posted on: October 29, 2010, 01:34:35 pm |
|
|
Joined: Apr 2008
Posts: 1860
|
This is updated in 30.04.2011! Description: These are all draw_text functions + string_width, _height and string_width_ext, and _height_ext functions. They are very optimized (thanks to Josh) and so they should work great. Notice: They are mostly the same as GM ones, but GM's color interpolation and text position is a little different. There are two images to compare at the next page. Functions:
void draw_set_font(int fnt); void draw_text(int x,int y,string str); void draw_text_color(int x,int y,string str,int c1,int c2,int c3,int c4,double a);
void draw_text_ext(int x,int y,string str, int sep, int w); void draw_text_ext_color(int x,int y,string str, int sep,int w,int c1,int c2,int c3,int c4,double a);
void draw_text_transformed(double x,double y,string str,double xscale,double yscale,double rot); void draw_text_transformed_color(double x,double y,string str,double xscale,double yscale,double rot,int c1,int c2,int c3,int c4,double a);
void draw_text_ext_transformed(double x,double y,string str,int sep,int w, double xscale,double yscale,double rot); void draw_text_ext_transformed_color(double x,double y,string str,int sep,int w,double xscale,double yscale,double rot,int c1,int c2,int c3,int c4,double a);
unsigned int font_get_texture(int fnt); int font_add_sprite(int spr, unsigned char first, bool prop, int sep); unsigned int font_get_texture_width(int fnt); unsigned int font_get_texture_height(int fnt);
int string_width(string str); int string_height(string str);
unsigned int string_width_ext(string str, int sep, int w); unsigned int string_height_ext(string str, int sep, int w);
unsigned int string_width_line(string str, int line); unsigned int string_width_ext_line(string str, int w, int line); unsigned int string_width_ext_line_count(string str, int w); You can download GSFont.h and .cpp in attachment, as well as a little screenshot. It shows draw_text_color and draw_text_ext_transformed_color.
P.s.: It wasn't as easy as I thought at the beginning. Mostly because of the trig for _transform and _ext functions that come with it. Also, what do you suggest on dealing with the # newline character? The easiest thing would be searching for all # and then checking if / is in front of it, if its not then it is a newline char, if there is a / in front, then just replace /# with # and draw it. But I think there should be some better way, like using regular expressions, but that could end up being a lot slower.?
Also, "prop" argument doesn't work in font_add_sprite. With the font sprite I tried it with it just returns 0x0 size, so it doesn't draw anything. I will look into that if Josh doesn't.
edit: Nevermind about the # question. Enigma will do this automatically, at least Josh said so.
edit2: I added string_width, _height and _ext functions.
|
|
« Last Edit: April 29, 2011, 04:10:16 pm by HaRRiKiRi »
|
Logged
|
|
|
|
|
|
|
|
IsmAvatar
|
|
Reply #5 Posted on: October 29, 2010, 04:59:21 pm |
|
|
LateralGM Developer
Location: Pennsylvania/USA Joined: Apr 2008
Posts: 877
|
That's what I meant, I just didn't feel like writing the code out. In fact, I don't know if GM does this, but if "//#" is displays the / glyph followed by a newline, you could do that with a boolean that toggles for each '/' encountered, and you don't have to look backwards then.
Also, watch out for EnigmaSettings.cppStrings, which is currently not passed to Enigma yet, but is togglable by the user. When toggled, # is treated as a literal # glyph, and / no longer serves as an escape character.
|
|
« Last Edit: October 29, 2010, 05:02:13 pm by IsmAvatar »
|
Logged
|
|
|
|
|
Josh @ Dreamland
|
|
Reply #7 Posted on: October 29, 2010, 06:18:36 pm |
|
|
Prince of all Goldfish
Location: Pittsburgh, PA, USA Joined: Feb 2008
Posts: 2950
|
First off, I'm quite impressed at how quickly you got on this; I haven't even announced that fonts were in. More importantly, I have to express some concerns before I adopt these: 1) Trig functions and multiple multiplication operations are performed in each loop iteration for the transformed font functions. That is a costly move compared to what could be accomplished with a simple precalculation (considering none of them are dynamic, as far as I know). 2) I was not quite done with linear fonts at the time of commit. For example, look what happens to the "I" in this screen shot. It's not the spacing that concerns me as much as the fact that "I" is only one pixel wide. I fear the worst. Your work is, of course, appreciated greatly nonetheless. Neither of those are a serious detriment; I will just need to go over them when I have a few more answers. Good work. Also, I was looking into regex for ENIGMA, but the best interpreter out there for C++ is apparently Boost, and they totally fucking overkill everything. I just want a damn preg_match and preg_replace for ENIGMA; it shouldn't be 65 source files and it shouldn't have a fucking config file. Damn it. And one more thing: in case you're wondering where that screenshot came from, it started out as an example someone posted on the GMC, which I stumbled upon looking for an explanation of the parameters to font_add_sprite().
|
|
« Last Edit: October 29, 2010, 06:25:52 pm by Josh @ Dreamland »
|
Logged
|
"That is the single most cryptic piece of code I have ever seen." -Master PobbleWobble "I disapprove of what you say, but I will defend to the death your right to say it." -Evelyn Beatrice Hall, Friends of Voltaire
|
|
|
|
Josh @ Dreamland
|
|
Reply #9 Posted on: October 29, 2010, 06:32:09 pm |
|
|
Prince of all Goldfish
Location: Pittsburgh, PA, USA Joined: Feb 2008
Posts: 2950
|
Please don't do that. ENIGMA lets you choose how to escape string literals. There are two settings, though you can't yet switch between them: 1) GML. "Quote inside quote looks like " + '"this."' + " Newlines are escaped from '#' automatically." 2) C++. "Quote inside quote looks like \"this.\" Newlines must use \\r\\n, like this: \r\n ^ line ^ \r\n # does nothing."
|
|
|
Logged
|
"That is the single most cryptic piece of code I have ever seen." -Master PobbleWobble "I disapprove of what you say, but I will defend to the death your right to say it." -Evelyn Beatrice Hall, Friends of Voltaire
|
|
|
|
Josh @ Dreamland
|
|
Reply #11 Posted on: October 29, 2010, 07:20:32 pm |
|
|
Prince of all Goldfish
Location: Pittsburgh, PA, USA Joined: Feb 2008
Posts: 2950
|
1) It is \r\n 2) The \r is optional in everything not strictly Microsoft (IE, not Notepad).
|
|
|
Logged
|
"That is the single most cryptic piece of code I have ever seen." -Master PobbleWobble "I disapprove of what you say, but I will defend to the death your right to say it." -Evelyn Beatrice Hall, Friends of Voltaire
|
|
|
TheExDeus
|
|
Reply #12 Posted on: October 30, 2010, 03:59:55 am |
|
|
Joined: Apr 2008
Posts: 1860
|
1) Trig functions and multiple multiplication operations are performed in each loop iteration for the transformed font functions. That is a costly move compared to what could be accomplished with a simple precalculation (considering none of them are dynamic, as far as I know). I do know that trig is costly, and I did my best to optimize it by calculating sin(rot) and cos(rot) only once. Also, cos(M_PI+rot) and sin(M_PI/2+rot) can be calculated only once and so on. So I will optimize it as much as I can. In the end it will be about 8 trig functions (4 sin and 4 cos I think) that is calculated in each draw call, but not for each symbol. So it shouldn't be that slow... should it? The only slow thing that needs to be calculated for every symbol is sqrt(x^2+y^2) (Pythagoras theorem), but it could be possible to fix that too. So I will optimize the code a bit, and maybe clean it up a bit too. Then I will show it again. ENIGMA lets you choose how to escape string literals. There are two settings, though you can't yet switch between them: 1) GML. "Quote inside quote looks like " + '"this."' + " Newlines are escaped from '#' automatically." 2) C++. "Quote inside quote looks like \"this.\" Newlines must use \\r\\n, like this: \r\n ^ line ^ \r\n # does nothing." Ou, so we don't need to add that for every draw text function? Nice. edit: Ok, I changed transform functions so all trig is calculated only once per call. Not once per symbol. This should speed it up a lot, but I want Enigma to use LGM Font resource before I benchmark. edit2: That sqrt() could be removed by just taking width as xx*xx + yy*yy and then comparing it to w*w no? Because I have heard that sqrt() is slow. edit3: Ok, reuploaded again. Now sqrt() is replaced and so should be even faster. edit4: Also, that "ENIGMA lets you choose how to escape string literals", I know how it would work on compile time, but if I need to change the string while running the game? Wouldn't it need to have something to do with # replacing in the functions themselves? Or you will need a way to catch the argument going to the text function and replace #, and only then pass the changed string to the function. Not sure how that would work. edit5: I hate double posting so this editing will continue. I just added string_width, _height and _ext functions. They do work as far as I tested them, but I did found a bug in string() function. string() doesn't return the correct string when there is unsigned int as an argument. I thought as string_width can't be negative I will use unsigned int as the return type, and it works further in calculations (like position and stuff), but when I put draw_text(10,10,string(string_height())) it will shows "322" for example, and "32" is the actual height, and that extra 2 is a bug. So.. just giving the heads up. Also, I would suggest cleaning up the files. There are a lot of outdated, and as far I as I know, unused files. Like GMsprite.h and so on.
|
|
« Last Edit: October 30, 2010, 08:30:14 am by HaRRiKiRi »
|
Logged
|
|
|
|
|
|
|