campo-sirio/ca/calib01.cpp
luca dd1994e6a7 Patch level :2.2 nopatch
Files correlati     :ca & friends
Ricompilazione Demo : [ ]
Commento            :
aggiunti i programmi di immissione dati per files 147,148,149;sistemate anche le maschere con i nuovi campi


git-svn-id: svn://10.65.10.50/trunk@12558 c028cbd2-c16b-5b4b-a496-9718f37d4682
2004-12-21 16:05:17 +00:00

777 lines
17 KiB
C++
Executable File

#include "calib01.h"
#include "calibmsk.h"
#include <tabutil.h>
#include <tree.h>
///////////////////////////////////////////////////////////
// TAnal_tree
///////////////////////////////////////////////////////////
struct TAnal_tree_pos : public TObject
{
TRecnotype _recno;
TToken_string _key;
void as_string(TString& id) const;
int level() const { return _key.items(); }
void reset();
};
void TAnal_tree_pos::as_string(TString& id) const
{
id.format("%ld|%s", _recno, (const char*)_key);
}
void TAnal_tree_pos::reset()
{
_recno = 0;
_key.cut(0);
}
class TAnal_tree : public TBidirectional_tree
{
TLocalisamfile* _file;
const TArray& _key1_fields;
const TArray& _key2_fields;
TAnal_tree_pos _curr;
protected:
virtual void node2id(const TObject* node, TString& id) const;
virtual bool goto_firstson();
virtual bool goto_rbrother();
virtual bool goto_node(const TString &id);
virtual TObject* curr_node() const;
virtual bool goto_father();
virtual bool goto_lbrother();
virtual bool get_description(TString& desc) const;
protected:
void update_curr();
const char* get_key_field(int key = 1) const;
int level_of(const TToken_string& key) const;
int level_of_file() const;
const TToken_string& curr_of_file() const;
int curr_level() const;
int max_level() const;
const TToken_string& father_of(const TToken_string& key) const;
const TToken_string& father_of_file() const;
bool repos() const;
public:
virtual bool goto_root();
TAnal_tree(int logicnum, const char* tabname, const TArray& key1, const TArray& key2);
virtual ~TAnal_tree();
};
///////////////////////////////////////////////////////////
// TAnal_msk
///////////////////////////////////////////////////////////
#define F_TREE 99
short TAnal_msk::get_field_id(int n, int k) const
{
short id = 0;
if (n >= 0 && n < fieldrefs(1))
{
if (k == 2)
id = F_DES1+n;
else
id = F_KEY1+n;
}
return id;
}
bool TAnal_msk::on_field_event(TOperable_field& o, TField_event e, long jolly)
{
switch (o.dlg())
{
case F_TREE:
if (e == fe_select)
{
if (edit_mode() && !dirty())
set_mode(MODE_QUERY);
if (query_mode())
{
const TTree_field& fld = (const TTree_field&)o;
const TTree& tree = *fld.tree();
TToken_string curr; tree.curr_id(curr);
for (int i = 0; ; i++)
{
const short id = get_field_id(i);
if (id <= 0)
break;
const char* tok = curr.get(i+1);
TEdit_field& e = efield(id);
e.set(tok);
e.show();
}
stop_run(K_AUTO_ENTER);
}
else
beep(0);
}
break;
default:
break;
}
return true;
}
int TAnal_msk::compute_offset() const
{
int delta = 0;
RCT rct; xvt_vobj_get_client_rect(TASK_WIN, &rct);
if (rct.right > 720)
delta = (rct.right - 720) / 2 / CHARX;
return delta;
}
void TAnal_msk::read(const char* name)
{
const int delta = compute_offset();
if (delta > 0)
{
const TFilename outname = "anal.msk";
TFilename inpname = name; inpname.ext("msk");
inpname.custom_path();
ofstream out(outname);
TString line;
int status = 0;
TScanner inp(inpname);
while (!inp.eof())
{
line = inp.line();
switch (status)
{
case 0:
if (line.starts_with("PA"))
status = 1; // Ho trovato la prima pagina
break;
case 1:
if (line.starts_with("PR")) // Ho trovato un prompt sulla prima pagina
{
TToken_string l(line, ' ');
int x = l.get_int(1);
if (x >= 0)
{
x += delta;
l.add(x, 1);
line = l;
}
} else
if (line.starts_with("PA")) // Ho finito la prima pagina
{
status = 2;
}
break;
default:
break;
}
out << line << endl;
}
out.close();
read_mask(outname, 0, 0);
xvt_fsys_removefile(outname);
}
else
read_mask(name, 0, 0);
create_key_fields();
create_tree_field();
}
int TAnal_msk::create_key_fields()
{
return 0;
}
short TAnal_msk::create_tree_field()
{
short id = 0;
const int delta = compute_offset();
if (delta > 0)
{
id = F_TREE;
add_tree(id, 0, 0, 1, (delta-1)*2, -1);
TAnal_tree* t = new TAnal_tree(get_logicnum(), get_tabname(), _key1_fields, _key2_fields);
tfield(id).set_tree(t);
t->goto_root();
t->expand();
}
set_handlers();
return id;
}
void TAnal_msk::update_tree_field()
{
const int pos = id2pos(F_TREE);
if (pos >= 0)
{
TTree_field& t = tfield(F_TREE);
t.win().force_update();
}
}
void TAnal_msk::add_fieldref(const char* name, int from, int to, int key)
{
TArray& a = key == 1 ? _key1_fields : _key2_fields;
TString80 str; str << name;
if (from > 0)
str << '[' << from << ',' << to << ']';
TFieldref* fr = new TFieldref(str, get_logicnum());
a.add(fr);
}
int TAnal_msk::fieldrefs(int k) const
{
const TArray& a = k == 1 ? _key1_fields : _key2_fields;
return a.items();
}
const TFieldref& TAnal_msk::fieldref(int n, int k) const
{
const TArray& a = k == 1 ? _key1_fields : _key2_fields;
return (const TFieldref&)a[n];
}
const TToken_string& TAnal_msk::get_key_value(const TRectype& rec, int c) const
{
TToken_string& val = get_tmp_string();
const int tot = fieldrefs(c);
for (int i = 0; i < tot; i++)
{
const TFieldref& field = fieldref(i, c);
val.add(field.read(rec));
}
return val;
}
const TToken_string& TAnal_msk::get_key_value(int c) const
{
TToken_string& val = get_tmp_string();
for (TEditable_field* f = get_key_field(c, true); f != NULL; f = get_key_field(c, false))
{
val.add(f->get());
}
return val;
}
///////////////////////////////////////////////////////////
// TAnal_tree
///////////////////////////////////////////////////////////
const TToken_string& TAnal_tree::curr_of_file() const
{
TToken_string& k = get_tmp_string();
const TRectype& rec = _file->curr();
for (int i = 0; i < max_level(); i++)
{
const TFieldref& fld = (const TFieldref&)_key1_fields[i];
k.add(fld.read(rec));
}
for (int j = k.len()-1; j >= 0; j--)
{
if (k[j] == ' ' || k[j] == k.separator())
k.cut(j);
else
break;
}
return k;
}
int TAnal_tree::level_of(const TToken_string& k) const
{
return k.items();
}
int TAnal_tree::level_of_file() const
{
const TToken_string& str = curr_of_file();
return level_of(str);
}
int TAnal_tree::curr_level() const
{
return level_of(_curr._key);
}
int TAnal_tree::max_level() const
{
return _key1_fields.items();
}
const TToken_string& TAnal_tree::father_of(const TToken_string& key) const
{
const int pos = key.rfind(key.separator());
if (pos <= 0)
return EMPTY_STRING;
TToken_string& k = get_tmp_string();
k = key.left(pos);
return k;
}
const TToken_string& TAnal_tree::father_of_file() const
{
const TToken_string& k = curr_of_file();
return father_of(k);
}
void TAnal_tree::update_curr()
{
_curr._key = curr_of_file();
if (_curr._key.not_empty())
_curr._recno = _file->recno();
else
_curr.reset();
}
bool TAnal_tree::repos() const
{
bool ok = false;
if (_curr.level() > 0)
{
if (_file->recno() != _curr._recno)
ok = ((TLocalisamfile*)_file)->readat(_curr._recno) == NOERR;
else
ok = true;
}
return ok;
}
void TAnal_tree::node2id(const TObject* node, TString& id) const
{
const TAnal_tree_pos* pos = (const TAnal_tree_pos*)node;
pos->as_string(id);
}
bool TAnal_tree::goto_root()
{
const bool ok = _file->first() == NOERR;
if (ok)
update_curr();
else
_curr.reset();
return ok;
}
bool TAnal_tree::goto_firstson()
{
bool ok = _curr.level() < max_level() && repos();
if (ok)
{
ok = _file->next() == NOERR;
if (ok)
{
ok = father_of_file() == _curr._key;
if (ok)
update_curr();
}
}
return ok;
}
bool TAnal_tree::goto_rbrother()
{
bool ok = false;
if (repos())
{
const TToken_string curr_father = father_of(_curr._key);
while (_file->next() == NOERR)
{
const int lev = level_of_file();
if (lev > _curr.level())
continue;
const TToken_string& next_father = father_of_file();
ok = next_father == curr_father;
break;
}
if (ok)
update_curr();
}
return ok;
}
bool TAnal_tree::goto_node(const TString &id)
{
const TRecnotype rec = atol(id);
const int err = _file->readat(rec);
if (err == NOERR)
update_curr();
return err == NOERR;
}
bool TAnal_tree::goto_father()
{
const int lev = _curr.level();
bool ok = lev > 1;
if (ok)
{
TRectype& rec = _file->curr();
rec.zero();
for (int i = 0; i < lev-1; i++)
{
const char* val = _curr._key.get(i);
const TFieldref& fld = (const TFieldref&)_key1_fields[i];
fld.write(val, rec);
}
ok = _file->read() == NOERR;
if (ok)
update_curr();
}
return ok;
}
bool TAnal_tree::goto_lbrother()
{
bool ok = false;
if (repos())
{
const TString curr_father = father_of(_curr._key);
while (_file->prev() == NOERR)
{
const int lev = level_of_file();
if (lev > _curr.level())
continue;
const TString& next_father = father_of_file();
ok = next_father == curr_father;
break;
}
if (ok)
update_curr();
}
return ok;
}
TObject* TAnal_tree::curr_node() const
{
return (TObject*)&_curr;
}
bool TAnal_tree::get_description(TString& desc) const
{
const bool ok = repos();
if (ok)
{
const int lev = _curr.level();
if (lev > 0)
{
const TFieldref& fld1 = (const TFieldref&)_key1_fields[lev-1];
const TFieldref& fld2 = (const TFieldref&)_key2_fields[0];
desc = fld1.read(_file->curr());
desc << ' ' << fld2.read(_file->curr());
}
}
return ok;
}
TAnal_tree::TAnal_tree(int logicnum, const char* tabname, const TArray& key1, const TArray& key2)
: _key1_fields(key1), _key2_fields(key2)
{
if (tabname && *tabname)
_file = new TTable(tabname);
else
_file = new TLocalisamfile(logicnum);
}
TAnal_tree::~TAnal_tree()
{
delete _file;
}
///////////////////////////////////////////////////////////
// TSimple_anal_msk
///////////////////////////////////////////////////////////
const char* TSimple_anal_msk::get_key_fieldname(int k) const
{
const int logic = get_logicnum();
const RecDes& rd = prefix().get_recdes(logic);
CHECKD(k > 0 && k <= rd.NKeys, "Invalid key ", k);
const KeyDes& ky = rd.Ky[k-1];
const int idx = (logic == LF_TAB || logic == LF_TABCOM) ? 1 : 0;
const int pos = ky.FieldSeq[idx] % MaxFields;
return rd.Fd[pos].Name;
}
void TSimple_anal_msk::append_select_clause(ostream& out, int level) const
{
const TFieldref& key = fieldref(level-1, 1);
TString str;
str << " SE STR(";
if (level > 1)
str << "(NUM(LEN(" << key.name() << "))>" << key.from() << ')'; // SE LEN(CODCONTO)>=4
if (level < fieldrefs())
{
if (level > 1) str << "&&";
str << "(NUM(LEN(" << key.name() << "))<=" << key.to() << ')'; // SE LEN(CODCONTO)<=7
}
str << ')';
out << str << endl;
}
void TSimple_anal_msk::create_key_browse(TEdit_field& kfld, int level, TConfig& cfg)
{
TFilename tmp; tmp.temp();
ofstream out(tmp);
const int logic = get_logicnum();
out << "US ";
if (logic == LF_TAB || logic == LF_TABCOM)
out << get_tabname();
else
out << get_logicnum();
out << " KE 1";
append_select_clause(out, level);
out << "KE 1" << endl;
for (int i = 1; i <= level; i++)
{
const TString& picture = cfg.get(get_key_var(), NULL, i);
const TString& prompt = cfg.get(get_des_var(), NULL, i);
const TFieldref& field = fieldref(i-1, 1);
const int length = field.to() - field.from();
out << "IN " << field << ' ' << get_field_id(i-1, 1) << endl;
out << "DI \"" << prompt << '@' << length << "\" " << field << endl;
out << "OU " << get_field_id(i-1, 1) << ' ' << field << endl;
if (i == level)
out << "FI " << field << endl;
}
const TFieldref& field = fieldref(0, 2);
out << "DI \"Descrizione@50\" " << fieldref(0, 2) << endl;
out << "OU " << get_field_id(level-1, 2) << ' ' << field << endl;
out << "CH " << (level == 1 ? "RE" : "NO") << endl;
out << "EN" << endl;
out.close();
TScanner scan(tmp);
while (scan.pop() != "EN")
kfld.parse_item(scan);
xvt_fsys_removefile(tmp);
}
void TSimple_anal_msk::create_des_browse(TEdit_field& kfld, int level, TConfig& cfg)
{
TString key2; key2 << fieldref(0, 2);
TFilename tmp; tmp.temp();
ofstream out(tmp);
const int logic = get_logicnum();
out << "US ";
if (logic == LF_TAB || logic == LF_TABCOM)
out << get_tabname();
else
out << get_logicnum();
out << " KE 2";
append_select_clause(out, level);
out << "KE 2" << endl;
out << "DI \"Descrizione@50\" " << key2 << endl;
out << "IN " << key2 << ' ' << kfld.dlg() << endl;
out << "OU " << kfld.dlg() << ' ' << key2 << endl;
int from = 1, to = 1;
for (int i = 1; i <= level; i++)
{
const TString& picture = cfg.get(get_key_var(), NULL, i);
const TString& prompt = cfg.get(get_des_var(), NULL, i);
const TFieldref& field = fieldref(i-1, 1);
const int length = field.to() - field.from();
out << "DI \"" << prompt << '@' << length << "\" " << field << endl;
out << "OU " << get_field_id(i-1, 1) << ' ' << field << endl;
from = to+1;
}
out << "CH NO" << endl;
out << "EN" << endl;
out.close();
TScanner scan(tmp);
while (scan.pop() != "EN")
kfld.parse_item(scan);
xvt_fsys_removefile(tmp);
}
int TSimple_anal_msk::create_key_fields()
{
TConfig cfg(CONFIG_DITTA, "ca");
const char* keyvar = get_key_var();
const char* desvar = get_des_var();
int maxkeylen = 0, maxdeslen = 0;
int level;
int from = 1, to = 1;
for (level = 1; ; level++)
{
const TString& prompt = cfg.get(desvar, NULL, level);
if (prompt.blank())
break;
const TString& picture = cfg.get(keyvar, NULL, level);
const int keylen = picture.len();
const int deslen = prompt.len();
if (keylen > maxkeylen) maxkeylen = keylen;
if (deslen > maxdeslen) maxdeslen = deslen;
to = from+keylen-1;
add_fieldref(get_key_fieldname(1), from, to, 1);
from = to+1;
}
add_fieldref(get_key_fieldname(2), 0, 0, 2);
maxdeslen++;
const int tab0 = compute_offset()+2;
const int tab1 = tab0 + maxdeslen + maxkeylen + 4;
int i;
for (i = 1; i < level; i++)
{
const short kid = get_field_id(i-1, 1);
CHECKD(kid > 100, "Invalid field id:", kid);
const TString& picture = cfg.get(keyvar, NULL, i);
TString80 prompt = cfg.get(desvar, NULL, i);
prompt.left_just(maxdeslen);
TEdit_field& kfld = add_string(kid, 0, prompt, tab0, i, picture.len(), "BU");
create_key_browse(kfld, i, cfg);
}
for (i = 1; i < level; i++)
{
const short did = get_field_id(i-1, 2);
TEdit_field& dfld = add_string(did, 0, "", tab1, i, 50, "B", 72+tab0-tab1);
create_des_browse(dfld, i, cfg);
}
return level;
}
///////////////////////////////////////////////////////////
// TAnal_app
///////////////////////////////////////////////////////////
void TAnal_app::init_key_fields() const
{
int maxlev = 0;
for (maxlev = 0; maxlev < 4; maxlev++)
{
const short id = _msk->get_field_id(maxlev, 1);
if (id <= 0 || _msk->id2pos(id) < 0)
break;
_msk->disable(id);
const short did = _msk->get_field_id(maxlev, 2);
_msk->disable(did);
}
for (int i = maxlev-1; i >= 0; i--)
{
const short id = _msk->get_field_id(i, 1);
TEdit_field& e = _msk->efield(id);
const short did = _msk->get_field_id(i, 2);
TEdit_field& d = _msk->efield(did);
if (e.empty())
{
e.hide();
d.hide();
}
else
{
TString key2; key2 << _msk->fieldref(0, 2);
e.show();
e.check(STARTING_CHECK);
d.show();
d.set_field(key2);
d.enable();
d.enable_check(false);
break;
}
}
}
TRelation* TAnal_app::create_relation() const
{
return new TRelation(_msk->get_logicnum());
}
bool TAnal_app::user_create()
{
_msk = create_mask();
_rel = create_relation();
return true;
}
void TAnal_app::init_query_mode(TMask& mask)
{
TAnal_msk& m = (TAnal_msk&)mask;
for (int i = 0; ; i++)
{
const short id = m.get_field_id(i, 1);
if (id <= 0 || m.id2pos(id) < 0)
break;
TEdit_field& e = m.efield(id);
e.show(); e.enable();
const short did = m.get_field_id(i, 2);
TEdit_field& d = m.efield(did);
d.show(); d.enable();
d.set_field(EMPTY_STRING);
d.enable_check();
}
}
void TAnal_app::init_modify_mode(TMask& m)
{
init_key_fields();
}
void TAnal_app::init_insert_mode(TMask& m)
{
init_key_fields();
}
int TAnal_app::write(const TMask& m)
{
_msk->update_tree_field();
return TRelation_application::write(m);
}
int TAnal_app::rewrite(const TMask& m)
{
_msk->update_tree_field();
return TRelation_application::rewrite(m);
}
bool TAnal_app::user_destroy()
{
if (_msk != NULL)
delete _msk;
if (_rel != NULL)
delete _rel;
return true;
}