Page 2 of 2 FirstFirst 12
Results 11 to 16 of 16

Thread: word wrap? no problem! [SRC | FREE]

  1. #11

    word wrap? no problem! [SRC | FREE]

    This board needs a tumbleweed smiley (or some people that give feedback).
    This is my game project - Top Down City:
    http://www.pascalgamedevelopment.com...y-Topic-Reboot

    My OpenAL audio wrapper with Intelligent Source Manager to use unlimited:
    http://www.pascalgamedevelopment.com...source+manager

  2. #12

    word wrap? no problem! [SRC | FREE]

    I have not had a chance to try your code, but if you say it works I believe you .
    <br /><br />There are a lot of people who are dead while they are still alive. I want to be alive until the day I die.<br />-= Paulo Coelho =-

  3. #13

    word wrap? no problem! [SRC | FREE]

    lol, ofcourse it works
    This is my game project - Top Down City:
    http://www.pascalgamedevelopment.com...y-Topic-Reboot

    My OpenAL audio wrapper with Intelligent Source Manager to use unlimited:
    http://www.pascalgamedevelopment.com...source+manager

  4. #14

    word wrap? no problem! [SRC | FREE]

    ok, i now realised i need a function to get text size extents when word-wrapped, so i made another function, the word wrap function also got some fixes, so if you happen to have used this function you should update it.


    Code:
    Procedure DrawText&#40;x, y, mx, my, trans&#58; single; const text&#58; string; fontn, wordwrap&#58; integer&#41;;
    var
    i&#58; integer;
    b&#58; byte;
    cw&#58; integer;
    ta, tb, tc, td&#58; single;
    va, vb, vc, vd&#58; single;
    
    // current left edge
    L&#58; single;
    // skip this much of characters from being parsed
    SK&#58; integer;
    
    wraps&#58; array&#91;0..31&#93; of word; // i dont think my game will ever need / have more than 32 word wraps
    maxwrap&#58; integer;
    currwrap&#58; integer;
    lastspace&#58; integer; // faster word wrap
    
    procedure Vwrap&#40;c&#58; integer&#41;;
    begin
    cw&#58;= 0;
    wraps&#91;maxwrap&#93;&#58;= c;
    maxwrap&#58;= maxwrap +1;
    // since there is no array bounds checking this takes care for safety
    if maxwrap > high&#40;wraps&#41; then maxwrap&#58;= high&#40;wraps&#41;;
    end;
    
    // this function processes the string and remembers all locations where lines should wrap &#40;line returns, word wraps, etc..&#41;
    procedure MeasureWraps;
    var
    i&#58; integer;
    begin
    maxwrap&#58;= 0;
    lastspace&#58;= -1; // faster word wrap
    
    for i&#58;= 1 to length&#40;text&#41; do begin
    
    if SK <> 0 then begin SK&#58;= SK -1; continue; end; // skipping text coding characters
    
    b&#58;= byte&#40;text&#91;i&#93;&#41;; // we need a integer type to use for array access,
    
    if b = 32 then lastspace&#58;= i; // remember last space for word wrapping
    
    if b = 126 then begin sk&#58;= 2; continue; end;  // skip ~X~ color coding keyword
    
    // next character would fall over the specified text width dimension, wrap at last known space character
    if &#40;wordwrap <> 0&#41; and &#40;cw + trunc&#40;FontGeo&#91;fontn, b&#93;.spacing * mx&#41; > wordwrap&#41; then begin
    Vwrap&#40;lastspace&#41;; continue;
    end;
    
    if b = 13 then begin Vwrap&#40;i&#41;; continue; end; // return character - go to new line
    
    // add character width to this line text width
    cw&#58;= cw + trunc&#40;FontGeo&#91;fontn, b&#93;.spacing * mx&#41;;
    
    end;
    end;
    
    // go to next line
    procedure wrap;
    begin
    cw&#58;= 0;
    L&#58;= L + &#40;FontGeo&#91;fontn, 32&#93;.H * my&#41;;
    end;
    
    // process color codes
    procedure EatColor; // changes font color depending on keyword
    begin
    if text&#91;i + 1&#93; = 'W' then glcolor4f&#40;1,     1,   1, trans&#41;; // white
    if text&#91;i + 1&#93; = 'N' then glcolor4f&#40;0,     0,   0, trans&#41;; // none - black
    if text&#91;i + 1&#93; = 'R' then glcolor4f&#40;0.9,   0,   0, trans&#41;; // red
    if text&#91;i + 1&#93; = 'G' then glcolor4f&#40;0,   0.9,   0, trans&#41;; // green
    if text&#91;i + 1&#93; = 'B' then glcolor4f&#40;0,     0, 0.9, trans&#41;; // blue
    
    if text&#91;i + 1&#93; = 'Y' then glcolor4f&#40;1.0,   1,   0, trans&#41;; // yellow
    if text&#91;i + 1&#93; = 'T' then glcolor4f&#40;0,     1,   1, trans&#41;; // teal
    if text&#91;i + 1&#93; = 'O' then glcolor4f&#40;1,   0.7734375, 0.09765625, trans&#41;; // orange
    
    SK&#58;= 2; // skip 2 chars so the color coding is like '~C~' where C is color
    end;
    
    
    begin
    
    if length&#40;text&#41; = 0 then exit; // idiot proof fuse
    
    // ensure variables are reset for preprocessing
    
    cw&#58;= 0;
    SK&#58;= 0;
    fillchar&#40;wraps, sizeof&#40;wraps&#41;, $FF&#41;;
    MeasureWraps;
    
    // ensure variables are reset for rendering
    cw&#58;= 0;
    L&#58;= 0;
    SK&#58;= 0;
    currwrap&#58;= 0;
    
    glBindTexture&#40;GL_TEXTURE_2D, Font.tex&#91;fontn&#93;.GLID&#41;;
    glBegin&#40;GL_quads&#41;;
    
    for i&#58;= 1 to length&#40;text&#41; do begin
    
    if SK <> 0 then begin SK&#58;= SK -1; continue; end;
    
    b&#58;= byte&#40;text&#91;i&#93;&#41;; // we need a integer type to use for array access
    
    if b = 126 then begin eatcolor; continue; end;
    
    // find out if we are supposed to wrap at this character
    if currwrap < maxwrap then
    if wraps&#91;currwrap&#93; = i then begin wrap; currwrap&#58;= currwrap +1; continue; end;
    
    // get tex coords from array
    ta&#58;= FontGeo&#91;fontn, b&#93;.X / 256;
    tb&#58;= FontGeo&#91;fontn, b&#93;.X / 256 + FontGeo&#91;fontn, b&#93;.W / 256;
    tc&#58;= FontGeo&#91;fontn, b&#93;.Y / 256;
    td&#58;= FontGeo&#91;fontn, b&#93;.Y / 256 + FontGeo&#91;fontn, b&#93;.H / 256;
    
    // build vertices
    va&#58;= cw;                                        // top left
    vb&#58;= va + &#40;FontGeo&#91;fontn, b&#93;.W * mx&#41;;           // top right
    vc&#58;= trunc&#40;&#40;FontGeo&#91;fontn, b&#93;.YOFS * my&#41; + L&#41;;  // bottom left, this needs to be trunc-ed here and nowhere else!
    vd&#58;= trunc&#40;vc + &#40;FontGeo&#91;fontn, b&#93;.H * my&#41;&#41;;    // bottom right, this needs to be trunc-ed here and nowhere else!
    
    // crunch
    gltexcoord2f&#40;ta, tc&#41;; glvertex2fwin&#40;x + va, y + vc&#41;;
    gltexcoord2f&#40;ta, td&#41;; glvertex2fwin&#40;x + va, y + vd&#41;;
    gltexcoord2f&#40;tb, td&#41;; glvertex2fwin&#40;x + vb, y + vd&#41;;
    gltexcoord2f&#40;tb, tc&#41;; glvertex2fwin&#40;x + vb, y + vc&#41;;
    
    // add character size to left edge
    cw&#58;= cw + trunc&#40;FontGeo&#91;fontn, b&#93;.spacing * mx&#41;;
    
    end;
    
    glend;
    
    end;
    
    function  GetTextExtents&#40;mx, my&#58; single; const text&#58; string; fontn, wordwrap&#58; integer&#41;&#58; IRect;
    var
    i&#58; integer;
    b&#58; byte;
    cw&#58; integer;
    
    // skip this much of characters from being parsed
    SK&#58; integer;
    
    LongestLine&#58; single;
    LinesAll&#58; single;
    
    maxwrap&#58; integer;
    lastspace, lastwrap&#58; integer; // faster word wrap
    lastspacew&#58; single;
    
    procedure Vwrap&#40;linew&#58; single&#41;;
    begin
    if cw > linew then LongestLine&#58;= linew;
    cw&#58;= 0;
    lastspacew&#58;= 0;
    maxwrap&#58;= maxwrap +1;
    end;
    
    begin
    
    if length&#40;text&#41; = 0 then exit; // idiot proof fuse
    
    // ensure variables are reset for preprocessing
    
    cw&#58;= 0;
    SK&#58;= 0;
    LongestLine&#58;= 0;
    lastwrap&#58;= 0;
    LinesAll&#58;= 1;
    lastspacew&#58;= 0;
    
    maxwrap&#58;= 0;
    lastspace&#58;= -1; // faster word wrap
    
    for i&#58;= 1 to length&#40;text&#41; do begin
    
    if SK <> 0 then begin SK&#58;= SK -1; continue; end; // skipping text coding characters
    
    b&#58;= byte&#40;text&#91;i&#93;&#41;; // we need a integer type to use for array access,
    
    if b = 32 then begin lastspace&#58;= i; lastspacew&#58;= cw end; // remember last space for word wrapping
    
    if b = 126 then begin sk&#58;= 2; continue; end;  // skip ~X~ color coding keyword
    
    // next character would fall over the specified text width dimension, wrap at last known space character
    if &#40;wordwrap <> 0&#41; and &#40;cw + trunc&#40;FontGeo&#91;fontn, b&#93;.spacing * mx&#41; > wordwrap&#41; then begin
    Vwrap&#40;lastspacew&#41;; continue;
    end;
    
    if b = 13 then begin Vwrap&#40;cw&#41;; continue; end; // return character - go to new line
    
    // add character width to this line text width
    cw&#58;= cw + trunc&#40;FontGeo&#91;fontn, b&#93;.spacing * mx&#41;;
    
    end;
    
    LinesAll&#58;= LinesAll + maxwrap;
    
    result.left&#58;= 0;
    result.top&#58;= 0;
    if LongestLine <> 0 then result.Right&#58;= trunc&#40;LongestLine&#41; else result.Right&#58;= cw; 
    result.Bottom&#58;= trunc&#40;LinesAll * &#40;FontGeo&#91;fontn, 32&#93;.H * my&#41;&#41;;
    
    end;
    This is my game project - Top Down City:
    http://www.pascalgamedevelopment.com...y-Topic-Reboot

    My OpenAL audio wrapper with Intelligent Source Manager to use unlimited:
    http://www.pascalgamedevelopment.com...source+manager

  5. #15

    Re: word wrap? no problem! [SRC | FREE]

    Quote Originally Posted by Delfi
    You probably wondered in early days how to add word wrap and line returns to your opengl text routines, basicly this is just what you want, this function will draw a text and wrap it by character (not words!) to fir the width you want.

    Code:
    Procedure DrawFont&#40;x, y, mx, my&#58; single; const text&#58; string; fontn, wordwrap&#58; integer&#41;;
    var
    i&#58; integer;
    b&#58; byte;
    cw&#58; integer;
    ta, tb, tc, td&#58; single;
    va, vb, vc, vd&#58; single;
    
    // current left edge
    L&#58; single;
    // skip this much of characters from being parsed
    SK&#58; integer;
    
    procedure wrap;
    begin
    cw&#58;= 0;
    L&#58;= L + &#40;FontGeo&#91;32&#93;.H * my&#41;;
    end;
    
    procedure EatColor; // changes font color depending on keyword
    begin
    if text&#91;i + 2&#93; = 'W' then glcolor3f&#40;1, 1, 1&#41;;
    if text&#91;i + 2&#93; = 'N' then glcolor3f&#40;0, 0, 0&#41;;
    if text&#91;i + 2&#93; = 'R' then glcolor3f&#40;1, 0, 0&#41;;
    if text&#91;i + 2&#93; = 'G' then glcolor3f&#40;0, 1, 0&#41;;
    if text&#91;i + 2&#93; = 'B' then glcolor3f&#40;0, 0, 1&#41;;
    SK&#58;= 2; // skip 2 chars so the color coding is like ~G~
    end;
    
    begin
    
    if length&#40;text&#41; = 0 then exit; // idiot proof fuse
    
    // ensure variables are reset
    cw&#58;= 0;
    L&#58;= 0;
    SK&#58;= 0;
    
    glBindTexture&#40;GL_TEXTURE_2D, Font.tex&#91;fontn&#93;.GLID&#41;;
    glBegin&#40;GL_quads&#41;;
    
    for i&#58;= 0 to length&#40;text&#41; do begin
    
    if SK <> 0 then begin SK&#58;= SK -1; continue; end;
    
    b&#58;= byte&#40;text&#91;i + 1&#93;&#41;; // we need a integer type to use for array access,
    
    // next character would wrap
    if &#40;wordwrap <> 0&#41; and &#40;cw + trunc&#40;FontGeo&#91;b&#93;.spacing * mx&#41; > wordwrap&#41; then wrap;
    
    // return character - go to new line
    if b = 13 then begin wrap; continue; end;
    // ~X~ color coding keyword
    if b = 126 then begin eatcolor; continue; end;
    
    // get tex coords from array
    ta&#58;= FontGeo&#91;b&#93;.X / 256;
    tb&#58;= FontGeo&#91;b&#93;.X / 256 + FontGeo&#91;b&#93;.W / 256;
    tc&#58;= FontGeo&#91;b&#93;.Y / 256;
    td&#58;= FontGeo&#91;b&#93;.Y / 256 + FontGeo&#91;b&#93;.H / 256;
    
    // build vertices
    va&#58;= cw;                                          // top left
    vb&#58;= va + &#40;FontGeo&#91;b&#93;.W * mx&#41;;                    // top right
    vc&#58;= &#40;FontGeo&#91;b&#93;.YOFS * my&#41; + L;  // bottom left
    vd&#58;= vc + &#40;FontGeo&#91;b&#93;.H * my&#41;;                    // bottom right
    
    // crunch
    gltexcoord2f&#40;ta, tc&#41;; glvertex2fwin&#40;x + va, y + vc&#41;;
    gltexcoord2f&#40;ta, td&#41;; glvertex2fwin&#40;x + va, y + vd&#41;;
    gltexcoord2f&#40;tb, td&#41;; glvertex2fwin&#40;x + vb, y + vd&#41;;
    gltexcoord2f&#40;tb, tc&#41;; glvertex2fwin&#40;x + vb, y + vc&#41;;
    
    // add character size to left edge
    cw&#58;= cw + trunc&#40;FontGeo&#91;b&#93;.spacing * mx&#41;;
    
    end;
    
    glend;
    
    end;
    character support records:

    Code:
    Glyph = packed record
    X, Y, W, H, YOFS, SPACING&#58; byte;
    end;
    
    FontGeo&#58; array&#91;0..255&#93; of Glyph;
    license: none, you can even eat it or whatever you want, but i take no responsibility for aynthing.

    2d opengl routines:

    Code:
    //this draws a vertex in windows coordinate system
    procedure glvertex2fwin&#40;const x, y&#58; single&#41;;
    begin
    glvertex2f&#40;x, win_height - y&#41;;
    end;
    how to get into this 2d mode?


    Code:
    // Dwarf with Axe - GAMEDEV forums&#58; 18 July 2002 6&#58;12&#58;57 PM
    //
    // There have been thousands of posts along the lines of
    // "How do I do 2d in OpenGL" to "Duuuhde, I wunt too maek
    // a two dee gaem in ohpun jee el; how do eye set uhp two dee???!?"
    //
    // I have developed a simple, nice, pretty way for all of you to have your 2D fun.
    
    procedure GlEnable2D;
    var
    vport&#58; array&#91;0..3&#93; of integer;
    begin
    glGetIntegerv&#40;GL_VIEWPORT, @vPort&#41;;
    
    glMatrixMode&#40;GL_PROJECTION&#41;;
    glPushMatrix;
    glLoadIdentity;
    glOrtho&#40;0, vPort&#91;2&#93;, 0, vPort&#91;3&#93;, -1, 1&#41;;
    
    glMatrixMode&#40;GL_MODELVIEW&#41;;
    glPushMatrix;
    glLoadIdentity;
    end;
    
    procedure GlDisable2D;
    begin
    glMatrixMode&#40;GL_PROJECTION&#41;;
    glPopMatrix;
    glMatrixMode&#40;GL_MODELVIEW&#41;;
    glPopMatrix;
    end;
    No offense dude, but any chance you can add indentation in your source code?

    No indentation...SHUDDER....

    Cheers,
    Paul.

  6. #16

    Re: word wrap? no problem! [SRC | FREE]

    Quote Originally Posted by paul_nicholls
    No offense dude, but any chance you can add indentation in your source code?

    No indentation...SHUDDER....

    Cheers,
    Paul.
    hehe, you are right, but the reason why the code lacks indentation is because of my syntax highlighting setup, and because sometimes too indented code becomes too wide to be on screen and requires too much horisontal scrolling.

    i bet ill get flamed for saying that :roll:
    This is my game project - Top Down City:
    http://www.pascalgamedevelopment.com...y-Topic-Reboot

    My OpenAL audio wrapper with Intelligent Source Manager to use unlimited:
    http://www.pascalgamedevelopment.com...source+manager

Page 2 of 2 FirstFirst 12

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •