Grant a long-standing wish of Lars's: LyX now functions even if we have

no text classes for some reason (e.g., a corrupt textclass.lst). We
still give the user a chance to reconfigure (Bo's idea).

I wonder if we still really need to "restart LyX to make use of any
updated document class specifications". What would happen if we just
reloaded?


git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/trunk@34081 a592a061-630c-0410-9148-cb99ea01b6c8
This commit is contained in:
Richard Heck 2010-04-07 17:02:44 +00:00
parent 907df4570d
commit f9fa189e02
3 changed files with 73 additions and 107 deletions

View File

@ -99,86 +99,74 @@ LayoutFile & LayoutFileList::operator[](string const & classname)
// Reads LyX textclass definitions according to textclass config file
bool LayoutFileList::read()
{
bool success = false;
Lexer lex;
FileName const real_file = libFileSearch("", "textclass.lst");
LYXERR(Debug::TCLASS, "Reading textclasses from `" << real_file << '\'');
LYXERR(Debug::TCLASS, "Reading textclasses from `" << real_file << "'.");
if (real_file.empty()) {
lyxerr << "LayoutFileList::Read: unable to find "
"textclass file `"
<< to_utf8(makeDisplayPath(real_file.absFilename(), 1000))
<< "'. Exiting." << endl;
return false;
// This causes LyX to end... Not a desirable behaviour. Lgb
// What do you propose? That the user gets a file dialog
// and is allowed to hunt for the file? (Asger)
// more that we have a layout for minimal.cls statically
// compiled in... (Lgb)
}
if (!lex.setFile(real_file)) {
lyxerr << "LayoutFileList::Read: "
"lyxlex was not able to set file: "
<< real_file << endl;
}
if (!lex.isOK()) {
lyxerr << "LayoutFileList::Read: unable to open "
"textclass file `"
<< to_utf8(makeDisplayPath(real_file.absFilename(), 1000))
<< "'\nCheck your installation. LyX can't continue."
<< endl;
return false;
}
bool finished = false;
// Parse config-file
LYXERR(Debug::TCLASS, "Starting parsing of textclass.lst");
while (lex.isOK() && !finished) {
LYXERR(Debug::TCLASS, "\tline by line");
switch (lex.lex()) {
case Lexer::LEX_FEOF:
finished = true;
break;
default:
string const fname = lex.getString();
LYXERR(Debug::TCLASS, "Fname: " << fname);
if (!lex.next())
LYXERR0("LayoutFileList::Read: unable to find textclass file `"
<< makeDisplayPath(real_file.absFilename(), 1000)
<< "'.");
success = false;
} else if (!lex.setFile(real_file)) {
LYXERR0("LayoutFileList::Read: lyxlex was not able to set file: "
<< real_file << '.');
} else if (!lex.isOK()) {
LYXERR0("LayoutFileList::Read: unable to open textclass file `"
<< makeDisplayPath(real_file.absFilename(), 1000)
<< "'\nCheck your installation.");
} else {
// we have a file we can read.
bool finished = false;
LYXERR(Debug::TCLASS, "Starting parsing of textclass.lst");
while (lex.isOK() && !finished) {
LYXERR(Debug::TCLASS, "\tline by line");
switch (lex.lex()) {
case Lexer::LEX_FEOF:
finished = true;
break;
string const clname = lex.getString();
LYXERR(Debug::TCLASS, "Clname: " << clname);
if (!lex.next())
break;
string const desc = lex.getString();
LYXERR(Debug::TCLASS, "Desc: " << desc);
if (!lex.next())
break;
bool avail = lex.getBool();
LYXERR(Debug::TCLASS, "Avail: " << avail);
if (!lex.next())
break;
string const prereq = lex.getString();
LYXERR(Debug::TCLASS, "Prereq: " << prereq);
// This code is run when we have
// fname, clname, desc, prereq, and avail
LayoutFile * tmpl = new LayoutFile(fname, clname, desc, prereq, avail);
if (lyxerr.debugging(Debug::TCLASS)) {
// only system layout files are loaded here so no
// buffer path is needed.
tmpl->load();
}
classmap_[fname] = tmpl;
}
}
LYXERR(Debug::TCLASS, "End of parsing of textclass.lst");
default:
string const fname = lex.getString();
LYXERR(Debug::TCLASS, "Fname: " << fname);
if (!lex.next())
break;
string const clname = lex.getString();
LYXERR(Debug::TCLASS, "Clname: " << clname);
if (!lex.next())
break;
string const desc = lex.getString();
LYXERR(Debug::TCLASS, "Desc: " << desc);
if (!lex.next())
break;
bool avail = lex.getBool();
LYXERR(Debug::TCLASS, "Avail: " << avail);
if (!lex.next())
break;
string const prereq = lex.getString();
LYXERR(Debug::TCLASS, "Prereq: " << prereq);
// This code is run when we have
// fname, clname, desc, prereq, and avail
LayoutFile * tmpl = new LayoutFile(fname, clname, desc, prereq, avail);
if (lyxerr.debugging(Debug::TCLASS)) {
// only system layout files are loaded here so no
// buffer path is needed.
tmpl->load();
}
classmap_[fname] = tmpl;
} // end of switch
} // end of while loop
LYXERR(Debug::TCLASS, "End parsing of textclass.lst");
success = true;
} // end of else
// lyx will start with an empty classmap_, but only reconfigure is allowed
// in this case. This gives users a second chance to configure lyx if
// initial configuration fails. (c.f. bug 2829)
// LyX will start with an empty classmap_. This is OK because
// (a) we will give the user a chance to reconfigure (see bug 2829) and
// (b) even if that fails, we can use addEmptyClass() to get some basic
// functionality.
if (classmap_.empty())
lyxerr << "LayoutFileList::Read: no textclasses found!"
<< endl;
return true;
LYXERR0("LayoutFileList::Read: no textclasses found!");
return success;
}
@ -346,26 +334,10 @@ LayoutFileIndex defaultBaseclass()
if (LayoutFileList::get().haveClass("article"))
return string("article");
if (LayoutFileList::get().empty())
return string();
// we'll call it that, since this gives the user a chance to
// have a functioning document when things improve.
return string("article");
return LayoutFileList::get().classList().front();
}
// Reads the style files
bool LyXSetStyle()
{
LYXERR(Debug::TCLASS, "LyXSetStyle: parsing configuration...");
if (!LayoutFileList::get().read()) {
LYXERR(Debug::TCLASS, "LyXSetStyle: an error occured "
"during parsing.\n Exiting.");
return false;
}
LYXERR(Debug::TCLASS, "LyXSetStyle: configuration parsed.");
return true;
}
} // namespace lyx

View File

@ -29,10 +29,6 @@ namespace lyx {
class Layout;
/// Reads the style files
extern bool LyXSetStyle();
/// Index into LayoutFileList. Basically a 'strong typedef'.
class LayoutFileIndex {
public:

View File

@ -502,16 +502,16 @@ void LyX::execCommands()
// aknowledged.
// if reconfiguration is needed.
while (LayoutFileList::get().empty()) {
if (LayoutFileList::get().empty()) {
switch (Alert::prompt(
_("No textclass is found"),
_("LyX cannot continue because no textclass is found. "
"You can either reconfigure normally, or reconfigure using "
"default textclasses, or quit LyX."),
_("LyX will have minimal functionality because no textclasses "
"have been found. You can either try to reconfigure LyX normally, "
"try to reconfigure using only the defaults, or continue."),
0, 2,
_("&Reconfigure"),
_("&Use Default"),
_("&Exit LyX")))
_("&Use Defaults"),
_("&Continue")))
{
case 0:
// regular reconfigure
@ -523,8 +523,7 @@ void LyX::execCommands()
" --without-latex-config"));
break;
default:
lyx::dispatch(FuncRequest(LFUN_LYX_QUIT));
return;
break;
}
}
@ -762,10 +761,9 @@ bool LyX::init()
// Set the language defined by the user.
setRcGuiLanguage();
// Load the layouts
LYXERR(Debug::INIT, "Reading layouts...");
if (!LyXSetStyle())
return false;
// Load the layouts
LayoutFileList::get().read();
//...and the modules
theModuleList.read();