campo-sirio/ba/ba0100.cpp
guy ea1fdbbc2c Patch level : 10.0
Files correlati     : ba0.exe
Ricompilazione Demo : [ ]
Commento            :
Aggiunta opzione per eseguire programmi a schermo intero quando si hanno piccoli monitor  4:3, per cui il menu outlook sia troppo ingombrante


git-svn-id: svn://10.65.10.50/trunk@19099 c028cbd2-c16b-5b4b-a496-9718f37d4682
2009-07-09 13:02:07 +00:00

2165 lines
54 KiB
C++
Executable File
Raw Blame History

#include <applicat.h>
#include <automask.h>
#include <controls.h>
#include <dongle.h>
#include <execp.h>
#include <modaut.h>
#include <execp.h>
#include <recarray.h>
#include <relation.h>
#include <progind.h>
#include <sheet.h>
#include <treectrl.h>
#include <utility.h>
#include <urldefid.h>
#include <nditte.h>
#include <user.h>
#include "ba0.h"
#include "ba0101.h"
#include "ba0102.h"
#include "ba0103.h"
#include "ba0100.h"
#include "ba0100a.h"
#include "ba0400a.h"
#define MEN_FILE "bamenu.men"
#define PREFERRED_MENU M_STYLE
#define DLG_TREE 301
#define DLG_LIST 302
///////////////////////////////////////////////////////////
// TMenu_application declaration
///////////////////////////////////////////////////////////
class TMenu_application : public TSkeleton_application
{
TFilename _menuname;
TMenu _menu;
int _tree_view;
TString_array _preferred;
TMask* _mask;
protected: // TApplication
virtual bool user_create();
virtual bool destroy();
virtual bool menu(MENU_TAG m);
virtual long handler(WINDOW win, EVENT* ep);
virtual bool firm_change_enabled() const;
virtual void on_firm_change();
virtual bool test_assistance_year() const;
bool ask_user_password(TString& utente);
protected:
void deconnect_user();
virtual void main_loop();
void test_temp();
int do_level();
int do_tree();
int do_explore();
int do_outlook();
int get_user_status(const char* usr) const;
bool set_user_status(const char* usr, int status) const;
bool check_user();
static bool menu_item_handler(TMask_field& f, KEY k);
static bool menu_find_handler(TMask_field& f, KEY k);
static bool tree_handler(TMask_field& f, KEY k);
static bool explore_handler(TMask_field& f, KEY k);
bool choose_colors();
bool choose_editors();
bool choose_study();
void load_preferences();
void save_preferences();
void update_preferred_tree();
void update_preferred();
void add_to_preferred();
void manage_preferred();
bool test_programs();
bool copy_setup(const TString& remote_path);
public:
TTree_field& tree_field() const;
void select_tree_current();
static bool tree_find_handler(TMask_field& f, KEY k);
static bool tree_shrink_handler(TMask_field& f, KEY k);
public:
void reload_images();
TMenu& main_menu() { return _menu; }
TMenu_application(const char* name) : _menuname(name), _mask(NULL) { }
virtual ~TMenu_application() { }
};
inline TMenu_application& app()
{ return (TMenu_application&)main_app(); }
///////////////////////////////////////////////////////////
// Picture Mask
///////////////////////////////////////////////////////////
class TPicture_mask : public TMask
{
TSubmenu* _submenu;
TImage* _logo;
protected: // TMask
virtual void update();
virtual bool on_key(KEY k);
virtual void on_firm_change();
public:
virtual bool stop_run(KEY key);
void set_current(const TSubmenu& sm);
TPicture_mask(const char* name, int dx, int dy, const TSubmenu& sm, int x = -1, int y = -1);
virtual ~TPicture_mask();
};
bool TPicture_mask::stop_run(KEY key)
{
if (key == K_FORCE_CLOSE)
key = K_QUIT;
return TWindow::stop_run(key);
}
void TPicture_mask::update()
{
if (!ADVANCED_GRAPHICS)
return;
const TImage& image = _submenu->image();
if (image.ok())
{
RCT client; xvt_vobj_get_client_rect(win(), &client);
const bool tree_view = id2pos(DLG_TREE) >= 0;
if (tree_view) // TreeView == 1
{
RCT tree; tfield(DLG_TREE).get_rect(tree);
RCT lgo = client; lgo.left = tree.right; lgo.bottom /= 3;
if (_logo != NULL)
_logo->draw(win(), lgo, 'R', 'T', '-');
lgo = client; lgo.left = tree.right; lgo.top = lgo.bottom/3; lgo.bottom -= lgo.top;
image.draw(win(), lgo, 'R', 'B', '-');
}
else
{
RCT but; field(101).get_rect(but);
RCT lgo = client; lgo.right = but.left; lgo.bottom /= 2;
if (_logo != NULL)
_logo->draw(win(), lgo, 'L', 'T', '-');
lgo = client; lgo.right = but.left; lgo.top = lgo.bottom/2;
image.draw(win(), lgo, 'L', 'B', '-');
}
}
}
bool TPicture_mask::on_key(KEY k)
{
switch (k)
{
case K_F3:
case K_F8:
set(DLG_USER, app().main_menu().last_search_string(), true);
return true;
default:
break;
}
return TMask::on_key(k);
}
void TPicture_mask::on_firm_change()
{
force_update();
}
void TPicture_mask::set_current(const TSubmenu& sm)
{
_submenu = (TSubmenu*)&sm;
}
TPicture_mask::TPicture_mask(const char* name, int dx, int dy,
const TSubmenu& submenu, int x, int y)
: TMask(name, 1, dx, dy, x, y), _submenu(NULL), _logo(NULL)
{
set_current(submenu);
//trova il logo corretto in base al producer
const TString& currlogo = get_logo();
_logo = new TImage(currlogo);
if (_logo->ok())
{
if (can_be_transparent(*_logo))
_logo->convert_transparent_color(MASK_BACK_COLOR);
}
else
{
delete _logo;
_logo = NULL;
}
}
TPicture_mask::~TPicture_mask()
{
if (_logo != NULL)
delete _logo;
}
///////////////////////////////////////////////////////////
// Color Mask
///////////////////////////////////////////////////////////
class TColor_mask : public TAutomask
{
class TPreview_panel : public TWindow
{
TColor_mask* _owner;
protected:
COLOR get_color_entry(const char* name) const;
virtual void update();
public:
TPreview_panel(short x, short y, short dx, short dy, TColor_mask* owner);
} *_preview;
class TPreview_icons : public TWindow
{
TColor_mask* _owner;
protected:
virtual void update();
public:
TPreview_icons(short x, short y, short dx, short dy, TColor_mask* owner);
} *_icons;
int _cur_theme;
TAssoc_array _color;
protected: // TMask
virtual bool stop_run(KEY key) { return TWindow::stop_run(key); }
virtual bool on_field_event(TOperable_field& f, TField_event e, long jolly);
void colors2mask();
void mask2colors();
protected:
COLOR get_color_entry(const char* c) const;
void set_color_entry(const char* name, COLOR col);
const TString& get_font_desc() const;
void set_font_desc(const TString& fd);
const char* cid2name(short cid) const;
COLOR cid2color(short cid) const;
COLOR cid2syscolor(short cid, const XVT_COLOR_COMPONENT* cc) const;
bool find_themes_ini(TFilename& ininame) const;
void load_themes();
bool apply_theme();
void save_colors(TConfig& colors);
public:
void save_colors();
TColor_mask();
};
COLOR TColor_mask::TPreview_panel::get_color_entry(const char* name) const
{ return _owner->get_color_entry(name); }
TColor_mask::TPreview_panel::TPreview_panel(short x, short y, short dx, short dy, TColor_mask* owner)
: _owner(owner)
{ create(x, y, dx, dy, "", 0, W_PLAIN, owner->page_win(0)); }
void TColor_mask::TPreview_panel::update()
{
COLOR p, b;
const int x = 0;
const int y = 0;
const int w = columns();
const int h = rows();
b = get_color_entry("MaskBack");
clear(b);
set_pen(p = get_color_entry("MaskLight"));
line(x+1, y, x+w-2, y);
line(x+1, y, x+1, y+h-1);
set_pen(p = get_color_entry("MaskDark"));
line(x+1, y+h-1, x+w-2, y+h-1);
line(x+w-2, y+h-1, x+w-2, y);
const TString& font_desc = _owner->get_font_desc();
if (font_desc.full())
{
XVT_FNTID fontid = xvt_font_create();
xvt_font_deserialize(fontid, font_desc);
xvt_dwin_set_font(win(), fontid);
xvt_font_destroy(fontid);
}
else
xvt_dwin_set_font(win(), xvtil_default_font());
set_opaque_text(false);
set_pen(p = get_color_entry("Normal"));
set_brush(b = get_color_entry("NormalBack"));
frame(x+3, y+1, x+w-3, y+2, 0);
set_color(p, b);
stringat(x+4, y+1, "Campo normale");
set_pen(p = get_color_entry("Normal")); // Stesso inchiostro del normale
set_brush(b = get_color_entry("RequiredBack"));
frame(x+3, y+3, x+w-3, y+4, 0);
set_color(p, b);
stringat(x+4, y+3, "Campo obbligatorio");
set_pen(p = get_color_entry("Focus"));
set_brush(b = get_color_entry("FocusBack"));
frame(x+3, y+5, x+w-3, y+6, 0);
set_color(p, b);
stringat(x+4, y+5, "Campo attivo");
set_pen(p = get_color_entry("Disabled"));
set_brush(b = get_color_entry("DisabledBack"));
frame(x+3, y+7, x+w-3, y+8, 0);
set_color(p, b);
stringat(x+4, y+7, "Campo disabilitato");
set_pen(p = get_color_entry("ButtonLight"));
set_brush(b = get_color_entry("ButtonBack"));
frame(x+3, y+9, x+w-3, y+10, 0);
set_color(get_color_entry("Normal"), b);
stringat(x+4, y+9, "Bottone normale");
}
void TColor_mask::TPreview_icons::update()
{
RCT rct; xvt_vobj_get_client_rect(win(), &rct);
clear(MASK_BACK_COLOR);
set_pen(MASK_DARK_COLOR);
xvt_dwin_draw_rect(win(), &rct);
const int s = _owner->get_int(217);
const int sz = 16 + s*8;
const int y = (rct.bottom - sz)/2;
int x = (rct.right - 3*sz)/2;
for (short id = 201; id <= 203; id++, x += sz)
xvt_dwin_draw_tool(win(), x, y, id, sz);
}
TColor_mask::TPreview_icons::TPreview_icons(short x, short y, short dx, short dy, TColor_mask* owner)
: _owner(owner)
{ create(x, y, dx, dy, "", 0, W_PLAIN, owner->page_win(1)); }
void TColor_mask::load_themes()
{
TList_field& fl = lfield(211);
TToken_string codes = fl.get_codes();
TToken_string values = fl.get_values();
const int default_items = 3; // Corrente, Tradizionale, Sistema
// Elimina tutti gli elementi non standard (oltre il terzo)
if (codes.items() > default_items)
{
for (int i = 0; i < 2; i++)
{
TToken_string& str = i == 0 ? codes : values;
int pos = 0;
for (int j = 0; j < default_items; j++)
pos = str.find(str.separator(), pos);
str.cut(pos);
}
}
int k = codes.items();
TFilename ininame; find_themes_ini(ininame);
TConfig default_themes(ininame);
TString_array pl;
default_themes.list_paragraphs(pl);
FOR_EACH_ARRAY_ROW(pl, i, row)
{
codes.add(k++);
values.add(row->left(15));
}
TConfig user_themes(CONFIG_GUI, "Colors");
user_themes.list_paragraphs(pl);
FOR_EACH_ARRAY_ROW(pl, j, raw)
{
if (raw->starts_with("Theme_"))
{
codes.add(k++);
values.add(raw->mid(6, 15));
}
}
if (k > default_items)
fl.replace_items(codes, values);
}
bool TColor_mask::find_themes_ini(TFilename& ininame) const
{
ininame = get_oem_info("Themes");
bool ok = ininame.full();
if (ok)
{
ininame.insert("setup/");
ok = ininame.exist();
if (!ok)
{
ininame = "res/themes.ini"; // Compatibility mode
ok = ininame.exist();
}
}
return ok;
}
void TColor_mask::colors2mask()
{
TProp_field& pg = (TProp_field&)field(212);
pg.freeze(true);
FOR_EACH_ASSOC_STRING(_color, h, key, color)
{
const TFixed_string str(color);
if (str.find(',') > 0) // E' una proprieta' colore?
pg.set_property(key, color);
}
pg.freeze(false);
_preview->force_update();
}
void TColor_mask::mask2colors()
{
const TProp_field& pg = (const TProp_field&)field(212);
FOR_EACH_ASSOC_STRING(_color, h, key, color)
{
const TFixed_string str(color);
if (str.find(',') > 0) // E' una proprieta' colore?
{
const COLOR rgb = pg.get_color_property(key);
if (rgb != COLOR_INVALID)
set_color_entry(key, rgb);
}
}
_preview->force_update();
}
bool TColor_mask::apply_theme()
{
bool applied = false;
const int theme = get_int(211);
if (theme > 2) // Normal theme
{
const TList_field& fl = lfield(211);
TToken_string values = fl.get_values();
TString name = values.get(theme);
TFilename thini; find_themes_ini(thini);
TConfig def_themes(thini, name);
TAssoc_array& def_colors = def_themes.list_variables();
name.insert("Theme_");
TConfig usr_themes(CONFIG_GUI, name);
TAssoc_array& usr_colors = usr_themes.list_variables();
TAssoc_array& colors = usr_colors.empty() ? def_colors : usr_colors;
if (!colors.empty())
{
_color = colors;
FOR_EACH_MASK_FIELD((*this), i, f)
{
const TFieldref* fr = f->field();
if (fr != NULL)
{
const TString* val = (const TString*)_color.objptr(fr->name());
if (val != NULL)
f->set(*val);
}
}
applied = true;
}
}
if (!applied)
{
switch (theme)
{
case 1: // Campo default colors
{
for (short bid = 101; bid <= 113; bid++)
{
const char* name = cid2name(bid);
const COLOR color = cid2color(bid);
set_color_entry(name, color);
}
set_font_desc("");
applied = true;
}
break;
case 2: // System colors
{
XVT_COLOR_COMPONENT* cc = (XVT_COLOR_COMPONENT*)xvt_vobj_get_attr(NULL_WIN, ATTR_APP_CTL_COLORS);
for (short bid = 101; bid <= 113; bid++)
{
const char* name = cid2name(bid);
const COLOR color = cid2syscolor(bid, cc);
set_color_entry(name, color);
}
xvt_mem_free((DATA_PTR)cc);
XVT_FNTID defont = xvtil_default_font(false, false); // Legge il font standard
XVT_FNTID fontid = xvt_res_get_font(0); // Legge il font di sistema
xvt_font_set_size(fontid, xvt_font_get_size(defont)); // Forza l'altezza standard
TString256 fd; xvt_font_serialize(fontid, fd.get_buffer(), fd.size());
set_font_desc(fd);
xvt_font_destroy(fontid); // Rilascia il font di sistema
set(213, "X"); // Campi 3D
set(214, "X"); // System buttons
applied = true;
}
break;
default: // User defined settings
{
TConfig color(CONFIG_GUI, "Colors");
_color = color.list_variables();
}
break;
}
}
if (applied)
_cur_theme = theme;
colors2mask();
return applied;
}
bool TColor_mask::on_field_event(TOperable_field& f, TField_event e, long jolly)
{
const short id = f.dlg();
bool ok = true;
switch (id)
{
case 211:
if (e == fe_init)
load_themes();
if (e == fe_modify && is_running())
{
const int new_theme = atoi(f.get());
if (new_theme != _cur_theme)
apply_theme();
}
break;
case 217:
if (e == fe_init || e == fe_modify)
_icons->force_update();
break;
case DLG_OK:
if (e == fe_button)
{
stop_run(K_CTRL+'R');
return false;
}
break;
case DLG_SAVEREC:
if (e == fe_button)
{
stop_run(K_ENTER);
return false;
}
break;
case DLG_NEWREC:
if (e == fe_button)
{
TString80 name = user();
xvt_dm_post_string_prompt(TR("Nome del tema"), name.get_buffer(), 16);
if (name.full())
{
name.trim();
name.upper();
name.insert("Theme_");
{
TConfig ini(CONFIG_GUI, name);
save_colors(ini);
}
load_themes();
}
return false;
}
break;
case DLG_DELREC:
if (e == fe_button)
{
TList_field& themes = lfield(211);
const int pos = atoi(themes.get());
bool can_delete = pos > 2;
if (can_delete) // Tema non standard
{
TToken_string values = themes.get_values();
TString name = values.get(pos);
bool done = yesno_box(FR("Confermare la cancellazione del tema %s"), name.get_buffer());
if (done)
{
name.insert("Theme_");
TConfig ini(CONFIG_GUI, name);
if (ini.new_paragraph())
done = can_delete = false;
else
ini.remove_all();
}
if (done)
load_themes();
}
if (!can_delete)
error_box(TR("Tema non cancellabile"));
return false;
}
break;
case DLG_USER:
if (e == fe_button)
{
XVT_FNTID fontid = xvt_font_create();
TString256 fd = get_font_desc();
if (fd.full())
xvt_font_deserialize(fontid, fd);
else
xvt_font_copy(fontid, xvtil_default_font(), XVT_FA_ALL);
if (xvt_dm_post_font_sel(win(), fontid, NULL, 0))
{
xvt_font_serialize(fontid, fd.get_buffer(), fd.size());
set_font_desc(fd);
_preview->force_update();
}
xvt_font_destroy(fontid);
return false;
}
break;
case 212:
if (e == fe_init)
colors2mask(); else
if (e == fe_modify)
mask2colors();
break;
default:
break;
}
return ok;
}
TColor_mask::TColor_mask()
: TAutomask("ba0200a"), _cur_theme(0)
{
TConfig color(CONFIG_GUI, "Colors");
_color = color.list_variables();
set(213, CAMPI_SCAVATI ? "X" : "");
set(214, NATIVE_CONTROLS ? "X" : "");
set(215, ADVANCED_GRAPHICS ? "X" : "");
set(216, color.get_int("TreeView"));
_preview = new TPreview_panel(1, 10, -1, 8, this);
_icons = new TPreview_icons(1, 10, -2, -2, this);
const int sz = color.get_int("ToolSize");
set(217, (sz-16)/8);
set(218, EASY_RIDER ? "X" : "");
set(219, TOOL_TEXT ? "X" : "");
set(220, ENTER_AS_TAB ? "X" : "");
set(221, TMenuitem::always_run_fullscreen() ? "X" : "");
}
void TColor_mask::save_colors(TConfig& colors)
{
FOR_EACH_ASSOC_STRING(_color, obj, key, str)
colors.set(key, str);
colors.set("Campi3D", get_bool(213) ? "X" : "");
colors.set("NativeControls", get_bool(214) ? "X" : "");
colors.set("AdvancedGraphics", get_bool(215) ? "X" : "");
colors.set("TreeView", get_int(216));
const int sz = get_int(217);
colors.set("ToolSize", 16+sz*8);
colors.set("EasyRider", get_bool(218) ? "X" : "");
colors.set("ToolText", get_bool(219) ? "X" : "");
colors.set("EnterAsTab", get_bool(220) ? "X" : "");
colors.set("RunModal", get_bool(221) ? "X" : "");
}
void TColor_mask::save_colors()
{
TConfig colors(CONFIG_GUI, "Colors");
save_colors(colors);
TMenuitem::always_run_fullscreen(get_bool(221));
}
const TString& TColor_mask::get_font_desc() const
{
const TObject* s = ((TColor_mask*)this)->_color.objptr("FontDesc");
return s != NULL ? *(TString*)s : (const TString&)EMPTY_STRING;
}
COLOR TColor_mask::get_color_entry(const char* name) const
{
COLOR c = COLOR_INVALID;
const TObject* s = ((TColor_mask*)this)->_color.objptr(name);
if (s)
{
TToken_string colore(*(TString*)s, ',');
const byte r = (byte)colore.get_int();
const byte g = (byte)colore.get_int();
const byte b = (byte)colore.get_int();
c = RGB2COLOR(r, g, b);
}
return c;
}
void TColor_mask::set_color_entry(const char* name, COLOR col)
{
TString* s = (TString*)_color.objptr(name);
if (s == NULL)
{
s = new TString(15);
_color.add(name, s);
}
s->format("%d,%d,%d", XVT_COLOR_GET_RED(col), XVT_COLOR_GET_GREEN(col), XVT_COLOR_GET_BLUE(col));
}
void TColor_mask::set_font_desc(const TString& fd)
{
_color.add("FontDesc", fd, true);
}
const char* TColor_mask::cid2name(short cid) const
{
const int colors = 13;
const char* name[colors] = { "MaskBack", "MaskLight", "MaskDark",
"Normal", "NormalBack", "RequiredBack",
"Focus", "FocusBack",
"Disabled", "DisabledBack",
"ButtonBack", "ButtonLight", "ButtonDark" };
const int i = cid < DLG_USER ? cid : cid - 101;
CHECK(i >= 0 && i < colors, "Invalid color id");
return name[i];
}
COLOR TColor_mask::cid2color(short cid) const
{
COLOR color[] = { XVT_MAKE_COLOR(201,194,188), COLOR_WHITE, COLOR_GRAY,
COLOR_BLACK, COLOR_WHITE, blend_colors(COLOR_WHITE, COLOR_YELLOW, 0.60),
COLOR_BLACK, COLOR_YELLOW,
COLOR_DKGRAY, COLOR_LTGRAY,
COLOR_LTGRAY, COLOR_WHITE, COLOR_GRAY };
const int i = cid < DLG_USER ? cid : cid - 101;
CHECK(i >= 0 && i < 13, "Invalid color id");
return color[i];
}
COLOR TColor_mask::cid2syscolor(short cid, const XVT_COLOR_COMPONENT* cc) const
{
int entry[] = { XVT_COLOR_BACKGROUND, XVT_COLOR_BLEND, XVT_COLOR_BORDER,
XVT_COLOR_FOREGROUND, XVT_COLOR_BACKGROUND, XVT_COLOR_BACKGROUND,
XVT_COLOR_HIGHLIGHT, XVT_COLOR_SELECT,
XVT_COLOR_BLEND, XVT_COLOR_BORDER,
XVT_COLOR_BACKGROUND, XVT_COLOR_BLEND, XVT_COLOR_BORDER };
const unsigned int component = entry[cid < DLG_USER ? cid : cid-101];
for (int i = 0; cc[i].type != XVT_COLOR_NULL; i++) if (cc[i].type == component)
{
switch (cid)
{
case 105: return COLOR_WHITE;
case 106: return blend_colors(cid2syscolor(105, cc), cid2syscolor(108, cc), 0.60);
default : return cc[i].color;
}
}
return COLOR_BLACK;
}
///////////////////////////////////////////////////////////
// Menu application
///////////////////////////////////////////////////////////
bool TMenu_application::test_assistance_year() const
{
return true;
}
bool TMenu_application::menu_item_handler(TMask_field&f, KEY k)
{
if (k == K_SPACE)
{
app()._menu.select(f.dlg()-101);
f.set_focusdirty(false);
return f.mask().stop_run(K_AUTO_ENTER);
}
return true;
}
bool TMenu_application::menu_find_handler(TMask_field&f, KEY k)
{
if (k == K_TAB && f.focusdirty() && !f.empty())
{
const TString& v = f.get();
if (app()._menu.find_string(v))
{
f.set_focusdirty(false);
return f.mask().stop_run(K_F9);
}
else
{
beep();
return false;
}
}
return true;
}
int TMenu_application::do_level()
{
const TSubmenu& curr = _menu.current();
const int bwidth = 20;
TPicture_mask mask(curr.caption(), 0, 0, curr, 0, 0);
CHECK(_mask == NULL, "Two masks are better than one?");
_mask = &mask;
const int ampiezza = 51;
const int margin = (mask.columns()-80) / 2;
const int x = mask.columns() - ampiezza -margin;
int y = 1;
TString caption;
for (int i = 0; i < curr.items(); i++, y++)
{
const TMenuitem& item = curr[i];
caption = item.caption();
if (item.is_submenu() && caption.right(3) != "...")
caption << "...";
mask.add_static(-1, 0, caption, x+4, y);
const short id = 100+y;
mask.add_button(id, 0, "", x, y, 1, 1, "", BMP_STOPREC);
mask.set_handler(id, menu_item_handler);
if (item.disabled())
mask.disable(id);
}
mask.add_static(DLG_NULL, 0, PR("Cerca"), x, -4);
TEdit_field& ef = mask.add_string(DLG_USER, 0, "", x, -3, 50, "", ampiezza - 2);
ef.set_handler(menu_find_handler);
const int bottone = ampiezza / 3;
const int spazio = (ampiezza - bottone * 2) / 3;
const bool top = _menu.at_top();
mask.add_button(DLG_QUIT, 0, PR("Fine"), x + spazio, -1, bottone, 2);
if (!top)
mask.add_button(DLG_CANCEL, 0, PR("Menu precedente"), x + spazio * 2 + bottone, -1, bottone, 2);
mask.first_focus(101+_menu.selected());
const int k = mask.run();
_mask = NULL;
int m = 0;
switch (k)
{
case K_ESC:
_menu.pop();
m = -1;
break;
case K_QUIT:
mask.reset();
m = -2;
break;
case K_F9:
case K_CTRL+'R':
m = 0;
break;
default:
m = _menu.selected() + 1; // Sempre > 0
break;
}
return m;
}
void TMenu_application::test_temp()
{
TFilename dir; dir.tempdir(); // Directory temporanea
dir.add("*");
TString_array files;
const int count = list_files(dir, files);
if (count > 0 && yesno_box(TR("Cancellare tutti i file temporanei in %s?"), dir.path()))
{
TProgind bar(count, TR("Cancellazione file temporanei"), true, true);
for (int i = count-1; i >= 0; i--)
{
bar.addstatus(1);
if (bar.iscancelled())
break;
const char* e = files.row(i);
::remove(e);
}
}
}
HIDDEN bool pwd_handler(TMask_field& fld, KEY key)
{
if (key == K_F8)
{
TMask& m = fld.mask();
TString pwd;
TString usr = dongle().administrator(&pwd);
TLocalisamfile users(LF_USER);
users.put(USR_USERNAME, usr);
users.read();
pwd = decode(users.get(USR_PASSWORD));
m.set(F_USER, usr);
m.set(F_PASSWORD, pwd);
m.stop_run(K_ENTER);
}
return true;
}
HIDDEN bool user_mask_handler(TMask& mask, KEY key)
{
if (key == K_ENTER)
mask.stop_run(key);
return true;
}
void TMenu_application::reload_images()
{
_menu.reload_images();
}
bool TMenu_application::ask_user_password(TString& utente)
{
bool ok = false;
// Disabilita le voci di personalizzazione
enable_options_menu(false);
TMask m("ba0100a");
m.set_handler(user_mask_handler);
if (is_power_station())
{
m.set_handler(F_USER, pwd_handler);
m.set_handler(F_PASSWORD, pwd_handler);
}
m.set(F_USER, utente);
m.first_focus(F_PASSWORD);
TEdit_field& e = m.efield(F_USER);
e.browse()->set_filter("ISGROUP!=\"X\"");
TLocalisamfile& users = e.browse()->cursor()->file();
TString pwd;
for (int i = 0; i < 3 && !ok; i++)
{
if (utente.not_empty() && utente != dongle().administrator())
{
m.set(F_USER, utente);
m.first_focus(F_PASSWORD);
}
if (m.run() == K_ESC)
break;
utente = m.get(F_USER);
TString pwd;
users.put(USR_USERNAME, utente);
if (users.read() == NOERR)
{
pwd = decode(users.get(USR_PASSWORD));
}
else
{
// Creo l'amministratore se necessario
users.zero();
if (utente == dongle().administrator(&pwd))
{
users.put(USR_USERNAME, utente);
users.put(USR_USERDESC, "Amministratore");
users.put(USR_PASSWORD, encode(pwd));
users.write();
}
else
utente.cut(0);
}
const TString& pass = m.get(F_PASSWORD);
ok = utente.full() && pwd == pass;
if (ok)
{
if (users.get_bool(USR_CONNECTED))
{
ok = yesno_box("%s\n%s",
TR("L'utente risulta essere gi<67> collegato"),
TR("Si desidera continuare ugualmente?"));
}
}
else
{
error_box(TR("Utente e/o password errata: fare attenzione alle maiuscole"));
m.reset(F_PASSWORD);
}
}
if (ok && users.curr().exist(USR_DATAPWD))
{
const long expiration = ini_get_int(CONFIG_STUDIO, "Main", "PasswordExpiration");
bool runba = expiration > 0;
while (runba)
{
runba = users.get(USR_PASSWORD).empty();
if (!runba)
{
const TDate oggi(TODAY);
const TDate datapwd = users.get_date(USR_DATAPWD);
if (datapwd.ok())
runba = expiration < (oggi-datapwd); // Password scaduta
else
{
// Scrivi la data se necessario
users.put(USR_DATAPWD, oggi);
users.rewrite();
}
}
if (runba)
{
warning_box(TR("E' necessario inserire una nuova password"));
user() = utente;
TExternal_app app("ba1 -3");
app.run();
users.reread();
}
}
}
// Abilita le voci di personalizzazione
enable_options_menu(true);
return ok;
}
// Testa stato utente: 0 inesistente; 1 = esiste; 2 connesso; 4 conversione in corso
// ATTENZIONE: non usare mai cache() in ba0!
int TMenu_application::get_user_status(const char* usr) const
{
CHECK(usr && *usr, "Utente nullo");
int status = 0;
if (prefix_valid())
{
TLocalisamfile utonti(LF_USER);
utonti.put(USR_USERNAME, usr);
status = utonti.read() == NOERR;
if (status)
{
if (utonti.get_bool(USR_CONNECTED))
status |= 2;
if (dongle().administrator() == usr && utonti.get(USR_AUTSTR) == "CONVERTING")
status |= 4;
}
}
else
{
// Senza file aperti questo e' il massimo che posso fare
status = dongle().administrator() == usr;
}
return status;
}
bool TMenu_application::set_user_status(const char* usr, int status) const
{
CHECK(usr && *usr, "Utente nullo");
bool ok = false;
if (prefix_valid())
{
TLocalisamfile utonti(LF_USER);
utonti.put(USR_USERNAME, usr);
if (utonti.read(_isequal, _lock) == NOERR)
{
utonti.put(USR_CONNECTED, status & 2 ? "X" : "");
ok = utonti.rewrite() == NOERR;
}
}
if (status & 2)
{
// Memorizza utente per riproporlo la prossima volta
TConfig campo_ini(CONFIG_INSTALL, "Main");
campo_ini.set("User", usr);
}
return ok;
}
bool TMenu_application::check_user()
{
bool ok = dongle().type() == _no_dongle;
if (!ok)
{
TString utente = user();
if (_mask == NULL) // Primo login della sessione;
{
TConfig campo_ini(CONFIG_INSTALL, "Main");
const bool use_system_user = campo_ini.get_bool("AutoLogin");
if (use_system_user)
ok = !cache().get(LF_USER, utente).empty();
}
if (!ok)
ok = ask_user_password(utente);
if (ok)
{
const TString& autstr = cache().get(LF_USER, dongle().administrator(), USR_AUTSTR);
if (autstr == "CONVERTING")
{
TString msg; msg << TR("E' in corso una conversione archivi") << ":\n";
if (utente == dongle().administrator())
{
msg << TR("Si desidera continuare ugualmente?");
ok = yesno_box(msg);
}
else
{
msg << TR("Accesso negato.");
ok = error_box(msg);
}
}
if (ok)
{
dongle().logout();
user() = utente;
ok = get_serial_number() >= 0;
if (!ok)
error_box(TR("Probabilmente <20> stato superato il numero massimo di utenti"));
}
if (ok)
set_user_status(utente, 3); // Esistente e connesso (1 | 2 = 3)
}
}
if (ok)
{
set_perms(); // Aggiorna permessi utente
customize_colors(); // Aggiorna set di colori
reload_images(); // Ritrasparentizza immagini e abilitazioni alberi
xvt_dwin_invalidate_rect(TASK_WIN, NULL); // Ridisegna sfondo
load_preferences(); // Aggiorna menu preferiti
test_temp(); // Cancella file temporanei
}
return ok;
}
HIDDEN int compare_version(const char* v1, int p1, const char* v2, int p2)
{
TString16 ver1(v1), ver2(v2);
ver1.trim();
if (ver1.len() == 4)
ver1.insert((v1[0] == '9') ? "19" : "20", 0);
ver2.trim();
if (ver2.len() == 4)
ver2.insert((v2[0] == '9') ? "19" : "20", 0);
int res = ver1.compare(ver2, -1, true);
if (res == 0)
res = p1 - p2;
return res;
}
static int get_module_version(TConfig& cfg, void* jolly)
{
const TString& p = cfg.get_paragraph();
if (p.len() == 2)
{
TAssoc_array& map = *(TAssoc_array*)jolly;
TToken_string* tok = new TToken_string(15);
*tok = cfg.get("Versione");
tok->add(cfg.get("Patch"));
map.add(p, tok);
}
return false;
}
bool TMenu_application::copy_setup(const TString& remote_path)
{
bool ok = false;
const TFilename local_setupdir = "setup";
TFilename remote_setupdir = remote_path;
remote_setupdir.add(local_setupdir.name());
//controlla se esiste la directory;<3B> necessario in quanto se <20> una vecchia 4.0 potrebbe non esserci
if (remote_setupdir.exist())
{
remote_setupdir.add("*.*");
TString_array ar;
list_files(remote_setupdir, ar);
if (!ar.empty())
{
make_dir(local_setupdir);
ok = true;
TFilename strsrc, strdst;
FOR_EACH_ARRAY_ROW (ar, i, row)
{
strsrc = *row;
strdst = local_setupdir;
strdst.add(strsrc.name());
//se la copia dei files si inchioda esce
if (!fcopy(strsrc, strdst))
{
ok = false;
break;
}
} //FOR_EACH_ARRAY...
} //if(!ar.empty...
} //if(remote_setupdir...
return ok;
}
bool TMenu_application::test_programs()
{
TToken_string dangerous;
int update_needed = 0;
bool is_client = false;
bool sy_needed = false;
//parentesi necessaria per richiudere subito il .ini!
{
TConfig prawin(CONFIG_INSTALL, "Main");
const int type = prawin.get_int("Type");
is_client = type == 3 || prawin.get_bool("TestPrograms");
}
TString msg = TR("I seguenti moduli devono essere aggiornati prima dell'utilizzo:\n");
if (is_client)
{
TConfig install("install.ini", "Main");
TFilename remote_name = install.get("DiskPath");
remote_name.add("install.ini");
if (remote_name.exist())
{
TProgind pi(3, TR("Controllo aggiornamento programmi"), false, true);
TConfig remote_install(remote_name, "Main");
remote_install.write_protect();
TAssoc_array my_modules, his_modules;
pi.addstatus(1);
install.for_each_paragraph(get_module_version, &my_modules);
pi.addstatus(1);
remote_install.for_each_paragraph(get_module_version, &his_modules);
pi.addstatus(1);
//giro su tutti i moduli che sono sul server
const TDongle& chiavetta = dongle();
FOR_EACH_ASSOC_STRING(his_modules, h, str_code, str_tok)
{
//per prima cosa controlla se deve aggiornare SY e/o BA
const TString4 code = str_code;
if (code == "sr")
continue; // Un client non pu<70> aggiornare il modulo server!
int module = 0;
if (code != "sy" && code != "ba")
module = chiavetta.module_name2code(code);
if (chiavetta.active(module) && chiavetta.shown(module))
{
//const TString4 code = dongle().module_code2name(module);
TToken_string* mytok = (TToken_string*)my_modules.objptr(code);
TToken_string* histok = (TToken_string*)his_modules.objptr(code);
const TString16 v1 = mytok ? mytok->get(0) : "";
const int p1 = mytok ? mytok->get_int() : 0;
const TString16 v2 = histok ? histok->get(0) : "";
const int p2 = histok ? histok->get_int() : 0;
if (!v1.blank() && compare_version(v1, p1, v2, p2) < 0)
{
// Non disabilitare mai il modulo base! Se non funzionasse qualcosa (vedi anno di assistenza)...
//...non lascierebbe funzionare nulla!!!!
if (module > 0)
dangerous.add(code);
else
{
if (code == "sy")
sy_needed = true;
}
if (msg.len() < 200)
{
TString name;
if (code == "sy")
name = TR("Sistema");
else
name = chiavetta.module_code2desc(module);
if (update_needed > 0)
msg << ", ";
msg << name;
}
else
{
if (msg.right(1) != ".")
msg << ",etc.";
}
update_needed++;
} //if (!v1.blank()...
} //if (chiavetta.active(module...
} //FOR_EACH_ASSOC_STR
} //if(remote_name.exist()...
if (update_needed > 0 && yesno_box(msg))
{
//copia il contenuto della setup del server nella setup del client
if (sy_needed && copy_setup(remote_name.path()))
{
//mette il flag di installing
set_installing_flag();
//lancia setup in modalita' aggiornamento client e si suicida! (banzai!!)
TExternal_app app("setup\\setup.exe -uc");
app.run(true, 0, false);
}
else //lancia l'installazione moduli alla vecchia maniera (e' una vecchia 4.0)
{
TExternal_app app("ba1 -6 /uADMIN");
app.run(true, 0, false);
}
//se lancia un'installazione->esce!!!
return false;
} //(if(update_needed>0...
} //if(is_client..
_menu.set_dangerous_modules(dangerous);
return true;
}
bool TMenu_application::user_create()
{
disable_menu_item(M_FILE_PRINT); // Questa voce di menu non serve per ora
if (dongle().type() == _no_dongle)
warning_box(TR("ATTENZIONE\nQuesto programma <20> in versione dimostrativa.\n"
"Esso funzionera' per circa due ore al giorno con un numero limitato di registrazioni."));
if (!check_user())
return false;
if (!TApplication::test_assistance_year())
{
TExternal_app app("ba1 -4");
app.run();
}
if (!test_programs())
return false;
if (!_menu.ok())
{
TWait_cursor hourglass;
TFilename menu = _menuname;
menu.ext("men");
_menu.read(menu);
update_preferred_tree();
}
return true;
}
void TMenu_application::deconnect_user()
{
if (get_user_status(user()) & 2) // Se e' connesso
set_user_status(user(), 1); // Sconnettilo
}
bool TMenu_application::destroy()
{
deconnect_user();
return true;
}
void TMenu_application::main_loop()
{
bool run = user_create();
while (run)
{
int m = 0;
switch (_tree_view)
{
case 1: m = do_tree(); break;
case 2: m = do_explore(); break;
case 3: m = do_outlook(); break;
default: m = do_level(); break;
}
if (m > 0)
_menu.perform();
else
run = m >= -1;
if (installing()) //esce dal ciclo se ha lanciato una installazione moduli
break;
}
}
void enable_options_menu(bool on)
{
const WINDOW tw = TASK_WIN;
xvt_menu_set_item_enabled(tw, M_FILE_NEW, on); // Cambio ditta
xvt_menu_set_item_enabled(tw, M_FILE_PG_SETUP, on); // Imposta Stampante
for (int i = 2; i <= 7; i++) // Menu opzioni
xvt_menu_set_item_enabled(tw, MENU_ITEM_ID(i), on);
xvt_menu_update(tw);
}
bool TMenu_application::choose_colors()
{
enable_options_menu(false);
bool update_needed = false;
KEY key = K_CTRL+'R';
while (key == K_CTRL+'R')
{
TColor_mask cm;
key = cm.run();
if (key == K_ENTER || key == K_CTRL+'R') // Salva o Applica
{
_tree_view = cm.get_int(216); // Aggiorna stile menu
cm.save_colors(); // Aggiorna config
customize_colors(); // Aggiorna set di colori
reload_images(); // Aggiorna bitmaps del menu
// Ridisegna sfondo
TTemp_window tw(TASK_WIN);
tw.force_update();
update_needed = true;
}
}
// Provoca chiusura forzata del menu
if (update_needed && _mask != NULL)
_mask->stop_run(K_CTRL + 'R');
enable_options_menu(true);
return key == K_ENTER;
}
HIDDEN bool browse_file_handler(TMask_field& f, KEY k)
{
bool ok = true;
if (k == K_F9)
{
TFilename n = f.get(); n.ext("exe");
FILE_SPEC fs; xvt_fsys_convert_str_to_fspec(n, &fs);
//DIRECTORY dir; xvt_fsys_get_dir(&dir);
const int err = xvt_dm_post_file_open(&fs, TR("Selezione programma"));
//xvt_fsys_set_dir(&dir);
if (err == FL_OK)
{
xvt_fsys_convert_fspec_to_str(&fs, n.get_buffer(), n.size());
f.set(n);
}
}
if (k == K_TAB && f.focusdirty())
{
TFilename infile(f.get());
if (infile.not_empty())
{
TFilename outfile;
if (!infile.search_in_path(outfile))
{
if (*infile.ext() == '\0')
infile.ext("exe");
if (!infile.search_in_path(outfile))
ok = error_box("Il programma %s non esiste!", (const char*)infile);
}
}
}
return ok;
}
HIDDEN bool link_notify(TSheet_field& s, int r, KEY k)
{
bool ok = true;
if (k == K_INS)
{
ok = s.items() < 29; // Accetta 29 righe al massimo
}
return ok;
}
bool TMenu_application::choose_editors()
{
enable_options_menu(false);
TConfig link(CONFIG_GUI, "Link");
TMask* msk = new TMask("ba0300a");
TMask& m = *msk;
TSheet_field& sheet = m.sfield(201);
sheet.set_notify(link_notify);
TMask& sm = sheet.sheet_mask();
sm.set_handler(102, browse_file_handler);
TAssoc_array& var = (TAssoc_array&)link.list_variables();
FOR_EACH_ASSOC_STRING(var, obj, key, str)
{
TToken_string& row = sheet.row(-1);
if (strlen(key) <= 3)
{
row = key;
row.lower();
row.add(str);
}
}
sheet.rows_array().sort();
if (m.run() == K_ENTER)
{
link.remove_all();
FOR_EACH_SHEET_ROW_BACK(sheet, r, row)
{
TString16 ext = row->get(0);
if (!ext.blank())
{
ext.lower();
TFilename prg = row->get();
link.set(ext, prg);
}
}
}
delete msk;
enable_options_menu(true);
return true;
}
HIDDEN int dir_sort(const TObject** d1, const TObject** d2)
{
const TString& s1 = (const TString&)**d1;
const TString& s2 = (const TString&)**d2;
return xvt_str_compare_ignoring_case(s1, s2);
}
HIDDEN bool study_handler(TMask_field& f, KEY k)
{
bool ok = true;
if (f.to_check(k))
{
TFilename path(f.get());
path.add("com");
path.add("dir.gen");
if (!path.exist() || path.find(' ') >= 0)
ok = f.error_box("%s %s", (const char*)f.get(), TR("non e' uno studio valido!"));
} else
if (k == K_F9)
{
TFilename str = firm2dir(-1);
for (int i = str.len()-2; i > 0; i--)
{
if (str[i] == '\\' || str[i] == '/')
{
str.cut(i);
break;
}
}
str.add("*");
SLIST dirs = xvt_fsys_list_files(DIR_TYPE, str.get_buffer(), true);
TFilename dirgen;
TArray_sheet sht(-1, -1, 78, 16, TR("Scelta studio"), HR("Studio@76"));
for (SLIST_ELT e = xvt_slist_get_first(dirs); e; e = xvt_slist_get_next(dirs, e))
{
const char* f = xvt_slist_get(dirs, e, NULL);
dirgen = f;
if (dirgen.find(' ') < 0)
{
dirgen.add("com/dir.gen");
if (dirgen.exist())
sht.add(f);
}
}
xvt_slist_destroy(dirs);
sht.rows_array().TArray::sort(dir_sort);
if (sht.run() == K_ENTER)
f.set(sht.row(-1)); // -1 = selected row
}
return ok;
}
bool TMenu_application::choose_study()
{
// Disbilita le voci di personalizzazione
enable_options_menu(false);
TMask m(TR("Scelta studio"), 1, 62, 4);
m.add_button(DLG_OK, 0, "", -12, -1, 10, 2);
m.add_button(DLG_CANCEL, 0, "", -22, -1, 10, 2);
m.add_string(DLG_USER, 0, PR("Studio "), 1, 1, 50, "B");
m.set_handler(DLG_USER, study_handler);
m.set(DLG_USER, prefix().get_studio());
bool ok = m.run() == K_ENTER;
if (ok)
{
deconnect_user();
prefix().set_studio(m.get(DLG_USER));
ok = check_user();
if (ok)
{
_menu.set_firm(0);
_mask->stop_run(K_F9); // Ricarica maschera
}
else
{
dispatch_e_menu(M_FILE_QUIT); // Termina applicazione gracefully
}
}
// Abilita le voci di personalizzazione
enable_options_menu(true);
return ok;
}
long TMenu_application::handler(WINDOW win, EVENT* ep)
{
long ret = TApplication::handler(win, ep);
if (ep->type == E_FONT)
{
if (_mask != NULL)
_mask->stop_run(K_CTRL + 'R');
}
return ret;
}
///////////////////////////////////////////////////////////
// Tree view implementation
///////////////////////////////////////////////////////////
bool TMenu_application::tree_handler(TMask_field& f, KEY k)
{
if (k == K_CTRL + K_SPACE)
{
TTree_field& tf = (TTree_field&)f;
TMenu_tree& mt = *(TMenu_tree*)tf.tree();
const TMenuitem& mi = mt.curr_item();
mi.perform();
if (mi.is_submenu())
{
TPicture_mask& pm = (TPicture_mask&)f.mask();
if (mt.expanded())
{
TMenu& menu = mt.curr_submenu().menu();
pm.set_current(menu.current());
}
pm.force_update();
}
}
return true;
}
TTree_field& TMenu_application::tree_field() const
{
CHECK(_tree_view > 0, "No menu tree");
return _mask->tfield(_tree_view == 3 ? 101 : 301);
}
void TMenu_application::select_tree_current()
{
TTree_field& tf = tree_field();
synchronize_tree_field(tf);
tf.set_focus();
}
bool TMenu_application::tree_find_handler(TMask_field&f, KEY k)
{
if (k == K_TAB && f.focusdirty() && !f.empty())
{
const TString& v = f.get();
TTree_field& tf = app().tree_field();
TMenu_tree& mt = *(TMenu_tree*)tf.tree();
if (mt.find_string(v))
app().select_tree_current();
else
beep();
}
return true;
}
bool TMenu_application::tree_shrink_handler(TMask_field&f, KEY k)
{
if (k == K_SPACE)
{
TTree_field& tf = app().tree_field();
TMenu_tree& mt = (TMenu_tree&)*tf.tree();
mt.shrink_all();
mt.goto_root();
app().select_tree_current();
}
return true;
}
void TMenu_application::update_preferred()
{
MENU_ITEM* mm = xvt_menu_get_tree(TASK_WIN);
MENU_ITEM* mi;
for (mi = mm; mi != NULL && mi->tag != 0 && mi->tag != PREFERRED_MENU; mi++);
if (mi == NULL || mi->tag <= 0 || mi->child == NULL)
{
NFCHECK("Can't find Preferiti Menu");
return;
}
int i;
MENU_ITEM* pm = (MENU_ITEM*)xvt_mem_zalloc((_preferred.items()+4)*sizeof(MENU_ITEM));
memcpy(pm, mi->child, 3*sizeof(MENU_ITEM));
for (i = 0; i < 2; i++)
{
const char* src = mi->child[i].text;
pm[i].text = xvt_str_duplicate(src);
}
xvt_res_free_menu_tree(mi->child);
mi->child = pm;
for (i = -1; i < _preferred.items(); i++)
{
MENU_ITEM& m = pm[i+3];
if (i >= 0)
{
m.tag = MENU_ITEM_ID(50+i);
m.enabled = true;
const char* src = _preferred.row(i).get(0);
m.text = xvt_str_duplicate(src);
}
else
{
m.tag = -1;
m.separator = true;
}
}
xvt_menu_set_tree(TASK_WIN, mm);
xvt_menu_update(TASK_WIN);
xvt_res_free_menu_tree(mm);
update_preferred_tree();
}
void TMenu_application::update_preferred_tree()
{
TSubmenu* pref = _menu.find("MENU_PREFERITI");
if (pref != NULL)
{
TToken_string node(16, '.');
pref->destroy_items();
FOR_EACH_ARRAY_ROW(_preferred, i, row)
{
int slash = row->rfind('/');
if (slash < 0)
slash = row->rfind(row->separator());
node = row->mid(slash+1);
if (node.items() == 2)
{
const char* sub = node.get(0);
TSubmenu* sm = _menu.find(sub);
if (sm != NULL)
{
const int num = node.get_int(1);
if (num >= 0 && num < sm->items())
pref->add(new TMenuitem(sm->item(num)));
}
}
}
if (_tree_view == 3 && _mask != NULL)
{
TMask_field& ol = _mask->field(102);
ol.set_focusdirty(false);
ol.on_hit(); // fe_init
}
}
}
void TMenu_application::load_preferences()
{
TConfig cfg(CONFIG_GUI, "ba0");
_preferred.destroy();
for (int i = 0; ; i++)
{
TToken_string row = cfg.get("Preferred", NULL, i);
if (row.empty_items())
break;
_preferred.add(row);
}
update_preferred();
TMenuitem::always_run_fullscreen(cfg.get_bool("AlwaysFullScreen"));
_tree_view = cfg.get_int("TreeView", "Colors", -1, 3);
}
void TMenu_application::save_preferences()
{
TConfig cfg(CONFIG_GUI, "ba0");
int i;
for (i = 0; i < _preferred.items(); i++)
cfg.set("Preferred", _preferred.row(i), NULL, true, i);
cfg.set("Preferred", "", NULL, true, i);
}
void TMenu_application::add_to_preferred()
{
if (_mask == NULL) // Succede durante il login!
return;
if (_preferred.items() < 16) // Massimo numero di preferiti
{
TToken_string tok;
switch (_tree_view)
{
case 0:
{
const TMask_field& butt = _mask->focus_field();
const int index = butt.dlg() - 101;
if (index >= 0 && index < 16)
{
_menu.select(index);
tok = _menu.curr_item().caption();
tok.add(_menu.current().name());
tok << '.' << index;
}
}
break;
case 2:
{
TMenulist_field& mf = (TMenulist_field&)_mask->field(DLG_LIST);
mf.curr_item(tok);
}
break;
default:
{
TTree_field& tf = tree_field();
tf.goto_selected();
tf.tree()->get_description(tok);
TString id; tf.tree()->curr_id(id);
tok.add(id);
}
break;
}
if (tok.full() && tok.find("MENU_PREFERITI")<0 && _preferred.find(tok)<0)
{
_preferred.add(tok);
save_preferences();
update_preferred();
}
}
else
error_box(TR("Non e' possibile memorizzare piu' di %d preferenze"), _preferred.items());
}
class TPreferred_mask : public TAutomask
{
protected:
virtual bool on_field_event(TOperable_field& o, TField_event e, long jolly);
public:
TPreferred_mask() : TAutomask("ba0400a") { }
};
bool TPreferred_mask::on_field_event(TOperable_field& o, TField_event e, long jolly)
{
switch (o.dlg())
{
case F_PREF_SHEET:
switch (e)
{
case se_query_add:
return false;
case se_enter:
enable(F_PREF_UP, jolly > 0);
enable(F_PREF_DN, jolly < ((TSheet_field&)o).items()-1);
break;
default:
break;
}
break;
case F_PREF_UP:
if (e == fe_button)
{
TSheet_field& sf = sfield(F_PREF_SHEET);
const int r = sf.selected();
if (r > 0)
{
sf.rows_array().swap(r, r-1);
sf.select(r-1);
sf.force_update();
}
}
break;
case F_PREF_DN:
if (e == fe_button)
{
TSheet_field& sf = sfield(F_PREF_SHEET);
const int r = sf.selected();
if (r < sf.items()-1)
{
sf.rows_array().swap(r, r+1);
sf.select(r+1);
sf.force_update();
}
}
break;
case DLG_DELREC:
if (e == fe_button && jolly == 0) // Main delete button pressed
{
TSheet_field& sf = sfield(F_PREF_SHEET);
const int r = sf.selected();
if (r >= 0)
sf.destroy(r);
return false;
}
break;
default:
break;
}
return true;
}
void TMenu_application::manage_preferred()
{
TPreferred_mask* m = new TPreferred_mask;
TSheet_field& sf = m->sfield(F_PREF_SHEET);
sf.rows_array() = _preferred;
sf.force_update();
if (m->run() == K_ENTER)
{
_preferred = sf.rows_array();
save_preferences();
update_preferred();
}
delete m;
}
int TMenu_application::do_tree()
{
_menu.jumpto_root();
const TSubmenu& curr = _menu.current();
TPicture_mask mask(curr.caption(), 0, 0, curr, 0, 0);
CHECK(_mask == NULL, "Two masks are better than one?");
_mask = &mask;
const int margin = (mask.columns()-80) / 2;
const int twidth = mask.columns() - 51;
const int bwidth = (mask.columns() - twidth - 8);
TMenu_tree tree(_menu);
TTree_field& tree_fld = mask.add_tree(DLG_TREE, 0, 0, 0, twidth, -1);
tree_fld.set_tree(&tree);
tree_fld.set_handler(tree_handler);
const int inizio = twidth - margin + 2;
const int ampiezza = mask.columns() - inizio - margin;
const int bottone = ampiezza / 3;
const int spazio = (ampiezza - 2 * bottone) / 3;
mask.add_static(DLG_NULL, 0, PR("Cerca"), inizio + 2, -4);
TEdit_field& ef = mask.add_string(DLG_USER, 0, "", inizio + 2, -3, 50, "", ampiezza - 4);
ef.set_handler(tree_find_handler);
TButton_field& mf = mask.add_button(201, 0, PR("Menu Principale"), inizio + spazio * 2 + bottone, -1, bottone, 2);
mf.set_handler(tree_shrink_handler);
mask.add_button(DLG_QUIT, 0, PR("Fine"), inizio + spazio, -1, bottone, 2);
mask.first_focus(DLG_TREE);
KEY key = mask.run();
_mask = NULL;
return key == K_QUIT ? -2 : 0;
}
int TMenu_application::do_explore()
{
CHECK(_mask == NULL, "Two masks are better than one?");
_menu.jumpto_root();
TExplorer_mask mask(_menu);
_mask = &mask;
KEY key = mask.run();
_mask = NULL;
return key == K_QUIT ? -2 : 0;
}
int TMenu_application::do_outlook()
{
CHECK(_mask == NULL, "Two masks are better than one?");
TOutlook_mask mask(_menu);
_mask = &mask;
KEY key = mask.run();
_mask = NULL;
return key == K_QUIT ? -2 : 0;
}
bool TMenu_application::firm_change_enabled() const
{
return _mask != NULL; // Impedisci il cambio ditta durante il login
}
void TMenu_application::on_firm_change()
{
TConfig cfgs(CONFIG_STUDIO, "Main"); // Forza creazione STUDIO.INI copiandolo eventulamente da PRASSIS.INI
TConfig cfgd(CONFIG_DITTA, "ba"); // Forza creazione DITTA.INI copiandolo eventulamente da PRASSID.INI
}
bool TMenu_application::menu(MENU_TAG mt)
{
bool ok = true;
switch (mt)
{
case BAR_ITEM_ID(1): main_loop(); ok = false; break;
case MENU_ITEM_ID(2): choose_colors(); break;
case MENU_ITEM_ID(3): choose_editors(); break;
case MENU_ITEM_ID(4): choose_study(); break;
case MENU_ITEM_ID(5): add_to_preferred(); break;
case MENU_ITEM_ID(6): manage_preferred(); break;
case MENU_ITEM_ID(7):
if (check_user())
_mask->stop_run(K_CTRL + 'R'); // Ricarica maschera
break;
default:
if (mt >= MENU_ITEM_ID(50) && mt < MENU_ITEM_ID(50+_preferred.items()))
{
bool ok = false;
const int index = mt - MENU_ITEM_ID(50);
TToken_string node(_preferred.row(index).get(1), '/');
if (_tree_view != 0)
{
TMenu_tree& met = *(TMenu_tree*)tree_field().tree();
ok = node.items() == 1 ? met.find_leaf(node) : met.goto_node(node);
if (ok)
{
select_tree_current();
if (met.curr_item().is_program())
tree_field().on_key(K_CTRL+K_SPACE); // Esegue subito il programma
}
}
else
{
TToken_string mi(node.get(-2), '.');
const char* sub = mi.get(0);
TSubmenu* sm = _menu.find(sub);
if (sm && _menu.jumpto(sm))
{
ok = true;
_menu.select(mi.get_int());
_mask->stop_run(K_CTRL + 'R');
}
}
if (!ok)
beep();
}
break;
}
return ok;
}
int ba0100(int argc, char** argv)
{
TApplication::check_parameters(argc, argv);
TString& u = user();
if (u.blank())
{
TConfig campo_ini(CONFIG_INSTALL, "Main");
const bool su = campo_ini.get_bool("AutoLogin");
if (su) // usa utente di windows
{
xvt_sys_get_user_name(u.get_buffer(), u.size()+1);
u.upper();
if (u.compare("Administrator", -1, true) == 0) // Converti amministratore
u = dongle().administrator();
}
if (u.blank())
u = campo_ini.get("User"); // Ultimo utente usato
if (u.blank())
u = dongle().administrator(); // Usa amministratore come extrema ratio
}
TFilename menu = (argc < 2) ? MEN_FILE : argv[1];
if (menu.custom_path())
{
TMenu_application *ma = new TMenu_application(menu);
ma->run(argc, argv, TR("Menu Principale"));
delete ma;
}
else
error_box(FR("Non esiste il menu %s"), (const char*)menu);
return 0;
}