campo-sirio/ci/cilib.cpp

913 lines
22 KiB
C++
Raw Normal View History

#include <colors.h>
#include <diction.h>
#include <image.h>
#include "cilib.h"
#include "RILORE.h"
#include "cimsk.h"
///////////////////////////////////////////////////////////
// TAlmanac_window
///////////////////////////////////////////////////////////
// @doc EXTERNAL
// @class TAlmanac_window | Finestra associata ad un TAlmanac_field
//
// @base public | TField_window
class TAlmanac_window : public TField_window
{
// @author:(INTERNAL) Brugno
// @access Protected Member
protected:
// override da TField_window
virtual void update();
// override da TField_window
virtual long handler(WINDOW win, EVENT* ep);
// @access Public Member
public:
// override da TField_window
virtual bool on_key(KEY k);
// @access Public Member
public:
// @cmember Costruttore
TAlmanac_window(int x, int y, int dx, int dy, WINDOW parent, TWindowed_field *owner);
// @cmember Distruttore
virtual ~TAlmanac_window() {}
};
void TAlmanac_window::update()
{
COLOR col_f, col_b;
RCT rct; xvt_vobj_get_client_rect(win(), &rct);
RCT rcttd;
TString str;
TAlmanac_field& o = (TAlmanac_field&)owner();
TField_window::update();
TDate cdate = o.selected_date();
cdate.set_day(1);
int cpage = o.mask().curr_page();
int rct_l, rct_t;
int rct_w = (rct.right - rct.left) / 9;
int rct_h = (rct.bottom - rct.top) / 9;
int pad = o.padding();
int row = 3;
set_font("", XVT_FS_BOLD);
set_color(NORMAL_COLOR, NORMAL_BACK_COLOR);
int fh = CHARY;
if (o.show_month_name())
{
str.format("%s %d", itom(cdate.month()),cdate.year());
rct_l = rct.left + rct_w;
rct_t = rct.top + rct_h;
xvt_dwin_draw_text(win(), rct_l + pad + 2, fh + rct_t + pad + 2, str, -1);
}
for (int i=1;i<=7;i++)
{
str.format("%.3s", itow(i));
rct_l = rct.left + rct_w*i;
rct_t = rct.top + rct_h*2;
xvt_dwin_draw_text(win(), rct_l + pad + 2, fh + rct_t + pad + 2, str, -1);
}
--cdate;
do
{
if ((++cdate).wday()==1 && cdate.day() > 1) row++;
col_b = NORMAL_BACK_COLOR;
col_f=NORMAL_COLOR;
if (o.is_date_void(cpage, cdate))
{
if (!o.can_insert(cdate))
col_b = DISABLED_BACK_COLOR;
}
else
col_b = FOCUS_BACK_COLOR;
set_pen(col_f);
set_brush(col_b);
rct_l = rct.left + rct_w*cdate.wday();
rct_t = rct.top + rct_h*row;
str.format("%2d", cdate.day());
rcttd.top = rct_t + pad;
rcttd.left = rct_l + pad;
rcttd.bottom = rct_t + rct_h - pad;
rcttd.right = rct_l + rct_w - pad;
xvt_dwin_draw_rect(win(), &rcttd);
if (cdate.is_holiday())
{
set_brush(o.can_insert(cdate) ? DISABLED_BACK_COLOR : NORMAL_COLOR, PAT_FDIAG);
xvt_dwin_draw_rect(win(), &rcttd);
}
if (o.is_selected(cdate.day()))
{
set_pen(FOCUS_COLOR,1);
rcttd.top++; rcttd.left++; rcttd.bottom--; rcttd.right--;
xvt_dwin_draw_rect(win(), &rcttd);
}
xvt_dwin_draw_text(win(), rct_l + pad + 2, fh + rct_t + pad, str, -1);
}
while (!cdate.is_end_month());
}
bool TAlmanac_window::on_key(KEY key)
{
TAlmanac_field& o = (TAlmanac_field&)owner();
TAlmanac_mask& m = (TAlmanac_mask&)o.mask();
const int smonth = o.selected_month();
const int syear = o.selected_year();
switch (key)
{
case K_RIGHT: o.move_selected_day(1); break;
case K_LEFT: o.move_selected_day(-1); break;
case K_UP: o.move_selected_day(-7); break;
case K_DOWN: o.move_selected_day(+7); break;
case K_SPACE:
case K_ENTER: m.open_day_mask(); break;
case K_PREV:
case K_NEXT:
case K_CTRL+K_F1:
case K_CTRL+K_F2:
case K_CTRL+K_F3:
case K_CTRL+K_F4:
case K_CTRL+K_F5:
case K_CTRL+K_F6:
case K_CTRL+K_F7:
case K_CTRL+K_F8:
case K_CTRL+K_F9:
case K_CTRL+K_F10:
case K_CTRL+K_F11:
case K_CTRL+K_F12:
m.on_key(key);
break;
default:
return TField_window::on_key(key);
}
if(syear != o.selected_year())
{
m.set_year(o.selected_year());
}
return true;
}
long TAlmanac_window::handler(WINDOW win, EVENT* ep)
{
switch(ep->type)
{
case E_MOUSE_DOWN:
case E_MOUSE_DBL:
{
TAlmanac_field & o = (TAlmanac_field&)owner();
TDate cdate = o.selected_date();
TDate fdate = cdate; fdate.set_day(1);
RCT rct; xvt_vobj_get_client_rect(win, &rct);
int rct_w = ((rct.right - rct.left) / 9);
int rct_h = ((rct.bottom - rct.top) / 9);
int pnt_c = (ep->v.mouse.where.h) / rct_w;
int pnt_r = (ep->v.mouse.where.v) / rct_h;
int delta = 7*pnt_r + pnt_c - (7*(3+cdate.week()-fdate.week()) + cdate.wday());
o.move_selected_day(delta);
if (ep->type==E_MOUSE_DBL)
((TAlmanac_mask&)o.mask()).open_day_mask();
}
break;
default:
break;
}
return TField_window::handler(win, ep);
}
TAlmanac_window::TAlmanac_window(int x, int y, int dx, int dy, WINDOW parent, TWindowed_field *owner)
: TField_window(x, y, dx, dy, parent, owner)
{
set_scroll_max(0, 0); // Get rid of that useless scrollbars
}
///////////////////////////////////////////////////////////
// TImage_window
///////////////////////////////////////////////////////////
// @doc EXTERNAL
// @class TAlmanac_window | Finestra associata ad un TAlmanac_field
//
// @base public | TField_window
class TImage_window : public TField_window
{
// @author:(INTERNAL) Brugno
int _curr_month;
// @access Protected Member
protected:
// override da TField_window
virtual void update();
// @access Public Member
public:
// @cmember Costruttore
TImage_window(int x, int y, int dx, int dy, WINDOW parent, TWindowed_field *owner);
// @cmember Distruttore
virtual ~TImage_window() {}
};
void TImage_window::update()
{
RCT rct; xvt_vobj_get_client_rect(win(), &rct);
TAlmanac_field & f = (TAlmanac_field&) owner();
const int month = f.selected_date().month();
_curr_month = month;
clear(MASK_BACK_COLOR);
TFilename month_img; month_img.format("%2smn%02d.jpg", (const char *) f.mask().source_file().left(2), _curr_month);
if (month_img.custom_path())
{
TImage bmp(month_img);
const double ratiox = (double) (rct.right) / (double) bmp.width();
const double ratioy = (double) (rct.bottom) / (double) bmp.height();
if (ratiox < ratioy)
{
int h = int(bmp.height() * ratiox);
rct.top = (rct.bottom - h) / 2;
rct.bottom = rct.top + h;
}
else
{
int w = int(bmp.width() * ratioy);
rct.left = (rct.right - w) / 2;
rct.right = rct.left + w;
}
bmp.draw(win(), rct);
}
}
TImage_window::TImage_window(int x, int y, int dx, int dy, WINDOW parent, TWindowed_field *owner)
: TField_window(x, y, dx, dy, parent, owner), _curr_month(0)
{
set_scroll_max(0, 0); // Get rid of that useless scrollbars
}
///////////////////////////////////////////////////////////
// TAlmanac_field
///////////////////////////////////////////////////////////
TField_window* TAlmanac_field::create_window(int x, int y, int dx, int dy, WINDOW parent)
{
TAlmanac_window* obj = new TAlmanac_window(x, y, dx, dy, parent, this);
RCT rct; xvt_vobj_get_outer_rect(obj->win(), &rct);
const int pad = 6;
if (rct.left > pad * 4)
{
_image = new TImage_window(-1, y, -1, dy, parent, this);
RCT img_rect; xvt_vobj_get_outer_rect(_image->win(), &img_rect);
img_rect.right = rct.left - pad;
img_rect.left = pad;
xvt_vobj_move(_image->win(), &img_rect);
}
return obj;
}
void TAlmanac_field::create(short id, const RCT& rect, WINDOW parent)
{
int x = rect.left/CHARX, y = rect.top/ROWY;
int h = (rect.bottom - rect.top)/ROWY, w = (rect.right - rect.left)/CHARX;
if (x+w > 80)
x = x + w - mask().columns() - 1;
TWindowed_field::create(id, x, y, w, h, parent);
}
bool TAlmanac_field::is_date_void(int currpage, const TDate& cdate)
{
return ((TAlmanac_mask &)mask()).is_date_void(currpage, cdate);
}
void TAlmanac_field::force_update(bool update_image)
{
win().force_update();
if (update_image && _image != NULL)
_image->force_update();
}
void TAlmanac_field::adjust_selected_day()
{
const int last = TDate::last_day(_selecteddate.month(), _selecteddate.year());
if (_selecteddate.day() > last)
_selecteddate.set_day(last);
}
void TAlmanac_field::set_selected_day(int nday)
{
if (nday>=1 && nday<=31 && nday != _selecteddate.day())
{
_selecteddate.set_day(nday);
adjust_selected_day();
force_update(false); // Dont'update the picture
}
}
void TAlmanac_field::move_selected_day(int ddays)
{
const int old_month = _selecteddate.month();
_selecteddate += ddays;
force_update(old_month != _selecteddate.month()); // Dont'update the picture if needed
}
void TAlmanac_field::set_selected_month(int nmonth)
{
if (nmonth >= 1 && nmonth <= 12 && nmonth != _selecteddate.month())
{
_selecteddate.set_month(nmonth);
adjust_selected_day();
force_update(true); // Update the picture too
}
}
void TAlmanac_field::move_selected_month(int dmonths)
{
_selecteddate.addmonth(dmonths);
force_update(true); // Update the picture too
}
void TAlmanac_field::set_selected_year(int nyear)
{
_selecteddate.set_year(nyear);
adjust_selected_day();
force_update(false); // Don't update the picture
}
///////////////////////////////////////////////////////////
// TAlmanac_mask
///////////////////////////////////////////////////////////
TMask_field* TAlmanac_mask::parse_field(TScanner& scanner)
{
const TString& k = scanner.key();
if (k.starts_with("AL", true))
{
TAlmanac_field* na = new TAlmanac_field(this);
_almanacs.add(na);
return na;
}
return TAutomask::parse_field(scanner);
}
bool TAlmanac_mask::on_field_event(TOperable_field& o, TField_event e, long jolly)
{
switch (o.dlg())
{
case F_PREVMONTH:
case F_NEXTMONTH:
if (e == fe_button)
{
TAlmanac_field& al = almanac();
const int old_year = al.selected_year();
al.move_selected_month(o.dlg() == F_PREVMONTH ? -1 : +1);
const int new_year = al.selected_year();
if (old_year != new_year) // Se cambio anno
set_year(new_year);
}
break;
case F_PREVYEAR:
case F_NEXTYEAR:
if (e == fe_button)
{
TAlmanac_field& al = almanac();
const int year = al.selected_year();
set_year(year + (o.dlg() == F_PREVYEAR ? -1 : +1));
}
break;
default:
break;
}
return true;
}
void TAlmanac_mask::set_focus()
{
TAutomask::set_focus();
int i;
for (i = _almanacs.last(); i >= 0; i = _almanacs.pred(i))
{
if (almanac(i).parent() == curr_win())
break;
}
const bool nav = i >= 0;
enable(F_PREVYEAR, nav);
enable(F_PREVMONTH, nav);
enable(F_NEXTMONTH, nav);
enable(F_NEXTYEAR, nav);
}
int TAlmanac_mask::activate_almanac(const short id, const char* title)
{
int i = -1; // Calendario non trovato
const int pos = id2pos(id);
if (pos >= 0) // Calendario esistente
{
for (i = _almanacs.last(); i >= 0; i = _almanacs.pred(i))
if (almanac(i).dlg() == id)
break;
if (i < 0) // Calendario non ancora censito ...
i = _almanacs.add(fld(pos)); // ... non dovrebbe mai succedere
}
if (i < 0) // Devo creare al volo un calendario
{
WINDOW parent = create_page(TR("Calendario"), -1);
const TAlmanac_field& ca = almanac(0);
RCT rect; ca.get_rect(rect);
TAlmanac_field* na = new TAlmanac_field(this);
na->create(id, rect, parent);
add_field(na);
i = _almanacs.add(na);
}
TAlmanac_field& na = almanac(i);
if (title && *title)
{
const int page = find_parent_page(na);
xvt_notebk_set_tab_title(notebook(), page, title);
}
const TDate sdate(TODAY); // Inizilizzo con la data odierna
na.set_selected_date(sdate);
return i;
}
TAlmanac_field & TAlmanac_mask::almanac(byte page) const
{
if (page >= _almanacs.items()) // Calcolo dell'indice del calendario corrente
{
for (page = _almanacs.last(); page > 0; page = _almanacs.pred(page))
{
if (almanac(page).parent() == curr_win())
break;
}
}
return (TAlmanac_field&)_almanacs[page];
}
void TAlmanac_mask::set_year(int newyear)
{
for (int i = _almanacs.last(); i >= 0; i = _almanacs.pred(i))
almanac(i).set_selected_year(newyear);
change_year(newyear);
}
const TDate& TAlmanac_mask::selected_day() const
{ return almanac().selected_date(); }
void TAlmanac_mask::change_year(int newyear)
{
// Funzione virtuale da ridefinire!
}
bool TAlmanac_mask::is_date_void(int currpage, const TDate& cdate)
{
return true;
}
TAlmanac_mask::TAlmanac_mask(const char* name)
{
read_mask(name, 0, -1); // Deve funzionare la virtual parse_field
set_handlers();
}
////////////////////////////
//// TRISOATT_KEY ////
////////////////////////////
//codlist: metodo che restituisce il codice listino
const TString & TRisoatt_key::codlist() const
{
return left(4);
}
//TIPO: metodo che restituisce il tipo (<R>isorsa o <A>ttrezzatura)
const char TRisoatt_key::tipo() const
{
return mid(4, 1)[0];
}
//COD: metodo che restituisce il codice della risorsa op dell'attrezzatura
const TString& TRisoatt_key::cod() const
{
return mid(5, 16);
}
//ANNO: metodo che restituisce l'anno a cui fa riferimento la risorsa o l'attrezzatura
const int TRisoatt_key::anno() const
{
return atoi(mid(21, 4));
}
//MESE: metodo che restituisce il mese a cui fa riferimento la risorsa o l'attrezzatura
const TString& TRisoatt_key::mese() const
{
return mid(25, 2);
}
const TString& TRisoatt_key::giorno() const
{
return mid(27, 2);
}
const TString& TRisoatt_key::data() const
{
TDate d(mid(21, 8));
TString & str = get_tmp_string(12);
str = d.string(ANSI);
return str;
}
//TPORA: metodo che restituisce il tipo dell'ora a cui fa riferimento la risorsa o l'attrezzatura
const TString& TRisoatt_key::tpora() const
{
return right(2);
}
TRisoatt_key::TRisoatt_key(const char* codlist, const char risoatt, const char* codice, const int anno, const char* mese, const char* giorno, const char* tpora)
{
TString16 lis = codlist; lis.left_just(4);
TString16 cod = codice; cod.left_just(16);
TString chiave; chiave << lis << risoatt << cod << anno << mese << giorno << tpora;
set(chiave);
}
TRisoatt_key::TRisoatt_key(const char* codlist, const char risoatt, const char* codice, const TDate & date, const char* tpora)
{
TString16 lis = codlist; lis.lpad(4, '0');
TString16 cod = codice; cod.left_just(16);
TString chiave; chiave << lis << risoatt << cod << date.string(ANSI) << tpora;
set(chiave);
}
TRisoatt_key::TRisoatt_key(const char* roakey)
{
set(roakey);
}
////////////////////////
//// TRISOATT ////
////////////////////////
bool TRisoatt::read(const TRisoatt_key& chiave)
{
int err = _iskeynotfound;
TModule_table tabmod("&ROA");
tabmod.put("CODTAB", chiave);
err = tabmod.read();
if (err != NOERR)
zero();
return err == NOERR;
}
//CHIAVE: metodo che restituisce la chiave della tabella di modulo
const TString& TRisoatt::chiave() const
{
return get("CODTAB");
}
//DESCR: metodo che restituisce la descrizione contenuta nella tabella di modulo
const TString& TRisoatt::descr() const
{
return get("S0");
}
//VALUNI: metodo che restituisce il valore unitario contenuto nella tabella di modulo
const real TRisoatt::valuni() const
{
return get_real("R1");
}
//VALUNIPR: metodo che restituisce il valore unitario contenuto nella tabella di modulo
const real TRisoatt::valunipr() const
{
return get_real("R2");
}
//costruttore
TRisoatt::TRisoatt(const TRectype& r)
: TRectype(r)
{
CHECK(r.num() == LF_TABMOD, "Tipo record errato");
}
TRisoatt::TRisoatt(const TRisoatt_key &chiave)
: TRectype(LF_TABMOD)
{
read(chiave);
}
/////////////////////////////
//// TDISP_RISOATT ////
/////////////////////////////
//CHIAVE: metodo che restituisce la chiave della tabella di modulo
const TString& TDisp_risoatt::chiave() const
{
return get("CODTAB");
}
//DESCR: metodo che restituisce la descrizione contenuta nella tabella di modulo
const long TDisp_risoatt::id() const
{
return get_long("S0");
}
//DESCR: metodo che restituisce la descrizione contenuta nella tabella di modulo
void TDisp_risoatt::set_id(long id)
{
TString & idstr = get_tmp_string(12);
idstr << id;
idstr.lpad('0');
put("S0", idstr);
}
//VALUNI: metodo che restituisce il valore unitario contenuto nella tabella di modulo
const int TDisp_risoatt::ore_prev() const
{
return get_int("I0");
}
//VALUNI: metodo che restituisce il valore unitario contenuto nella tabella di modulo
const int TDisp_risoatt::ore_cons() const
{
return get_int("I1");
}
//costruttore
TDisp_risoatt::TDisp_risoatt(const TRectype& r)
: TRectype(r)
{
CHECK(r.num() == LF_TABMOD, "Tipo record errato");
}
////////////////////////////////
//// TRILEVAMENTO_ORE ////
////////////////////////////////
//READ: cerca una riga rilevamento ore in base alla chiave primaria
int TRilevamento_ore::read(const char tipo, const long id, TReclock lock)
{
TLocalisamfile rilore(LF_RILORE);
int err = _iskeynotfound;
zero();
if (id > 0L)
{
put(RILORE_TIPO, tipo);
put(RILORE_ID, id);
while ((err = TRectype::read(rilore,_isequal, lock)) == _islocked)
if (!yesno_box("Dati in uso da parte di un altro utente"))
break;
}
if (err != NOERR)
{
long id = 0L;
zero();
put(RILORE_TIPO, tipo);
put(RILORE_ID, 99999999L);
int err1 = TRectype::read(rilore,_isequal);
if (err1 != _isemptyfile)
{
if (err1 != _iseof && err1 != _isbof)
rilore.prev();
if (tipo == rilore.get_char(RILORE_TIPO))
id = rilore.get_long(RILORE_ID);
}
id++;
put(RILORE_TIPO, tipo);
put(RILORE_ID, id);
}
return err;
}
int TRilevamento_ore::read(const char tipo, const int anno, const int mese, const int giorno, const char tipora, const char *codice, const char *tpora, const char* codcosto, const char* codcms, const char* codfase, TReclock lock)
{
TLocalisamfile rilore(LF_RILORE);
int err = NOERR;
rilore.setkey(2);
zero();
put(RILORE_TIPO, tipo);
put(RILORE_ANNO, anno);
put(RILORE_MESE, mese);
put(RILORE_GIORNO, giorno);
put(RILORE_TIPORA, tipora);
put(RILORE_CODICE, codice);
put(RILORE_TPORA, tpora);
put(RILORE_CODCOSTO, codcosto);
put(RILORE_CODCMS, codcms);
put(RILORE_CODFASE, codfase);
TRectype saverec(*this);
while ((err = TRectype::read(rilore,_isequal, lock)) == _islocked)
if (!yesno_box("Dati in uso da parte di un altro utente"))
break;
if (err != NOERR)
{
long id = 0L;
zero();
put(RILORE_TIPO, tipo);
put(RILORE_ID, 99999999L);
int err1 = TRectype::read(rilore,_isequal);
if (err1 != _isemptyfile)
{
if (err1 != _iseof && err1 != _isbof)
rilore.prev();
if (tipo == rilore.get_char(RILORE_TIPO))
id = rilore.get_long(RILORE_ID);
}
id++;
*this = saverec;
put(RILORE_ID, id);
}
rilore.setkey(1);
return err;
}
void TRilevamento_ore::update_id()
{
if (get_long(RILORE_ID) == 0L)
{
long id = 0;
TLocalisamfile rilore(LF_RILORE);
const TString4 tipo = get(RILORE_TIPO);
rilore.put(RILORE_TIPO, tipo);
rilore.put(RILORE_ID, 99999999L);
if (rilore.read() != _isemptyfile)
{
if (rilore.get(RILORE_TIPO) != tipo)
rilore.prev();
id = rilore.get_long(RILORE_ID);
}
put(RILORE_ID, ++id);
}
}
int TRilevamento_ore::write_rewrite()
{
if (!empty())
{
TLocalisamfile rilore(LF_RILORE);
update_id();
return TRectype::write_rewrite(rilore);
}
return _iskeynotfound;
}
int TRilevamento_ore::rewrite_write()
{
if (!empty())
{
TLocalisamfile rilore(LF_RILORE);
update_id();
return TRectype::rewrite_write(rilore);
}
return _iskeynotfound;
}
int TRilevamento_ore::remove()
{
if (!empty())
{
TLocalisamfile rilore(LF_RILORE);
return TRectype::remove(rilore);
}
return _iskeynotfound;
}
//Metodi costruttori
TRilevamento_ore::TRilevamento_ore(const TRectype& rec)
: TRectype(rec)
{
}
TRilevamento_ore::TRilevamento_ore(const TRilevamento_ore& rilore)
: TRectype(rilore)
{
}
TRilevamento_ore::TRilevamento_ore(const char tipo, const long id)
: TRectype(LF_RILORE)
{
read(tipo, id);
}
TRilevamento_ore::TRilevamento_ore(const char tipo, const int anno, const int mese, const int giorno, const char tipora, const char* codice, const char* tpora, const char* codcosto, const char* codcms, const char* codfase)
: TRectype(LF_RILORE)
{
read(tipo, anno, mese, giorno, tipora, codice, tpora, codcosto, codcms, codfase);
}
TRilevamento_ore::TRilevamento_ore()
: TRectype(LF_RILORE)
{
zero();
}
const long date2ndoc(const TDate& data)
{
const TDate inizio(1, 1, data.year());
return data - inizio + 1;
}
///////////////////////////
//// TDoc_cache ////
///////////////////////////
//KEY2OBJ:sceglie il documento giusto da disco in modo da poterlo continuare, o lo crea se non c'<27>
TObject* TDoc_cache::key2obj(const char* key)
{
TDocumento* doc = NULL;
TToken_string tmp(key);
TDoc_key chiave(key);
const char provv = chiave.provv();
const int anno = chiave.anno();
const TString& codnum = chiave.codnum();
const int ndoc = chiave.ndoc();
doc = new TDocumento(provv, anno, codnum, ndoc);
return doc;
}
//DOC: restituisce un puntatore ad un documento identificato dalla chiave documento completa
TDocumento& TDoc_cache::doc(const TDoc_key& kdoc)
{
return *(TDocumento*)objptr(kdoc);
}
TDocumento& TDoc_cache::new_doc(TDoc_key& kdoc)
{
kdoc.set_ndoc(0L);
return *(TDocumento*)objptr(kdoc);
}
//DISCARDING: salva un documento sul disco prima di eliminarlo dalla cache
void TDoc_cache::discarding(const THash_object* obj)
{
TDocumento& doc = (TDocumento&)obj->obj();
if (doc.physical_rows() == 0)
doc.remove();
else
doc.rewrite();
}