///////////////////////////////////////////////////////////////////////////////
//                                                         
// CegoProcObject.cc 
// ------------------
// Cego procedure object implementation
//     
// Design and Implementation by Bjoern Lemke               
//     
// (C)opyright 2000-2010 Bjoern Lemke
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2, or (at your option)
// any later version.
// 
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; see the file COPYING.  If not, write to
// the Free Software Foundation, 59 Temple Place - Suite 330,
// Boston, MA 02111-1307, USA.
//
// IMPLEMENTATION MODULE
//
// Class: CegoProcObject
// 
// Description: 
//
// Status: QG-2.6
//
///////////////////////////////////////////////////////////////////////////////

// base includes
#include <lfc/Tokenizer.h>

// cego includes
#include "CegoProcObject.h"
#include "CegoXMLdef.h"

#include <string.h>
#include <stdlib.h>

CegoProcObject::CegoProcObject()
{
}

CegoProcObject::CegoProcObject(const CegoProcObject& po)  : CegoDecodableObject(po)
{
    _procText = po._procText;
}

CegoProcObject::CegoProcObject(const Chain& procName, int tabSetId) : CegoDecodableObject(CegoObject::PROCEDURE, procName, tabSetId)
{
}

CegoProcObject::CegoProcObject(int tabSetId, const Chain& procName, const Chain& procText) : CegoDecodableObject(CegoObject::PROCEDURE, procName, tabSetId)
{
    _procText = procText;
}

CegoProcObject::~CegoProcObject()
{   
}

int CegoProcObject::getEntrySize() const
{
    int entrySize = CegoObject::getBaseSize();
    entrySize += _procText.length() + 1;
    return entrySize;
}

void CegoProcObject::encode(char *buf)
{
    char* bufPtr = buf;
    int entrySize = getEntrySize();
    CegoObject::encodeBase(bufPtr, entrySize);
    bufPtr += CegoObject::getBaseSize();
    memcpy (bufPtr, (char*)_procText , _procText.length() + 1);
}

void CegoProcObject::decode(char *buf)
{
    char* bufPtr = buf;
    int size;
    CegoObject::decodeBase(bufPtr, size);
    bufPtr += CegoObject::getBaseSize();
    _procText = Chain(bufPtr);
}

CegoProcObject& CegoProcObject::operator = ( const CegoProcObject& po)
{
    CegoObject::operator=(po);

    _procText = po._procText;
    return (*this);
}

bool CegoProcObject::operator == ( const CegoProcObject& po)
{
    return CegoObject::operator==(po);
}


const Chain& CegoProcObject::getProcText() const
{
    return _procText;
}



Chain CegoProcObject::toChain() const
{
    Chain s;
    
    s = CegoObject::toChain();
    s += Chain("Proc Text: ") + _procText + Chain("\n");
    s += Chain("EntrySize = ") + Chain(getEntrySize()) + Chain("\n");
    return s;
}

Element* CegoProcObject::getElement() const
{
    Element* pRoot = new Element(XML_OBJ_ELEMENT);

    pRoot->setAttribute(XML_TSID_ATTR, Chain(getTabSetId()));
    pRoot->setAttribute(XML_OBJTYPE_ATTR, XML_PROCOBJ_VALUE);	
    pRoot->setAttribute(XML_OBJNAME_ATTR, getName());
    pRoot->setAttribute(XML_PROCTEXT_ATTR, _procText);

    return pRoot;
}

void CegoProcObject::putElement(Element* pElement)
{
    Element *pRoot = pElement;
    
    if ( pRoot )
    {
	int tabSetId = pRoot->getAttributeValue(XML_TSID_ATTR).asInteger();
	setTabSetId(tabSetId);
	Chain objName = pRoot->getAttributeValue(XML_OBJNAME_ATTR);
	setName(objName);
	setType(CegoObject::PROCEDURE);
	_procText = pRoot->getAttributeValue(XML_PROCTEXT_ATTR);
    }
}

Chain CegoProcObject::getFormatted() const
{


    Chain s;
    int maxFillLen = 80;

    Chain line;

    Tokenizer ppt(_procText, "\n");	
    while ( ppt.nextToken(line) )
    {
	if ( line.length() > maxFillLen )
	    maxFillLen = line.length();
    }
    
    s += "+" + fill("-", maxFillLen) + "+\n";
    s += "| ObjectName : "+ getName() + fill(" ", maxFillLen - getName().length()-13) + "|\n";
    s += "| ObjectType : procedure" + fill(" ", maxFillLen-23) + "|\n";
    s += "+-----------------------" + fill("-", maxFillLen-23) +  "+\n";
    s += "| Procedure Text        " +  fill(" ", maxFillLen-23) + "|\n";
    s += "+" + fill("-", maxFillLen) + "+\n";
	

    Tokenizer pt(_procText, "\n");
    
    while ( pt.nextToken(line) )
    {
	s += "| " + line + fill(" ", maxFillLen-line.length()) + "|\n";
    }
    s +="+" + fill("-", maxFillLen) + "+\n";

    return s;

}

Chain CegoProcObject::fill(const Chain& s, int num) const
{
    
    Chain fs = Chain("");
    while (num > 0)
    {
	fs = fs + s;
	num--;
    }

    return fs;
}
