THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 20/07/2012 at 09:05, xxxxxxxx wrote:
User Information:
Cinema 4D Version: 12
Platform: Windows ;
Language(s) : C++ ;
---------
I found a few posts where people said they figured out how to draw text. But they did not post enough of the code for me to build my own working example.
I did find an older R11.5 version posted by Matthias that sort of works. But it has problems.
It inverts the front facing polygons of the object the tag is on. And makes them invisible.
Plus the text is always behind the object.
I'm posting the complete version that Matthias posted long ago(I hope that's ok?) in the hopes that someone out there knows why it's doing these unwanted things. Or has a better working version that they will be kind enough to post here.
#include "c4d.h"
#include "c4d_symbols.h"
#include "tsimpletag.h"
#include "customgui_priority.h" //needed for the priority stuff to work
#include "..\..\..\..\resource\_api\c4d_libs\lib_clipmap.h"
#define PLUGIN_ID 1000007 // be sure to use a unique ID obtained from www.plugincafe.com
class SimpleTag : public TagData
{
INSTANCEOF(SimpleTag,TagData)
public:
virtual Bool Message(GeListNode *node, LONG type, void *t_data);
virtual Bool Init(GeListNode *node);
virtual Bool GetDDescription(GeListNode *node, Description *description,DESCFLAGS_DESC &flags);
virtual Bool GetDParameter(GeListNode *node, const DescID &id,GeData &t_data,DESCFLAGS_GET &flags);
virtual Bool SetDParameter(GeListNode *node, const DescID &id,const GeData &t_data,DESCFLAGS_SET &flags);
virtual Bool Draw(BaseTag* tag, BaseObject* op, BaseDraw* bd, BaseDrawHelp* bh);
virtual EXECUTIONRESULT Execute(BaseTag *tag, BaseDocument *doc, BaseObject *op, BaseThread *bt, LONG priority, EXECUTIONFLAGS flags);
static NodeData *Alloc(void) { return gNew SimpleTag; }
};
Bool SimpleTag::GetDParameter(GeListNode *node, const DescID &id, GeData &t_data, DESCFLAGS_GET &flags) //Used to get the decriptions data
{
return SUPER::GetDParameter(node, id, t_data, flags);
}
Bool SimpleTag::SetDParameter(GeListNode *node, const DescID &id, const GeData &t_data, DESCFLAGS_SET &flags) //Used to change the decriptions data
{
return SUPER::SetDParameter(node, id, t_data, flags);
}
Bool SimpleTag::GetDDescription(GeListNode *node, Description *description,DESCFLAGS_DESC &flags)
{
//flags |= DESCFLAGS_DESC_LOADED;
return TRUE;
}
Bool SimpleTag::Message(GeListNode *node, LONG type, void *data)
{
BaseTag *tag = (BaseTag* )node; //Get the tag and assign it to a variable
//Do something
tag->SetDirty(DIRTYFLAGS_DATA); //Used to update a Tag's AM GUI items
return TRUE;
}
Bool SimpleTag::Init(GeListNode *node)
{ // intitial values for the tag when it's created are set in this section
BaseTag *tag = (BaseTag* )node; //Assigns a variable to the tag's node
BaseContainer *data = tag->GetDataInstance(); //Assigns a variable to that node's container
data->SetBool(MYBOX,FALSE); //Sets the checkbox to disabled by default when tag is created-->looks in the description->tbasictag.h file for matching name
return TRUE;
}
static Bool DrawText(String text, LONG xpos, LONG ypos, BaseDraw *bd) //Custom method to draw some text(static methods don't get declared in the class)
{
AutoAlloc<GeClipMap> cm;
if(!cm) return FALSE;
cm->Init(0, 0, 32);
cm->BeginDraw();
LONG width = cm->TextWidth(text); //Sets the width value based on the length of the string being held in this variable
LONG height = cm->TextHeight(); //Automatically calculates the maximum height of a string in the current font
cm->EndDraw();
cm->Destroy(); //Resets the clip map to its initial state and frees allocated memory.
//Requires a new call to Init*() before the clip map can be used again.
cm->Init(width, height, 32); //Re-init the clipmap because it was previously destroyed
GePrint(LongToString(width) + " " + LongToString(height));
cm->BeginDraw(); //Start editing the clipmap
cm->SetColor(255, 255, 255, 255); //Sets the color of the text to white
cm->TextAt(0,0,text);
cm->EndDraw();
bd->SetMatrix_Screen(); //Sets the transformation matrix to screen coordinates, i.e. from (0, 0) to (width, height)
bd->SetLightList(BDRAW_SETLIGHTLIST_NOLIGHTS); //Sets the lighting used by the draw functions
Vector *padr = bNew Vector[4];
Vector *cadr = bNew Vector[4];
Vector *vnadr = bNew Vector[4]; //Create vectors with four values
Vector *uvadr = bNew Vector[4];
padr[0] = Vector(xpos,ypos,0);
padr[1] = Vector(xpos+width,ypos,0);
padr[2] = Vector(xpos+width,ypos+height,0);
padr[3] = Vector(xpos,ypos+height,0);
cadr[0] = Vector(1,1,1);
cadr[1] = Vector(1,1,1);
cadr[2] = Vector(1,1,1);
cadr[3] = Vector(1,1,1);
vnadr[0] = Vector(0,0,1);
vnadr[1] = Vector(0,0,1);
vnadr[2] = Vector(0,0,1);
vnadr[3] = Vector(0,0,1);
uvadr[0] = Vector(0,0,0);
uvadr[1] = Vector(1,0,0);
uvadr[2] = Vector(1,1,0);
uvadr[3] = Vector(0,1,0);
BaseBitmap *cmbmp = cm->GetBitmap(); //Create a BaseBitmap instance to use in the DrawTexture function
if(!cmbmp) return FALSE;
BaseBitmap *bmp = cmbmp->GetClone(); //Create a clone of the above bitmap instance
if(!bmp) return FALSE;
BaseBitmap *alpha = bmp->GetInternalChannel(); //Create a third Bitmap instance to hold the alpha data
alpha = bmp->AddChannel(TRUE, FALSE);
if(!alpha)
{
BaseBitmap::Free(bmp); //Error handling: frees memory of the alpha bitmap instance if there was an error creating it
return FALSE;
}
LONG x,y;
for(y=0; y<height; y++)
{
for(x=0; x<width; x++)
{
UWORD r;
bmp->GetPixel(x,y,&r,&r,&r);
bmp->SetAlphaPixel(alpha, x, y, r); //r is the opacity
}
}
bd->DrawTexture(bmp,padr,cadr,vnadr,uvadr,4,DRAW_ALPHA_NORMAL,DRAW_TEXTUREFLAGS_0);
BaseBitmap::Free(bmp); //Free the memory being used by this bitmap instance
bDelete(padr);
bDelete(cadr);
bDelete(vnadr); //Free the memory being used by these pointers
bDelete(uvadr);
return TRUE;
}
Bool SimpleTag::Draw(BaseTag *tag, BaseObject *op, BaseDraw *bd, BaseDrawHelp *bh)
{
if(tag->GetData().GetBool(MYBOX)) //If the 'MYBOX' checkbox attribute is enabled
{
DrawText("Hello World", 256, 256, bd); //Draw text on the screen at x,y position 256,256
}
return TRUE;
}
EXECUTIONRESULT SimpleTag::Execute(BaseTag *tag, BaseDocument *doc, BaseObject *op, BaseThread *bt, LONG priority, EXECUTIONFLAGS flags)
{
return EXECUTIONRESULT_OK;
}
Bool RegisterSimpleTag(void)
{
String path=GeLoadString(IDS_SIMPLETAG); if (!path.Content()) return TRUE; // points to the res->c4d_symbols file which conatins the enum "IDS_SIMPLETAG" entry
return RegisterTagPlugin(PLUGIN_ID,path,TAG_EXPRESSION|TAG_VISIBLE,SimpleTag::Alloc,"tsimpletag",AutoBitmap("myicon.tif"),0);
}
If you know why this example doesn't work properly(clipping the object faces). Or if have a working version of drawing text that works better than this. Please post it.
It would very helpful.
Thanks,
-ScottA