X-Git-Url: https://git.ucc.asn.au/?a=blobdiff_plain;f=Usermode%2FApplications%2Faxwin3_src%2FWM%2Frenderers%2Frichtext.c;h=eca5765bad4a842ebc4d91eb085cb8595ce51b1c;hb=507f19941f45bca7c1de783a394f56b15f10be4d;hp=35fd5ef9303b68ddfe2016189c1f7ca06e59e36f;hpb=d02a9dd1f6752a65efe6a8326a86a288a4165c94;p=tpg%2Facess2.git diff --git a/Usermode/Applications/axwin3_src/WM/renderers/richtext.c b/Usermode/Applications/axwin3_src/WM/renderers/richtext.c index 35fd5ef9..eca5765b 100644 --- a/Usermode/Applications/axwin3_src/WM/renderers/richtext.c +++ b/Usermode/Applications/axwin3_src/WM/renderers/richtext.c @@ -8,6 +8,30 @@ #include #include #include +#include // sscanf + +#define LINES_PER_BLOCK 30 + +// === TYPES === +typedef struct sRichText_LineBlock +{ + struct sRichText_LineBlock *Next; + int FirstLine; + char *Lines[LINES_PER_BLOCK]; +} tRichText_LineBlock; +typedef struct sRichText_Window +{ + int DispLines, DispCols; + int FirstVisRow, FirstVisCol; + int nLines, nCols; + int CursorRow, CursorCol; + tRichText_LineBlock FirstBlock; + tColour DefaultFG; + tColour DefaultBG; + tFont *Font; + + short LineHeight; +} tRichText_Window; // === PROTOTYPES === int Renderer_RichText_Init(void); @@ -32,12 +56,132 @@ int Renderer_RichText_Init(void) tWindow *Renderer_RichText_Create(int Flags) { - return NULL; + tRichText_Window *info; + tWindow *ret = WM_CreateWindowStruct( sizeof(*info) ); + if(!ret) return NULL; + info = ret->RendererInfo; + // Everything starts at zero? + return ret; +} + +static inline int Renderer_RichText_RenderText_Act(tWindow *Window, tRichText_Window *info, int X, int Row, const char *Text, int Bytes, tColour FG, tColour BG) +{ + int rwidth; + // TODO: Fill only what is needed + WM_Render_DrawRect(Window, X, Row*info->LineHeight, + Window->W - X, info->LineHeight, + BG + ); + rwidth = WM_Render_DrawText(Window, + X, Row*info->LineHeight, + Window->W - X, info->LineHeight, + info->Font, FG, + Text, Bytes + ); + return rwidth; +} + +void Renderer_RichText_RenderText(tWindow *Window, int Line, const char *Text) +{ + tRichText_Window *info = Window->RendererInfo; + tColour fg = info->DefaultFG; + tColour bg = info->DefaultBG; + int bBold = 0; + int bULine = 0; + int bItalic = 0; + int bRender = 0; + int curx = 0; + const char *oldtext = Text; + + for( int i = 0; i < info->FirstVisCol + info->DispCols; i ++ ) + { + char ch, flags; + int len; + + if( i == info->FirstVisCol ) + bRender = 1; + + ch = *Text++; + if( ch == 0 ) break; + if( ch <=3 && bRender ) { + // Render previous characters + curx += Renderer_RichText_RenderText_Act(Window, info, curx, Line, + oldtext, Text - oldtext, fg, bg); + oldtext = Text; + } + switch(ch) + { + case 1: // FG Select (\1 RRGGBB) + len = sscanf(Text, "%6x", &fg); + if( len != 6 ) { + // Bad client + } + Text += len; + break ; + case 2: // BG Select (\2 RRGGBB) + len = sscanf(Text, "%6x", &bg); + if( len != 6 ) { + // Bad client + } + Text += len; + break ; + case 3: // Flagset (0,it,uline,bold) + len = sscanf(Text, "%1x", &flags); + if( len != 1 ) { + // Bad client + } + Text += len; + bItalic = !!(flags & (1 << 2)); + bULine = !!(flags & (1 << 1)); + bBold = !!(flags & (1 << 0)); + break ; + default: // Any char, nop + break; + } + } + curx += Renderer_RichText_RenderText_Act(Window, info, curx, Line, oldtext, Text - oldtext, fg, bg); + WM_Render_DrawRect(Window, curx, Line * info->LineHeight, Window->W - curx, info->LineHeight, info->DefaultBG); } void Renderer_RichText_Redraw(tWindow *Window) { - return; + tRichText_Window *info = Window->RendererInfo; + int i; + tRichText_LineBlock *lines = &info->FirstBlock; + + // Locate the first line block + for( i = info->FirstVisRow; i > LINES_PER_BLOCK && lines; i -= LINES_PER_BLOCK ) + lines = lines->Next; + + for( i = 0; i < info->DispLines && lines; i ++ ) + { + if( i >= info->nLines - info->FirstVisRow ) + break; + // TODO: Dirty rectangles? + WM_Render_DrawRect(Window, + 0, i*info->LineHeight, + Window->W, info->LineHeight, + info->DefaultBG + ); + // TODO: Horizontal scrolling? + // TODO: Formatting + //Renderer_RichText_RenderText(Window, i, lines->Lines[i % LINES_PER_BLOCK]); + WM_Render_DrawText(Window, + 0, i*info->LineHeight, + Window->W, info->LineHeight, + info->Font, info->DefaultFG, + lines->Lines[i % LINES_PER_BLOCK], + -1); + + if( (i + 1) % LINES_PER_BLOCK == 0 ) + lines = lines->Next; + } + // Clear out i -- info->DispLines + WM_Render_DrawRect(Window, + 0, i*info->LineHeight, + Window->W, (info->DispLines-i)*info->LineHeight, + info->DefaultBG + ); } int Renderer_RichText_HandleMessage(tWindow *Target, int Msg, int Len, const void *Data)