This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

How to change text.c functions in SimpleWidget library for DM368 to clear OSD

Hi. I’m working on a project with the LeopardBoard DM368 which includes writing some texts on screen (OSD) and I’m using Davinci SDK 4.02.00.06 version. I’m using TI SimpleWidget library to write texts on screen. I can successfully write on screen but I want to clear that region I want to write on first. Cause now if there was a text on that region from before then the new text wouldn't look very nice and they would get on each other! So I'm looking for a way to clear a pixel before writing something on it.

This is the function I have written that uses a couple of text.c functions included in SimpleWidget library It takes a UI buffer and the desired text, its color, its background color, transparency(if yes then it ignores background color), blending value and of course XY position on the screen where it will put the text on:

Int Text_showPrev(UI_Handle hUI, Char *txt, Int height, Int x, Int y, UInt32 colorVal, UInt32 bgColorVal, UInt8 keyEnable,UInt8 blendVal)
{
	Buffer_Handle hBuf,hBufAttr;
	Int ret;
	BufferGfx_Dimensions dim;

	if(getOSDAttrBuf(hUI, &hBuf, &hBufAttr))
		return FAILURE;

	BufferGfx_getDimensions(hBuf, &dim);
	if((x<0)||(y<0)||(x>=dim.width)||(y>=dim.height))
	{
		ERR("Invalid Param for show text\n");
		return FAILURE;
	}

	y=y+height+1;
	
//	keyEnable = 1 means transparent !
	if(keyEnable)
		ret=Text_show_key(hUI->hFont, txt, height, x, y, hBuf, colorVal, blendVal);
	else
		ret=Text_show_col(hUI->hFont, txt, height, x, y, hBuf, colorVal, bgColorVal, blendVal);
// 	Text_show(hUI->hFont, txt, height, x, y, hBuf);
	if(ret)
	{
		ERR("Failed to show text prev\n");
		return FAILURE;
	}

	if(Text_show_blend(hUI->hFont, txt, height, x, y, hBufAttr, keyEnable, blendVal))
	{
		ERR("Failed to show text prev\n");
		return FAILURE;
	}

	return putOSDAttrBuf(hUI, hBuf, hBufAttr);
}

As you can see I'm calling for Text_show_key() or Text_show_col() (depending on being transparent or not) and also Text_show_blend() at the end. I couldn't make much sense from the implementation of this functions in text.c which is attached to the post. Could you guys please check if there is a way that I could somehow make a change so they clear the pixels before they change its value. 

I don't know how exactly the buffer works or how the blending works. Unfortunately I couldn't find a documentation for this matter. It's kind of urgent. 


/*
 * Text.c
 *
 * ============================================================================
 * Copyright (c) Texas Instruments Inc 2009
 *
 * Use of this software is controlled by the terms and conditions found in the
 * license agreement under which this software has been supplied or provided.
 * ============================================================================
 */

#include <stdio.h>

#include <ft2build.h>
#include FT_FREETYPE_H
#include FT_GLYPH_H

#include <xdc/std.h>
#include <ti/sdo/dmai/BufferGfx.h>

#include <ti/sdo/simplewidget/Text.h>
#include <ti/sdo/simplewidget/Font.h>
#include <ti/sdo/simplewidget/Screen.h>
#include <ti/sdo/simplewidget/Convert.h>

#define GET_2BPP_BYTE(x) ((x) >> 2)
#define GET_2BPP_SHIFT(x) (((x) % 4) * 2)


Int Text_show_blend(Font_Handle hFont, Char *txt, Int fontHeight, Int x, Int y,
              Buffer_Handle hBuf, UInt8 keyEnable, UInt8 blendVal)
{
    BufferGfx_Dimensions dim;
    FT_Error error;
    Int index;
    Int width, height;
    Int i, j, p, q, x_max, y_max, sp;
    UInt8 *src;
    FT_Vector pen;
    FT_Face face = (FT_Face) hFont->face;
    UInt8 *ptr, *rowPtr;
    UInt8 blendCnt,blend0;
    Int x2;

    BufferGfx_getDimensions(hBuf, &dim);

    FT_Set_Char_Size(face,
                     fontHeight << 6,
                     fontHeight << 6,
                     100,
                     100);

    pen.x = x << 6;
    pen.y = (dim.height - y) << 6;

    blend0=blendVal&0xf;
    while (*txt) {
    	FT_Set_Transform(face, NULL, &pen);

    	index = FT_Get_Char_Index(face, *txt);

    	error = FT_Load_Glyph(face, index, 0);
    	if (error) {
    		SW_ERR("Failed to load glyph for character %c\n", *txt);
    		break;
    	}

    	if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) {
    		error = FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL);
    		if (error) {
    			SW_ERR("Failed to render glyph for character %c\n", *txt);
    			break;
    		}
    	}

    	width = face->glyph->bitmap.width;
    	height = face->glyph->bitmap.rows;


    	x = face->glyph->bitmap_left;
    	y = dim.height - face->glyph->bitmap_top;
    	x2=x>>1;

    	x_max = x + width;
    	y_max = y + height;

    	src = face->glyph->bitmap.buffer;

    	ptr = (UInt8 *) Buffer_getUserPtr(hBuf) + y * dim.lineLength;

    	printf("changes 5 \n");

    	for (j = y, q = 0; j < y_max; j++, q++) {
    		blendCnt=(x&0x1)<<2;
    		rowPtr = ptr + x2;
    		for (i = x, p = 0; i < x_max; i++, p++) {

    			if (i >= dim.width || j >= dim.height)
    				continue;

    			sp = q * width + p;

    			if(keyEnable && src[sp])
        		//if(keyEnable )
    			{
    				if(blend0)
    					*rowPtr|=(blend0<<blendCnt);
    				else
    					*rowPtr&=(0xf0>>blendCnt);
    			}
    			else if(!keyEnable)
    			{
    				if(blend0)
    					*rowPtr|=(blend0<<blendCnt);
    				else
    					*rowPtr&=(0xf0>>blendCnt);
    			}

    			blendCnt+=4;
    			if(blendCnt==8)
    			{
    				blendCnt=0;
    				rowPtr++;
    			}
    		}
    		ptr += dim.lineLength;
    	}

    	txt++;

    	pen.x += face->glyph->advance.x;
    	pen.y += face->glyph->advance.y;

    }

    return SW_EOK;
}

Int Text_show(Font_Handle hFont, Char *txt, Int fontHeight, Int x, Int y,
              Buffer_Handle hBuf)
{
    BufferGfx_Dimensions dim;
    FT_Error error;
    Int index;
    Int width, height;
    Int i, j, p, q, x_max, y_max, sp;
    UInt32 srcValue, dstValue;
    UInt8 *src;
    FT_Vector pen;
    FT_Face face = (FT_Face) hFont->face;
    Convert_Mode cMode;
    Int inc, start;
    UInt8 *ptr, *rowPtr;
    Int32 bufSize = Buffer_getSize(hBuf);
    ColorSpace_Type colorSpace = BufferGfx_getColorSpace(hBuf);

    BufferGfx_getDimensions(hBuf, &dim);

    FT_Set_Char_Size(face,
                     fontHeight << 6,
                     fontHeight << 6,
                     100,
                     100);

    Convert_init();

    if (colorSpace == ColorSpace_2BIT) {
        cMode = Convert_Mode_RGB888_2BIT;
        start = 65;
        inc = 80;
    }
    else if (colorSpace == ColorSpace_YUV422PSEMI) {
        cMode = Convert_Mode_RGB888_YUV422SEMI;
        start = 80;
        inc = 80;
    }
    else if (colorSpace == ColorSpace_RGB565) {
        cMode = Convert_Mode_RGB888_RGB565;
        start = 0;
        inc = 0;
    }
    else {
        SW_ERR("Text_show() not supporting image color format\n");
        return SW_EFAIL;
    }

    pen.x = x << 6;
    pen.y = (dim.height - y + start) << 6;

    while (*txt) {
        FT_Set_Transform(face, NULL, &pen);

        index = FT_Get_Char_Index(face, *txt);

        error = FT_Load_Glyph(face, index, 0);
        if (error) {
            SW_ERR("Failed to load glyph for character %c\n", *txt);
            break;
        }

        if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) {
            error = FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL);
            if (error) {
                SW_ERR("Failed to render glyph for character %c\n", *txt);
                break;
            }
        }

        width = face->glyph->bitmap.width;
        height = face->glyph->bitmap.rows;

        x = face->glyph->bitmap_left;
        y = dim.height + inc - face->glyph->bitmap_top;

        x_max = x + width;
        y_max = y + height;


        src = face->glyph->bitmap.buffer;

        ptr = (UInt8 *) Buffer_getUserPtr(hBuf) + y * dim.lineLength;
        for (j = y, q = 0; j < y_max; j++, q++) {
            rowPtr = ptr + Screen_getInc(colorSpace, x);
            for (i = x, p = 0; i < x_max; i++, p++) {

                if (i >= dim.width || j >= dim.height)
                    continue;

                sp = q * width + p;

                srcValue = src[sp] << 16 | src[sp] << 8 | src[sp];
                dstValue = Convert_execute(cMode, srcValue, i & 1);
                Screen_setPixelPtr(rowPtr, bufSize, i, dstValue,
                                   FALSE, colorSpace);

                rowPtr += Screen_getStep(colorSpace, i);
            }
            ptr += dim.lineLength;
        }

        txt++;

        pen.x += face->glyph->advance.x;
        pen.y += face->glyph->advance.y;

    }

    return SW_EOK;
}
Int Text_show_col(Font_Handle hFont, Char *txt, Int fontHeight, Int x, Int y,
              Buffer_Handle hBuf, UInt32 colorVal, UInt32 bgColorVal, UInt8 blendVal)
{
    BufferGfx_Dimensions dim;
    FT_Error error;
    Int index;
    Int width, height;
    Int i, j, p, q, x_max, y_max, sp;
    UInt32 srcValue, dstValue;
    UInt8 *src;
    FT_Vector pen;
    FT_Face face = (FT_Face) hFont->face;
    Convert_Mode cMode;
    Int inc, start;
    UInt8 *ptr, *rowPtr;
    Int32 bufSize = Buffer_getSize(hBuf);
    ColorSpace_Type colorSpace = BufferGfx_getColorSpace(hBuf);

    BufferGfx_getDimensions(hBuf, &dim);

    FT_Set_Char_Size(face,
                     fontHeight << 6,
                     fontHeight << 6,
                     100,
                     100);

    Convert_init();

    if (colorSpace == ColorSpace_2BIT) {
        cMode = Convert_Mode_RGB888_2BIT;
        start = 65;
        inc = 80;
    }
    else if (colorSpace == ColorSpace_YUV422PSEMI) {
        cMode = Convert_Mode_RGB888_YUV422SEMI;
        start = 80;
        inc = 80;
    }
    else if (colorSpace == ColorSpace_RGB565) {
        cMode = Convert_Mode_RGB888_RGB565;
        start = 0;
        inc = 0;
    }
    else {
        SW_ERR("Text_show() not supporting image color format\n");
        return SW_EFAIL;
    }

    pen.x = x << 6;
    pen.y = (dim.height - y + start) << 6;

    srcValue=0;
    while (*txt) {
        FT_Set_Transform(face, NULL, &pen);

        index = FT_Get_Char_Index(face, *txt);

        error = FT_Load_Glyph(face, index, 0);
        if (error) {
            SW_ERR("Failed to load glyph for character %c\n", *txt);
            break;
        }

        if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) {
            error = FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL);
            if (error) {
                SW_ERR("Failed to render glyph for character %c\n", *txt);
                break;
            }
        }

        width = face->glyph->bitmap.width;
        height = face->glyph->bitmap.rows;

        x = face->glyph->bitmap_left;
        y = dim.height + inc - face->glyph->bitmap_top;

        x_max = x + width;
        y_max = y + height;

        src = face->glyph->bitmap.buffer;

        ptr = (UInt8 *) Buffer_getUserPtr(hBuf) + y * dim.lineLength;
        for (j = y, q = 0; j < y_max; j++, q++) {
            rowPtr = ptr + Screen_getInc(colorSpace, x);
            for (i = x, p = 0; i < x_max; i++, p++) {

                if (i >= dim.width || j >= dim.height)
                    continue;

                sp = q * width + p;

                if(src[sp])
                	srcValue=colorVal;
                else
                	srcValue=bgColorVal;

                dstValue = Convert_execute(cMode, srcValue, i & 1);

                if(blendVal==0)
                	dstValue=0;

                Screen_setPixelPtr(rowPtr, bufSize, i, dstValue,
                                   FALSE, colorSpace);

                rowPtr += Screen_getStep(colorSpace, i);
            }
            ptr += dim.lineLength;
        }

        txt++;

        pen.x += face->glyph->advance.x;
        pen.y += face->glyph->advance.y;

    }

    return SW_EOK;
}

//Only Capture
Int Text_show_key(Font_Handle hFont, Char *txt, Int fontHeight, Int x, Int y,
              Buffer_Handle hBuf,UInt32 colorVal,  UInt8 blendVal)
{
    BufferGfx_Dimensions dim;
    FT_Error error;
    Int index;
    Int width, height;
    Int i, j, p, q, x_max, y_max, sp;
    UInt32 srcValue, dstValue;
    UInt8 *src;
    FT_Vector pen;
    FT_Face face = (FT_Face) hFont->face;
    Convert_Mode cMode;
    Int inc, start;
    UInt8 *ptr, *rowPtr;
    Int32 bufSize = Buffer_getSize(hBuf);
    ColorSpace_Type colorSpace = BufferGfx_getColorSpace(hBuf);

    BufferGfx_getDimensions(hBuf, &dim);

    FT_Set_Char_Size(face,
                     fontHeight << 6,
                     fontHeight << 6,
                     100,
                     100);

    Convert_init();

    if (colorSpace == ColorSpace_2BIT) {
        cMode = Convert_Mode_RGB888_2BIT;
        start = 65;
        inc = 80;
    }
    else if (colorSpace == ColorSpace_YUV422PSEMI) {
        cMode = Convert_Mode_RGB888_YUV422SEMI;
        start = 80;
        inc = 80;
    }
    else if (colorSpace == ColorSpace_RGB565) {
        cMode = Convert_Mode_RGB888_RGB565;
        start = 0;
        inc = 0;
    }
    else {
        SW_ERR("Text_show() not supporting image color format\n");
        return SW_EFAIL;
    }

    pen.x = x << 6;
    pen.y = (dim.height - y + start) << 6;

    while (*txt) {
        FT_Set_Transform(face, NULL, &pen);

        index = FT_Get_Char_Index(face, *txt);

        error = FT_Load_Glyph(face, index, 0);
        if (error) {
            SW_ERR("Failed to load glyph for character %c\n", *txt);
            break;
        }

        if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) {
            error = FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL);
            if (error) {
                SW_ERR("Failed to render glyph for character %c\n", *txt);
                break;
            }
        }

        width = face->glyph->bitmap.width;
        height = face->glyph->bitmap.rows;

        x = face->glyph->bitmap_left;
        y = dim.height + inc - face->glyph->bitmap_top;

        x_max = x + width;
        y_max = y + height;

        src = face->glyph->bitmap.buffer;

        ptr = (UInt8 *) Buffer_getUserPtr(hBuf) + y * dim.lineLength;

    	printf("changes 3\n");

        for (j = y, q = 0; j < y_max; j++, q++) {
            rowPtr = ptr + Screen_getInc(colorSpace, x);
            for (i = x, p = 0; i < x_max; i++, p++) {

                if (i >= dim.width || j >= dim.height)
                    continue;

                sp = q * width + p;

                if(src[sp])
                {
                	srcValue = colorVal;
                	dstValue = Convert_execute(cMode, srcValue, i & 1);
                	if(blendVal==0)
                		dstValue = 0;//transparent color = black

                	Screen_setPixelPtr(rowPtr, bufSize, i, dstValue,
                			FALSE, colorSpace);//======>FALSE
                }
                else
                {
                	Screen_setPixelPtr(rowPtr, bufSize, i, 0 ,
                			FALSE, colorSpace);//======>FALSE
                }

                rowPtr += Screen_getStep(colorSpace, i);
            }
            ptr += dim.lineLength;
        }

        txt++;

        pen.x += face->glyph->advance.x;
        pen.y += face->glyph->advance.y;

    }

    return SW_EOK;
}

Int Text_stringSize(Font_Handle hFont, Char *txt, Int fontHeight,
                    Int *stringWidth, Int *stringHeight)
{
    Int index;
    Int width = 0;
    Int height = 0;
    FT_Vector pen;
    FT_Face face = (FT_Face) hFont->face;

    FT_Set_Char_Size(face,
                     fontHeight << 6,
                     fontHeight << 6,
                     100,
                     100);

    pen.x = 0;
    pen.y = 0;

    while (*txt) {
        FT_Set_Transform(face, NULL, &pen);

        index = FT_Get_Char_Index(face, *txt);

        if (FT_Load_Glyph(face, index, 0)) {
            SW_ERR("Failed to load glyph for character %c\n", *txt);
            break;
        }

        if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) {
            if (FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL)) {
                SW_ERR("Failed to render glyph for character %c\n", *txt);
                break;
            }
        }

        width += face->glyph->bitmap.width + 1;
        if (face->glyph->bitmap.rows > height) {
            height = face->glyph->bitmap.rows;
        }

        pen.x += face->glyph->advance.x;
        pen.y += face->glyph->advance.y;
        txt++;
    }

    *stringWidth = width;
    *stringHeight = height;

    return SW_EOK;
}

  • Here is Text_show_blend() function implemented in text.c in SimpleWidget library :

    Int Text_show_blend(Font_Handle hFont, Char *txt, Int fontHeight, Int x, Int y,
                  Buffer_Handle hBuf, UInt8 keyEnable, UInt8 blendVal)
    {
        BufferGfx_Dimensions dim;
        FT_Error error;
        Int index;
        Int width, height;
        Int i, j, p, q, x_max, y_max, sp;
        UInt8 *src;
        FT_Vector pen;
        FT_Face face = (FT_Face) hFont->face;
        UInt8 *ptr, *rowPtr;
        UInt8 blendCnt,blend0;
        Int x2;
    
        BufferGfx_getDimensions(hBuf, &dim);
    
        FT_Set_Char_Size(face,
                         fontHeight << 6,
                         fontHeight << 6,
                         100,
                         100);
    
        pen.x = x << 6;
        pen.y = (dim.height - y) << 6;
    
        blend0=blendVal&0xf;
        while (*txt) {
        	FT_Set_Transform(face, NULL, &pen);
    
        	index = FT_Get_Char_Index(face, *txt);
    
        	error = FT_Load_Glyph(face, index, 0);
        	if (error) {
        		SW_ERR("Failed to load glyph for character %c\n", *txt);
        		break;
        	}
    
        	if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) {
        		error = FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL);
        		if (error) {
        			SW_ERR("Failed to render glyph for character %c\n", *txt);
        			break;
        		}
        	}
    
        	width = face->glyph->bitmap.width;
        	height = face->glyph->bitmap.rows;
    
        	x = face->glyph->bitmap_left;
        	y = dim.height - face->glyph->bitmap_top;
        	x2=x>>1;
    
        	x_max = x + width;
        	y_max = y + height;
    
        	src = face->glyph->bitmap.buffer;
    
        	ptr = (UInt8 *) Buffer_getUserPtr(hBuf) + y * dim.lineLength;
    
        	for (j = y, q = 0; j < y_max; j++, q++) {
        		blendCnt=(x&0x1)<<2;
        		rowPtr = ptr + x2;
        		for (i = x, p = 0; i < x_max; i++, p++) {
    
        			if (i >= dim.width || j >= dim.height)
        				continue;
    
        			sp = q * width + p;
    
        			if(keyEnable&&src[sp])
        			{
        				if(blend0)
        					*rowPtr|=(blend0<<blendCnt);
        				else
        					*rowPtr&=(0xf0>>blendCnt);
        			}
        			else if(!keyEnable)
        			{
        				if(blend0)
        					*rowPtr|=(blend0<<blendCnt);
        				else
        					*rowPtr&=(0xf0>>blendCnt);
        			}
    
        			blendCnt+=4;
        			if(blendCnt==8)
        			{
        				blendCnt=0;
        				rowPtr++;
        			}
        		}
        		ptr += dim.lineLength;
        	}
    
        	txt++;
    
        	pen.x += face->glyph->advance.x;
        	pen.y += face->glyph->advance.y;
    
        }
    
        return SW_EOK;
    }

    And here is Text_show_key() function :


    Int Text_show_key(Font_Handle hFont, Char *txt, Int fontHeight, Int x, Int y, Buffer_Handle hBuf,UInt32 colorVal, UInt8 blendVal) { BufferGfx_Dimensions dim; FT_Error error; Int index; Int width, height; Int i, j, p, q, x_max, y_max, sp; UInt32 srcValue, dstValue; UInt8 *src; FT_Vector pen; FT_Face face = (FT_Face) hFont->face; Convert_Mode cMode; Int inc, start; UInt8 *ptr, *rowPtr; Int32 bufSize = Buffer_getSize(hBuf); ColorSpace_Type colorSpace = BufferGfx_getColorSpace(hBuf); BufferGfx_getDimensions(hBuf, &dim); FT_Set_Char_Size(face, fontHeight << 6, fontHeight << 6, 100, 100); Convert_init(); if (colorSpace == ColorSpace_2BIT) { cMode = Convert_Mode_RGB888_2BIT; start = 65; inc = 80; } else if (colorSpace == ColorSpace_YUV422PSEMI) { cMode = Convert_Mode_RGB888_YUV422SEMI; start = 80; inc = 80; } else if (colorSpace == ColorSpace_RGB565) { cMode = Convert_Mode_RGB888_RGB565; start = 0; inc = 0; } else { SW_ERR("Text_show() not supporting image color format\n"); return SW_EFAIL; } pen.x = x << 6; pen.y = (dim.height - y + start) << 6; while (*txt) { FT_Set_Transform(face, NULL, &pen); index = FT_Get_Char_Index(face, *txt); error = FT_Load_Glyph(face, index, 0); if (error) { SW_ERR("Failed to load glyph for character %c\n", *txt); break; } if (face->glyph->format != FT_GLYPH_FORMAT_BITMAP) { error = FT_Render_Glyph(face->glyph, FT_RENDER_MODE_NORMAL); if (error) { SW_ERR("Failed to render glyph for character %c\n", *txt); break; } } width = face->glyph->bitmap.width; height = face->glyph->bitmap.rows; x = face->glyph->bitmap_left; y = dim.height + inc - face->glyph->bitmap_top; x_max = x + width; y_max = y + height; src = face->glyph->bitmap.buffer; ptr = (UInt8 *) Buffer_getUserPtr(hBuf) + y * dim.lineLength; for (j = y, q = 0; j < y_max; j++, q++) { rowPtr = ptr + Screen_getInc(colorSpace, x); for (i = x, p = 0; i < x_max; i++, p++) { if (i >= dim.width || j >= dim.height) continue; sp = q * width + p; if(src[sp]) { srcValue = colorVal; dstValue = Convert_execute(cMode, srcValue, i & 1); if(blendVal==0) dstValue = 0;//transparent color = black Screen_setPixelPtr(rowPtr, bufSize, i, dstValue, FALSE, colorSpace);//======>FALSE } rowPtr += Screen_getStep(colorSpace, i); } ptr += dim.lineLength; } txt++; pen.x += face->glyph->advance.x; pen.y += face->glyph->advance.y; } return SW_EOK; }

    So according to the first post how should I change these two functions to get what I wanted? (which by the way was clearing the screen before writing anything on it)