Patch level : 2.1 nopatch

Files correlati     : librerie
Ricompilazione Demo : [ ]
Commento            :

Aggiunti metodi vari per nuovi reports


git-svn-id: svn://10.65.10.50/trunk@12092 c028cbd2-c16b-5b4b-a496-9718f37d4682
This commit is contained in:
guy 2004-05-18 13:47:49 +00:00
parent 26cff3b057
commit 3ca976630a
16 changed files with 518 additions and 196 deletions

View File

@ -1,7 +1,6 @@
#include <ctype.h>
#include <stdlib.h>
#include <alex.h>
#include <automask.h>
#include <colors.h>
#include <dongle.h>
@ -275,7 +274,12 @@ void TAVM_list_window::update()
if (var.is_string() && var.as_string()[0] != '#')
str.cut(0) << '"' << var.as_string() << '"';
else
str = var.as_string();
{
if (var.is_null())
str = "NULL";
else
str = var.as_string();
}
} else
if (co == avm_call_word)
{
@ -332,7 +336,13 @@ void TAVM_stack_window::update()
if (_stack != NULL)
{
for (int i = 0; i < _stack->items(); i++)
printat(0, i, _stack->peek(i).as_string());
{
const TVariant& var = _stack->peek(i);
if (var.is_null())
printat(0, i, "NULL");
else
printat(0, i, var.as_string());
}
}
}
@ -421,7 +431,7 @@ TMask_field* TAVM_monitor::parse_field(TScanner& scanner)
TAVM_monitor::TAVM_monitor()
{
read_mask("ba8304", 0, -1);
read_mask("ba8300m", 0, -1);
set_handlers();
}
@ -461,10 +471,10 @@ public:
const TString& get_last_error() const { return _last_error; }
bool compile(istream& instr, TBytecode& bc);
bool execute(const TBytecode& bc, ostream* outstr = NULL);
bool execute(const TBytecode& bc);
void do_restart(bool cold);
bool do_include(const char* fname);
TVariant& do_fetch(const TString& name);
void do_fetch(const TString& name);
void do_add();
void do_store(const TString& name);
void set_interactive(bool inter) { _interactive = inter; }
@ -758,7 +768,7 @@ bool TAVM::do_include(const char* fname)
}
// Mette sullo stack il valore della variabile name
TVariant& TAVM::do_fetch(const TString& name)
void TAVM::do_fetch(const TString& name)
{
if (name[0] == '#')
{
@ -774,7 +784,6 @@ TVariant& TAVM::do_fetch(const TString& name)
else
_stack.push(NULL_VARIANT);
}
return _stack.peek();
}
void TAVM::do_add()
@ -960,7 +969,7 @@ void TAVM::execute(const TAVM_op& op)
break;
case avm_plus_store:
{
const TString& name = _stack.pop().as_string();
const TString name = _stack.pop().as_string();
do_fetch(name);
do_add();
do_store(name);
@ -1033,7 +1042,7 @@ void TAVM::execute(const TAVM_op& op)
}
}
bool TAVM::execute(const TBytecode& cmdline, ostream* outstr)
bool TAVM::execute(const TBytecode& cmdline)
{
const TBytecode* old_bc = _bc;
const int old_ip = _ip;
@ -1043,8 +1052,6 @@ bool TAVM::execute(const TBytecode& cmdline, ostream* outstr)
_bc = &cmdline;
_ip = 0;
if (outstr != NULL)
_outstr = outstr;
while (_bc != NULL)
{
while (_ip >= _bc->items()) // Fine funzione
@ -1169,9 +1176,9 @@ bool TAlex_virtual_machine::compile(istream& instr, TBytecode& bc)
return avm().compile(instr, bc);
}
bool TAlex_virtual_machine::execute(const TBytecode& bc, ostream& outstr)
bool TAlex_virtual_machine::execute(const TBytecode& bc)
{
return avm().execute(bc, &outstr);
return avm().execute(bc);
}
bool TAlex_virtual_machine::compile(const char* cmd, TBytecode& bc)
@ -1180,14 +1187,6 @@ bool TAlex_virtual_machine::compile(const char* cmd, TBytecode& bc)
return compile(instr, bc);
}
bool TAlex_virtual_machine::execute(const TBytecode& bc, TString& outs)
{
char* buf = outs.get_buffer();
memset(buf, 0, outs.size());
ostrstream outstr(buf, outs.size());
return execute(bc, outstr);
}
void TAlex_virtual_machine::warm_restart() // Ripartenza a caldo
{
avm().do_restart(false);
@ -1267,6 +1266,12 @@ bool TAlex_virtual_machine::include(const char* fname)
return avm().do_include(fname);
}
void TAlex_virtual_machine::include_libraries(bool reload)
{
if (reload || !defined("2DUP"))
include("alex.alx");
}
void TAlex_virtual_machine::set_interactive(bool inter)
{ avm().set_interactive(inter); }

View File

@ -31,11 +31,14 @@ public:
class TBytecode : public TArray
{
TString _name;
TString _name, _lib;
public:
void set_name(const char* name) { _name = name; }
const TString& name() const { return _name; }
void set_library(const char* lib) { _lib = lib; }
const TString& library() const { return _lib; }
};
// ALEX = Another Language EXtension
@ -54,13 +57,14 @@ public:
virtual bool execute_usr_word(unsigned int opcode, TVariant_stack& stack);
virtual bool get_usr_val(const TString& name, TVariant& var) const;
virtual bool set_usr_val(const TString& name, const TVariant& var);
virtual void include_libraries(bool reload = false);
const TString& get_last_error() const;
bool compile(istream& instr, TBytecode& bc);
bool compile(const char* cmd, TBytecode& bc);
bool execute(const TBytecode& bc, ostream& outstr);
bool execute(const TBytecode& bc, TString& outstr);
bool execute(const TBytecode& bc);
bool include(const char* fname);
void warm_restart();
void cold_restart();
void set_interactive(bool inter);

View File

@ -177,26 +177,7 @@ bool TArray::destroy(
return _items < old;
}
TArray::TArray(int arraysize)
: _data(NULL), _size(0), _items(0), _next(0)
{
if (arraysize)
resize(arraysize);
}
TArray::TArray()
: _data(NULL), _size(0), _items(0), _next(0)
{
}
TArray::TArray(const TArray& a)
: _data(NULL), _size(0), _items(0), _next(0)
{
(*this) = a;
}
TArray& TArray::operator= (const TArray& a)
void TArray::copy(const TArray& a)
{
destroy();
if (size() < a.size())
@ -217,7 +198,29 @@ TArray& TArray::operator= (const TArray& a)
}
_items = ( int )a.items();
_next = ( int )a._next;
}
TArray::TArray(int arraysize)
: _data(NULL), _size(0), _items(0), _next(0)
{
if (arraysize)
resize(arraysize);
}
TArray::TArray()
: _data(NULL), _size(0), _items(0), _next(0)
{
}
TArray::TArray(const TArray& a)
: _data(NULL), _size(0), _items(0), _next(0)
{
copy(a);
}
TArray& TArray::operator= (const TArray& a)
{
copy(a);
return *this;
}

View File

@ -112,6 +112,7 @@ protected:
// @cmember Modifica la dimensione dell'array.
void resize(int newdim);
void copy(const TArray& a);
// @access Public Member
public:
@ -143,7 +144,6 @@ public:
// @cmember Ritorna numero di oggetti nell'array
virtual int items( ) const
{ return _items; }
// @cmember Ritorna il primo elemento dell'array
virtual TObject* first_item( );
@ -168,7 +168,7 @@ public:
// @cmember Ritorna l'oggetto nella posizione index
TObject* objptr(int index) const ;
// @cmember Assegna all'array l'oggetto passato
TArray& operator= (const TArray& a);
TArray& operator=(const TArray& a);
// @cmember Rimuove uno o tutti (default) gli elementi
virtual bool destroy(int index = -1, bool pack = FALSE);

View File

@ -422,7 +422,7 @@ void TExpression::eval()
case _not:
{
real & r1 = evalstack.peek_real();
r1 = (r1 == ZERO) ? 1.0 : 0.0;
r1 = (r1 == ZERO) ? UNO : ZERO;
}
break;
case _equal:

View File

@ -781,6 +781,24 @@ const TRectype& TDB_cache::get(const char* table, const char* key)
return get(file, tabkey);
}
const TRectype& TDB_cache::get(const TRectype& curr)
{
const int num = curr.num();
if (num == LF_TAB || num == LF_TABCOM)
return get(curr.get("COD"), curr.get("CODTAB"));
const RecDes& recd = *curr.rec_des(); // Descrizione del record della testata
const KeyDes& kd = recd.Ky[0]; // Elenco dei campi della chiave
TToken_string key;
for (int i = 0; i < kd.NkFields; i++) // Riempie la chiave selezionata
{
const int nf = kd.FieldSeq[i] % MaxFields;
const RecFieldDes& rf = recd.Fd[nf];
key.add(curr.get(rf.Name));
}
return get(num, key);
}
bool TDB_cache::discard(int file, const char* key)
{
return rec_cache(file).discard(key);

View File

@ -228,7 +228,7 @@ public:
const TString& get(const char* chiave, const char* campo);
// @cmember ritorna il record con una determinata chiave numerica
const TRectype& get(long chiave);
const TString& get(long chiave, const char* campo) ;
const TString& get(long chiave, const char* campo);
TRecord_cache(int num, int key = 1);
TRecord_cache(TLocalisamfile *f, int key = 1);
@ -252,6 +252,7 @@ public:
const TRectype& get(int file, long key)
{ return rec_cache(file).get(key); }
const TRectype& get(const char* table, const char* key);
const TRectype& get(const TRectype& key);
const TString& get(int file, const char* key, const char * campo)
{ return get(file, key).get(campo); }

View File

@ -104,9 +104,9 @@ TDate TVariant::as_date() const
{
if (_type == _datefld)
return *(TDate*)_ptr;
const TDate d(as_int());
return d;
if (_type == _intfld || _type == _realfld)
return TDate(as_int());
return TDate(as_string());
}
long TVariant::as_int() const
@ -127,7 +127,7 @@ bool TVariant::as_bool() const
{
bool ok = false;
if (_type == _alfafld)
ok = strchr("XY", as_string()[0]) != NULL;
ok = strchr("1XY", as_string()[0]) != NULL;
else
ok = as_int() != 0;
return ok;
@ -323,15 +323,16 @@ int TTable_names::logic_num(const TString& name)
if (name[0] == '%' && name.len() == 4)
return LF_TABCOM;
if (name.len() == 3)
return LF_TAB;
TString* str = (TString*)_names.objptr(name);
if (str == NULL)
{
fill();
str = (TString*)_names.objptr(name);
}
if (str == NULL && name.len() == 3)
return LF_TAB;
return str == NULL ? 0 : atoi(*str);
}
@ -1808,7 +1809,7 @@ const TVariant& TISAM_recordset::get(int logic, const char* fldname) const
name.cut(colon);
}
const TRectype& rec = _relation->curr(logic);
const TRectype& rec = relation()->curr(logic);
const TFieldtypes ft = rec.type(name);
if (ft == _nullfld)
@ -1897,22 +1898,9 @@ const TRecordset_column_info& TISAM_recordset::column_info(size_t i) const
return (const TRecordset_column_info&)_column[i];
}
TRecnotype TISAM_recordset::current_row() const
TCursor* TISAM_recordset::cursor() const
{
return _cursor != NULL ? _cursor->pos() : -1;
}
bool TISAM_recordset::ask_variables(bool all)
{
bool ok = TRecordset::ask_variables(all);
if (ok)
reset();
return ok;
}
TRecnotype TISAM_recordset::items() const
{
if (_cursor == NULL)
if (_cursor == NULL && !_use.blank())
{
TString use; parsed_text(use);
TPerformance_profiler prof("ISAM query");
@ -1929,24 +1917,49 @@ TRecnotype TISAM_recordset::items() const
_cursor->freeze();
}
}
return _cursor;
}
return _cursor != NULL ? _cursor->items() : 0;
TRelation* TISAM_recordset::relation() const
{
cursor();
return _relation;
}
TRecnotype TISAM_recordset::current_row() const
{
TCursor* c = cursor();
return c != NULL ? c->pos() : -1;
}
bool TISAM_recordset::ask_variables(bool all)
{
bool ok = TRecordset::ask_variables(all);
if (ok)
reset();
return ok;
}
TRecnotype TISAM_recordset::items() const
{
TCursor* c = cursor();
return c != NULL ? c->items() : -1;
}
unsigned int TISAM_recordset::columns() const
{
if (_cursor == NULL)
items();
cursor();
return _column.items();
}
bool TISAM_recordset::move_to(TRecnotype pos)
{
bool ok = _cursor != NULL;
TCursor* c = cursor();
bool ok = c != NULL;
if (ok)
{
*_cursor = pos;
*c = pos;
ok = pos >= 0 && pos < items();
}
return ok;

View File

@ -1,12 +1,8 @@
#ifndef __RECORDSET_H
#define __RECORDSET_H
#ifndef __ASSOC_H
#include <assoc.h>
#endif
#ifndef __RECTYPES_H
#include <rectypes.h>
#ifndef __ISAM_H
#include <isam.h>
#endif
#ifndef __SHEET_H
@ -178,9 +174,12 @@ class TISAM_recordset : public TRecordset
TArray _column; // Column infos
protected:
TCursor* cursor() const;
TRelation* relation() const;
void reset();
TVariant& get_tmp_var() const;
const TVariant& get(int logic, const char* field) const;
virtual const TVariant& get(int logic, const char* field) const;
public:
void set(const char* use);

View File

@ -605,8 +605,7 @@ int TRelation::position_rels(
TString expr(80); // Stringa di lavoro per la valutazione delle espressioni
_errors = NOERR;
const int primo = first < 0 ? 0 : first;
const int ultimo = first < 0 && (-first) < _reldefs.items() ? -first : _reldefs.items();
@ -615,10 +614,12 @@ int TRelation::position_rels(
{
TRelationdef& rd = reldef(i);
if (primo > 0 && rd.link() < primo)
continue; // Inutile spostare file collegati a record precedenti
TLocalisamfile& from = file(rd.num());
TLocalisamfile& to = file(rd.link());
from.zero(); // Azzera il record corrente (tutti se TSortedfile)
if (to.curr().empty())
continue;

View File

@ -1,6 +1,7 @@
#include <colors.h>
#include <expr.h>
#include <image.h>
#include <recarray.h>
#include <relation.h>
#include <report.h>
#include <xml.h>
@ -150,32 +151,7 @@ TReport_font::~TReport_font()
///////////////////////////////////////////////////////////
// TReport_expr
///////////////////////////////////////////////////////////
class TReport_expr : public TExpression
{
TReport& _report;
TVariant _var;
protected:
virtual int parse_user_func(const char* name, int nparms) const;
virtual void evaluate_user_func(int index, int nparms, TEval_stack& stack, TTypeexp type) const;
bool is_numeric(const char* str) const;
public:
TReport_expr(TReport& rep, const char* exp);
const TVariant& as_variant(TFieldtypes ft);
};
int TReport_expr::parse_user_func(const char* name, int nparms) const
{
return -1;
}
void TReport_expr::evaluate_user_func(int index, int nparms, TEval_stack& stack, TTypeexp type) const
{
}
bool TReport_expr::is_numeric(const char* str) const
static bool is_a_number(const char* str)
{
if (str == NULL || *str == '\0' || *str == '0')
return false; // Se comincia per zero va preservato!
@ -194,6 +170,29 @@ bool TReport_expr::is_numeric(const char* str) const
return true;
}
class TReport_expr : public TExpression
{
TReport& _report;
TVariant _var;
protected:
virtual int parse_user_func(const char* name, int nparms) const;
virtual void evaluate_user_func(int index, int nparms, TEval_stack& stack, TTypeexp type) const;
public:
TReport_expr(TReport& rep, const char* exp);
const TVariant& as_variant(TFieldtypes ft);
};
int TReport_expr::parse_user_func(const char* name, int nparms) const
{
return -1;
}
void TReport_expr::evaluate_user_func(int index, int nparms, TEval_stack& stack, TTypeexp type) const
{
}
const TVariant& TReport_expr::as_variant(TFieldtypes ft)
{
set_type(ft == _alfafld || ft == _nullfld ? _strexpr : _numexpr);
@ -251,7 +250,7 @@ TReport_image_cache::TReport_image_cache() : TCache(7)
void advanced_draw_rect(TWindow& win, const RCT& r, int border, COLOR fore, COLOR back)
{
const bool has_pen = border > 0;
const bool has_brush = color_distance(back, COLOR_WHITE) != 0;
const bool has_brush = (back & 0xFFFFFF) != (COLOR_WHITE & 0xFFFFFF);
if (has_pen || has_brush)
{
if (has_pen)
@ -491,7 +490,7 @@ TPoint TReport_section::compute_size() const
for (int i = 0; i < items(); i++)
{
const TReport_field& rf = field(i);
if (rf.shown())
if (rf.active() && rf.shown())
{
const TRectangle r = rf.get_draw_rect();
if (_size.x <= 0 && r.right() > s.x) // Richiesto calcolo larghezza
@ -528,7 +527,7 @@ void TReport_section::draw(TWindow& win, TReport_draw_mode rdm) const
bool TReport_section::load_fields()
{
const bool ok = active() || shown();
const bool ok = active();
if (ok)
{
for (int i = 0; i < items(); i++)
@ -545,12 +544,11 @@ bool TReport_section::execute_prescript()
bool ok = true;
if (active())
{
TString80 str;
if (items() > 0)
report().set_curr_field(&field(0));
else
report().set_curr_field(NULL);
ok = _prescript.execute(report(), str);
ok = _prescript.execute(report());
}
for (int i = 0; i < items(); i++)
{
@ -569,10 +567,7 @@ bool TReport_section::execute_postscript()
f.execute_postscript();
}
if (active())
{
TString80 str;
ok = _postscript.execute(report(), str);
}
ok = _postscript.execute(report());
return ok;
}
@ -597,6 +592,8 @@ void TReport_section::save(TXmlItem& root) const
item.SetAttr("hidden_if_needed", hidden_if_needed());
item.SetAttr("pagebreak", _page_break);
item.SetAttr("keep_with_next", keep_with_next());
if (condition().not_empty())
item.AddChild("condition") << condition();
if (grouped_by().not_empty())
item.AddChild("groupby") << grouped_by();
if (has_font())
@ -627,6 +624,16 @@ void TReport_section::load(const TXmlItem& sec)
if (font.load(sec))
set_font(font);
if (level() > 0)
{
const TXmlItem* cnd = sec.FindFirstChild("condition");
if (cnd != NULL)
{
TString str;
cnd->GetEnclosedText(str);
set_condition(str);
}
}
if (level() > 1)
{
const TXmlItem* gb = sec.FindFirstChild("groupby");
@ -698,13 +705,6 @@ TString& TReport_script::translate_message(TReport& rep) const
{
cmd = msg.left(comma);
args = msg.mid(comma+1);
if (args[0] != '#') // Controlla se c'e' bisogno di un # all'inizio
{
char type;
int level, id;
if (rep.parse_field(args.get(0), type, level, id) >= 2)
args.insert("#");
}
}
else
{
@ -718,8 +718,25 @@ TString& TReport_script::translate_message(TReport& rep) const
if (rep.defined(cmd))
{
TString& alx = msg_empty ? empty_alex : alex;
TString arg;
for (int i = args.items()-1; i >= 0; i--)
alx << args.get(i) << ' ';
{
arg = args.get(i);
// Controlla se c'e' bisogno di un # all'inizio
if (arg[0] != '#' && arg[0] != '"' && !is_a_number(arg))
{
char type;
int level, id;
if (i == 0 && rep.parse_field(arg, type, level, id) >= 3)
arg.insert("#");
else
{
arg.insert("\"");
arg << '"';
}
}
alx << arg << ' ';
}
alx << cmd << ' ';
}
else
@ -774,7 +791,7 @@ bool TReport_script::compile(TReport& rep)
return good;
}
bool TReport_script::execute(TReport& rep, TString& output)
bool TReport_script::execute(TReport& rep)
{
bool good = true;
if (ok())
@ -782,7 +799,7 @@ bool TReport_script::execute(TReport& rep, TString& output)
if (_bc == NULL)
good = compile(rep);
if (good)
good = rep.execute(*_bc, output);
good = rep.execute(*_bc);
}
return good;
}
@ -792,10 +809,9 @@ bool TReport_script::execute(TReport_field& rf)
bool good = true;
if (ok())
{
TString str;
TReport& rep = rf.section().report();
rep.set_curr_field(&rf);
good = execute(rep, str);
good = execute(rep);
}
return good;
}
@ -862,20 +878,21 @@ void TReport_field::offset(const TPoint& pt)
void TReport_field::set_draw_pos(long x, long y)
{
_rct_draw.x = x;
_rct_draw.y = y;
_draw_rct.x = x;
_draw_rct.y = y;
}
void TReport_field::set_draw_size(long w, long h)
{
_rct_draw.set_width(w);
_rct_draw.set_height(h);
_draw_rct.set_width(w);
_draw_rct.set_height(h);
}
void TReport_field::compute_draw_rect() const
{
TRectangle& rct = ((TReport_field*)this)->_rct_draw;
rct = get_rect();
TRectangle& rct = ((TReport_field*)this)->_draw_rct;
rct = _rct;
if (type() == 'S')
{
if (rct.width() <= 0)
@ -1044,11 +1061,16 @@ bool TReport_field::load_field()
}
else
section().report().evaluate(_field, _var, ft);
if (_var.is_empty() && _alt_field.not_empty())
section().report().evaluate(_alt_field, _var, ft);
}
else
_var.set_null();
}
compute_draw_rect();
_draw_rct = _rct;
_draw_hidden = _hidden;
_draw_deactivated = _deactivated;
return ok;
}
@ -1056,14 +1078,17 @@ bool TReport_field::load_field()
bool TReport_field::execute_prescript()
{
bool ok = true;
if (active())
if (!draw_deactivated())
{
ok = _prescript.execute(*this);
compute_draw_rect();
}
return ok;
}
bool TReport_field::execute_postscript()
{
return deactivated() || _postscript.execute(*this);
return draw_deactivated() || _postscript.execute(*this);
}
void TReport_field::draw_rect(TWindow& win) const
@ -1089,6 +1114,7 @@ void TReport_field::draw_text(TWindow& win, const char* text, TReport_draw_mode
xvt_font_copy(lnkfont, font().get_xvt_font(win), XVT_FA_ALL);
xvt_font_set_style(lnkfont, XVT_FS_UNDERLINE);
xvt_dwin_set_font(win.win(), lnkfont);
xvt_font_destroy(lnkfont);
win.set_color(link_color(), back_color());
}
else
@ -1097,7 +1123,7 @@ void TReport_field::draw_text(TWindow& win, const char* text, TReport_draw_mode
win.set_color(fore_color(), back_color());
}
if (rct.height() > 100)
if (rct.height() > 100) // Devo scrivere piu' righe?
{
const unsigned columns = rct.width() / 100;
int rows = rct.height() / 100;
@ -1199,13 +1225,22 @@ const TString& TReport_field::formatted_text() const
case 'P':
case 'V':
{
TString& tmp = get_tmp_string();
TCurrency cur; get_currency(cur);
TString& tmp = get_tmp_string();
tmp = cur.string(true);
return tmp;
}
break;
default:
if (_picture.not_empty())
{
TString& tmp = get_tmp_string();
if (_picture.find('#') >= 0)
tmp.picture(_picture, _var.as_string());
else
tmp << _picture << ' ' << _var.as_string();
return tmp;
}
return _var.as_string();
}
return EMPTY_STRING;
@ -1213,15 +1248,11 @@ const TString& TReport_field::formatted_text() const
void TReport_field::draw(TWindow& win, TReport_draw_mode rdm) const
{
if (rdm != rdm_edit && (hidden() || deactivated()))
return;
if (rdm == rdm_edit)
compute_draw_rect();
PAT_STYLE back_pattern = PAT_HOLLOW;
if (rdm == rdm_edit)
{
compute_draw_rect();
if (hidden() || deactivated())
{
if (hidden() && deactivated())
@ -1230,6 +1261,11 @@ void TReport_field::draw(TWindow& win, TReport_draw_mode rdm) const
back_pattern = hidden() ? PAT_FDIAG : PAT_BDIAG;
}
}
else
{
if (draw_hidden() || draw_deactivated())
return;
}
switch (_type)
{
@ -1343,7 +1379,7 @@ void TReport_field::set_groups(const TString& groups)
const TString& TReport_field::groups() const
{
TString& str = get_tmp_string();
str << _groups;
str << _groups; str.trim();
return str;
}
@ -1367,7 +1403,7 @@ void TReport_field::save(TXmlItem& root) const
set_num_attr(fld, "height", rct.height(), 100);
fld.SetAttr("hidden", _hidden);
fld.SetAttr("deactivated", _deactivated);
fld.SetAttr("zeroes_hidden", _hide_zeroes);
fld.SetAttr("hide_zero", _hide_zeroes);
set_col_attr(fld, "bg_color", back_color(), COLOR_WHITE);
set_col_attr(fld, "fg_color", fore_color(), COLOR_BLACK);
if (has_font())
@ -1394,6 +1430,8 @@ void TReport_field::save(TXmlItem& root) const
fld.SetAttr("link", link());
if (field().not_empty())
fld.AddChild("source") << field();
if (alternate_field().not_empty())
fld.AddChild("alt_source") << alternate_field();
_prescript.save(fld, "prescript");
_postscript.save(fld, "postscript");
@ -1421,10 +1459,10 @@ bool TReport_field::load(const TXmlItem& fld)
set_row(get_num_attr(fld, "y"));
set_width(get_num_attr(fld, "width"));
set_height(get_num_attr(fld, "height", 100));
_rct_draw = _rct;
_draw_rct = _rct;
show(!fld.GetBoolAttr("hidden"));
activate(!fld.GetBoolAttr("deactivated"));
hide_zeroes(fld.GetBoolAttr("zeroes_hidden"));
hide_zeroes(fld.GetBoolAttr("hide_zero"));
set_border(fld.GetIntAttr("border"));
set_back_color(get_col_attr(fld, "bg_color", COLOR_WHITE));
set_fore_color(get_col_attr(fld, "fg_color", COLOR_BLACK));
@ -1505,7 +1543,7 @@ TReport_field::TReport_field(TReport_section* sec)
{
set_pos(0,0);
set_size(1600,100);
_rct_draw = _rct;
_draw_rct = _rct;
}
TReport_field::TReport_field(const TReport_field& rf) : _font(NULL)
@ -1667,19 +1705,27 @@ int TReport::parse_field(const char* code, char& type, int& level, int& id) cons
if (isdigit(code[0]) || strncmp(code, "THIS", 4) == 0) // Niente sezione davanti
{
if (strchr(code, '.') != NULL)
return 0; // Mi sono confuso con un a campo su file, es: 34.CODART
TReport_field* rf = curr_field();
if (rf != NULL)
{
type = rf->section().type();
level = rf->section().level();
}
id = atoi(code);
if (code[0] == 'T')
id = rf->id();
else
id = atoi(code);
}
else
{
type = code[0];
if (type != 'H' && type != 'B' && type != 'F') // Non comincia con un codice sezione
return 0;
if (!isdigit(code[1])) // Non c'e' il livello
return 0;
level = atoi((const char*)code + 1);
TReport_section* sec = find_section(type, level);
@ -1724,7 +1770,7 @@ bool TReport::evaluate(const char* expr, TVariant& var, TFieldtypes force_type)
if (e.numvar() == 1)
{
const TFixed_string name(e.varname(0));
if (name == expr)
if (name == expr)
{
if (get_usr_val(name, var))
{
@ -1807,17 +1853,28 @@ bool TReport::load(const char* fname)
}
_include = xml.GetAttr("libraries");
FOR_EACH_TOKEN(_include, lib)
{
TFilename libname = lib;
libname.trim();
if (libname.find('.') < 0)
libname.ext("alx");
include(libname);
}
include_libraries();
_prescript.load(xml, "prescript");
_postscript.load(xml, "postscript");
_params.destroy();
const TXmlItem* params = xml.FindFirstChild("parameters");
if (params != NULL)
{
TToken_string tok, str;
for (int i = 0; i < params->GetChildren(); i++)
{
const TXmlItem* item = params->GetChild(i);
tok = item->GetAttr("name");
if (!tok.blank())
{
item->GetEnclosedText(str);
tok.add(str);
_params.add(tok);
}
}
}
}
return ok;
}
@ -1854,6 +1911,17 @@ bool TReport::save(const char* fname) const
_prescript.save(xml, "prescript");
_postscript.save(xml, "postscript");
if (_params.items() > 0) // Salva lista dei parametri se necessario
{
TXmlItem& params = xml.AddChild("parameters");
FOR_EACH_ARRAY_ROW(_params, i, str) if (!str->empty_items())
{
TXmlItem& item = params.AddChild("item");
item.SetAttr("name", str->get(0));
item << str->get();
}
}
xml.Save(fname);
}
return ok;
@ -1892,8 +1960,7 @@ bool TReport::execute_prescript()
warm_restart();
if (_prescript.ok())
{
TString80 str;
ok = _prescript.execute(*this, str);
ok = _prescript.execute(*this);
if (recordset() != NULL)
recordset()->ask_variables(false);
}
@ -1919,8 +1986,7 @@ bool TReport::execute_prescript()
bool TReport::execute_postscript()
{
TString80 str;
return _postscript.execute(*this, str);
return _postscript.execute(*this);
}
bool TReport::get_report_field(const TString& name, TVariant& var) const
@ -2016,8 +2082,8 @@ size_t TReport::get_usr_words(TString_array& words) const
const char* const name[] =
{
"***", "DISABLE", "ENABLE", "GET_POS",
"GET_SIZE", "HIDE", "RUN_FORM", "SET_BACK_COLOR", "SET_FORE_COLOR",
"SET_POS", "SET_SIZE", "SHOW", NULL
"GET_SIZE", "HIDE", "ISAM_READ", "RUN_FORM", "SET_BACK_COLOR", "SET_FORE_COLOR",
"SET_POS", "SET_SIZE", "SHOW", "TABLE_READ", NULL
};
size_t i;
for (i = 0; name[i] != NULL; i++)
@ -2026,10 +2092,10 @@ size_t TReport::get_usr_words(TString_array& words) const
}
static void do_show(TReport_field& rf, void* jolly)
{ rf.show(jolly != NULL); }
{ rf.set_draw_hidden(jolly == NULL); }
static void do_enable(TReport_field& rf, void* jolly)
{ rf.activate(jolly != NULL); }
{ rf.set_draw_deactivated(jolly == NULL); }
static void do_set_pos(TReport_field& rf, void* jolly)
{
@ -2144,6 +2210,95 @@ KEY TReport::run_form(const TString& maskname)
return key;
}
void TReport::do_isam_read_output(const TRectype& file, TToken_string& out)
{
TVariant var;
TString curr;
FOR_EACH_TOKEN(out, tok)
{ // scansione sugli elementi dell'output
curr = tok;
int posrv = 0;
const int poseq= curr.find('='); // divide la stringa corrente in lvalue e rvalue
if (poseq > 0)
{
posrv = poseq+1;
if (curr[posrv] == '=')
posrv++;
}
if (poseq < 0)
{
const TFieldref fr(curr, 0);
const TVariant var = fr.read(file); // preleva il nome del campo del file e lo legge dal record
curr_field()->set(var); // setta il campo corrente
}
else
{
const TString& fld = curr.left(poseq); // preleva il nome del campo del form alla sinistra dell'uguale
TReport_field* dest = field(fld);
if (dest != NULL)
{
const TFieldref fr(curr.mid(posrv), 0);
const TVariant var = fr.read(file); // preleva il nome del campo del file e lo legge dal record
dest->set(var); // setta il campo corrente
}
}
}
}
void TReport::msg_isam_read(TVariant_stack& stack)
{
const TString& f_code = stack.pop().as_string(); // prende il codice del file da leggere
const int logicnum = table2logic(f_code);
if (logicnum < LF_USER)
return; // File sconosciuto
TRectype keyrec(logicnum);
if (logicnum == LF_TAB || logicnum == LF_TABCOM)
keyrec.put("COD", f_code);
TToken_string in(stack.pop().as_string(), '!');
TVariant var;
TString curr;
FOR_EACH_TOKEN(in, tok)
{ // scansione sugli elementi dell'input
curr = tok;
const int poseq= curr.find('='); // divide la stringa corrente in lvalue e rvalue
int posrv = poseq+1;
if (curr[posrv] == '=')
posrv++;
evaluate(curr.mid(posrv), var, _alfafld);
const TString& fld = curr.left(poseq); // preleva il nome del campo del file alla sinistra dell'uguale
keyrec.put(fld, var.as_string()); // scrive il risultato dell'espressione nel campo del file
}
const TRectype& file = cache().get(keyrec);
if (!file.empty())
{
TToken_string out(stack.pop().as_string(), '!');
do_isam_read_output(file, out);
}
}
void TReport::msg_table_read(TVariant_stack& stack)
{
const TString& t_code = stack.pop().as_string(); // prende il codice della tabella da leggere
const int logicnum = table2logic(t_code);
if (logicnum == LF_TAB || logicnum == LF_TABCOM)
{
const TString& codtab = stack.pop().as_string();
TVariant var;
evaluate(codtab, var, _alfafld);
const TRectype& file = cache().get(t_code, var.as_string());
if (!file.empty())
{
TToken_string out(stack.pop().as_string(), '!');
do_isam_read_output(file, out);
}
}
}
bool TReport::execute_usr_word(unsigned int opcode, TVariant_stack& stack)
{
switch (opcode)
@ -2183,26 +2338,29 @@ bool TReport::execute_usr_word(unsigned int opcode, TVariant_stack& stack)
case 6: // HIDE
do_message(stack.pop(), do_show, NULL);
break;
case 7: // RUN_FORM
case 7: // ISAM_READ
msg_isam_read(stack);
break;
case 8: // RUN_FORM
{
const TString& msk = stack.pop().as_string();
const KEY key = run_form(msk);
stack.push(key);
}
break;
case 8: // SET_BACK_COLOR
case 9: // SET_BACK_COLOR
{
const COLOR rgb = stack.pop().as_color();
do_message(stack.pop(), do_set_back_color, (void*)rgb);
}
break;
case 9: // SET_FORE_COLOR
case 10: // SET_FORE_COLOR
{
const COLOR rgb = stack.pop().as_color();
do_message(stack.pop(), do_set_fore_color, (void*)rgb);
}
break;
case 10: // SET_POS
case 11: // SET_POS
{
const TVariant& fld = stack.pop();
const real y = stack.pop().as_real() * CENTO;
@ -2211,7 +2369,7 @@ bool TReport::execute_usr_word(unsigned int opcode, TVariant_stack& stack)
do_message(fld, do_set_pos, (void*)&pt);
}
break;
case 11: // SET_SIZE
case 12: // SET_SIZE
{
const TVariant& fld = stack.pop();
const real h = stack.pop().as_real() * CENTO;
@ -2220,9 +2378,12 @@ bool TReport::execute_usr_word(unsigned int opcode, TVariant_stack& stack)
do_message(fld, do_set_size, (void*)&sz);
}
break;
case 12: // SHOW
case 13: // SHOW
do_message(stack.pop(), do_show, (void*)1);
break;
case 14: // TABLE_READ
msg_table_read(stack);
break;
default:
return false;
}
@ -2248,12 +2409,24 @@ bool TReport::on_link(const TReport_link& lnk)
return false;
}
void TReport::include_libraries(bool reload)
{
TAlex_virtual_machine::include_libraries(reload);
if (reload || !defined("MESSAGE_ALIGN"))
include("report.alx");
FOR_EACH_TOKEN(_include, lib)
{
TFilename libname = lib;
libname.trim();
if (libname.find('.') < 0)
libname.ext("alx");
include(libname);
}
}
TReport::TReport() : _lpi(6), _recordset(NULL), _curr_field(NULL), _include(15, ',')
{
_expressions.set_report(this);
include("report.alx"); // Include base libraries
_prescript.set_description("PRESCRIPT");
_postscript.set_description("POSTSCRIPT");
}

View File

@ -117,7 +117,7 @@ public:
void set_description(const char* d) { _desc = d; }
bool compile(TReport& report);
bool execute(TReport& report, TString& output);
bool execute(TReport& report);
bool execute(TReport_field& rf);
void save(TXmlItem& root, const char* tag) const;
@ -143,7 +143,7 @@ class TReport_section : public TArray
int _level; // 0,1,2,...
TPoint _pos; // Posizione assoluta in centesimi, default (0,0)
TPoint _size; // Dimensioni in centesimi, default (0,0)
TString _groupby;
TString _condition, _groupby;
bool _page_break, _hidden_if_needed, _keep_with_next;
bool _hidden, _deactivated;
TReport_script _prescript, _postscript;
@ -179,9 +179,12 @@ public:
bool page_break() const { return _page_break; }
void force_page_break(bool pb) { _page_break = pb; }
const TString& condition() const { return _condition; }
void set_condition(const char* str) { _condition = str; }
const TString& grouped_by() const { return _groupby; }
void group_by(const char* gb) { _groupby = gb; }
bool hidden_if_needed() const { return _hidden_if_needed; }
void hide_if_needed(bool h) { _hidden_if_needed = h; }
bool keep_with_next() const { return _keep_with_next; }
@ -222,12 +225,13 @@ class TReport_field : public TSortable
TReport_section* _section;
int _id;
char _type; // Text, String, Numeric, Price, Valuta, Date, Line, Rectangle, Image
TRectangle _rct, _rct_draw; // In centesimi
TRectangle _rct; // In centesimi
COLOR _fgcolor, _bgcolor;
short _border;
char _halign, _valign;
TBit_array _groups;
TString _picture, _field, _codval, _link;
TString _picture, _codval, _link;
TString _field, _alt_field;
TVariant _var;
TReport_script _prescript, _postscript;
TToken_string _list; // Elementi di un campo lista
@ -235,6 +239,9 @@ class TReport_field : public TSortable
TReport_font* _font;
bool _hidden, _deactivated, _hide_zeroes, _selected;
TRectangle _draw_rct; // In centesimi
bool _draw_hidden, _draw_deactivated;
protected:
virtual const char* class_name() const { return "ReportField"; }
virtual int compare(const TSortable& s) const;
@ -261,6 +268,9 @@ public:
const TString& field() const { return _field; }
void set_field(const char* str) { _field = str; }
const TString& alternate_field() const { return _alt_field; }
void set_alternate_field(const char* str) { _alt_field = str; }
const TVariant& get() const { return _var; }
void set(const char* str);
@ -286,10 +296,6 @@ public:
void set_height(long dy) { _rct.set_height(dy); }
const TRectangle& get_rect() const { return _rct; }
void set_draw_pos(long x, long y);
void set_draw_size(long x, long y);
const TRectangle& get_draw_rect() const { return _rct_draw; }
bool hidden() const { return _hidden; }
bool shown() const { return !hidden(); }
void show(bool on) { _hidden = !on; }
@ -301,6 +307,15 @@ public:
bool zeroes_hidden() const { return _hide_zeroes; }
void hide_zeroes(bool hz) { _hide_zeroes = hz; }
bool draw_hidden() const { return _draw_hidden; }
bool draw_deactivated() const { return _draw_deactivated; }
void set_draw_hidden(bool h) { _draw_hidden = h; }
void set_draw_deactivated(bool d) { _draw_deactivated = d; }
void set_draw_pos(long x, long y);
void set_draw_size(long x, long y);
const TRectangle& get_draw_rect() const { return _draw_rct; }
void set_groups(const TString& groups);
const TString& groups() const;
bool in_group(int group) const;
@ -376,6 +391,7 @@ class TReport : public TAlex_virtual_machine
int _lpi; // Lines per inch
TToken_string _include;
TReport_script _prescript, _postscript;
TString_array _params;
TRecordset* _recordset;
TReport_expr_cache _expressions;
TReport_image_cache _images;
@ -391,6 +407,10 @@ protected:
KEY run_form(const TString& msk);
bool do_message(const TVariant& var, FLDMSG_FUNC msg, void* jolly);
void do_isam_read_output(const TRectype& rec, TToken_string& out);
void msg_isam_read(TVariant_stack& stack);
void msg_table_read(TVariant_stack& stack);
void build_section_key(char type, int level, TString& key) const;
short get_num_attr(const TXmlItem& item, const char* attr, short def = 0) const;
@ -430,8 +450,12 @@ public:
bool execute_prescript();
bool execute_postscript();
const TString_array& params() const { return _params; }
void set_params(const TString_array& p) { _params = p; }
void set_libraries(const char* inc) { _include = inc; }
TToken_string& get_libraries() { return _include; }
virtual void include_libraries(bool reload = false);
void set_description(const char* d) { _description = d; }
const TString& description() const { return _description; }

View File

@ -732,6 +732,16 @@ long TReport_printer::print_section(TReport_section& rs)
return 0;
rs.load_fields();
// Non sono sicuro se vada prima di load_fields o dopo execute_prescript
if (rs.condition().not_empty())
{
TVariant var;
_report.evaluate(rs.condition(), var, _nullfld);
if (!var.as_bool())
return 0;
}
rs.execute_prescript();
const long height = rs.compute_size().y; // Compute size after the initilization script!
@ -842,7 +852,7 @@ bool TReport_printer::print_loop()
_delta.y += print_section('H', g);
}
}
// Stampa di tutti i body
for (int b = 1; b <= max_body; b++)
{
const int dy = print_section('B', b);
@ -878,7 +888,31 @@ bool TReport_printer::print_loop()
}
if (rex->eof())
print_section('F', 1);
{
TReport_section* fl = _report.find_section('F',1);
if (fl != NULL) // Gestione footer last (se esite)
{
const int fy = fl->pos().y;
if (fy > 0) // Ha una coordinata y imposta
{
if (fy < _delta.y) // Sono gia' andato oltre quindi salto pagina
{
close_page();
open_page();
}
_delta.x = 0;
_delta.y = fy;
// Azzero temporaneamente le dimensioni del footer per evitare salti pagina
const int lfp = _logical_foot_pos;
_logical_foot_pos = _logical_page_height;
print_section(*fl);
_logical_foot_pos = lfp;
}
else
print_section(*fl); // Stampa normale
}
}
_is_last_page = true;
close_page();
}

View File

@ -427,6 +427,9 @@ const TString& TString::left(
// @rdesc Ritorna l'indirizzo della stringa contenente i <p count> caratteri da sinistra
{
if (count <= 0)
return EMPTY_STRING;
TString& spark = get_tmp_string();
spark = _str;
spark.cut(count);
@ -493,6 +496,44 @@ const TString& TString::sub(
return mid(from, count);
}
const TString& TString::after(char c) const
{
const int pos = find(c);
if (pos >= 0)
return mid(pos+1);
return EMPTY_STRING;
}
const TString& TString::after(const char* str) const
{
if (str && *str)
{
const int pos = find(str);
if (pos >= 0)
return mid(pos+strlen(str));
}
return EMPTY_STRING;
}
const TString& TString::before(char c) const
{
const int pos = find(c);
if (pos >= 0)
return left(pos);
return *this;
}
const TString& TString::before(const char* str) const
{
if (str && *str)
{
const int pos = find(str);
if (pos >= 0)
return left(pos);
}
return *this;
}
// Certified 100%
TString& TString::cut(int n)
{

View File

@ -116,6 +116,12 @@ public:
const TString& sub(int from, int to = -1) const;
// @cmember Ritorna l'oggetto TString composto dai count caratteri da destra
const TString& right(int count) const;
// @cmember Ritorna l'oggetto TString dopo la string passata
const TString& after(char c) const;
const TString& after(const char* str) const;
// @cmember Ritorna l'oggetto TString prima della string passata
const TString& before(char c) const;
const TString& before(const char* str) const;
// @cmember Ritorna un oggetto TString temporaneo composto dai count caratteri da sinistra
TString sleft(int count) const

View File

@ -170,7 +170,7 @@ TXmlItem& TXmlItem::SetAttr(const char* strAttr, bool b)
bool TXmlItem::GetBoolAttr(const char* strAttr) const
{
return !GetAttr(strAttr).blank();
return GetIntAttr(strAttr, 0) != 0;
}
int TXmlItem::GetChildren() const