Hi!
Not my day today. The ids+maths-patch still has the compile errors. Here's the corrected one.
/Andreas
Index: src/paragraph.C =================================================================== RCS file: /cvs/lyx/lyx-devel/src/paragraph.C,v retrieving revision 1.380 diff -u -p -r1.380 paragraph.C --- src/paragraph.C 2004/10/07 15:21:03 1.380 +++ src/paragraph.C 2004/10/21 07:35:03 @@ -1338,7 +1338,7 @@ string Paragraph::getDocbookId() const InsetBase const * inset = getInset(i); InsetBase::Code lyx_code = inset->lyxCode(); if (lyx_code == InsetBase::LABEL_CODE) { - return static_cast<InsetCommand const *>(inset)->getContents(); + return sgml::cleanID(static_cast<InsetCommand const *>(inset)->getContents()); } } Index: src/sgml.C =================================================================== RCS file: /cvs/lyx/lyx-devel/src/sgml.C,v retrieving revision 1.15 diff -u -p -r1.15 sgml.C --- src/sgml.C 2004/05/14 15:47:35 1.15 +++ src/sgml.C 2004/10/21 07:35:03 @@ -12,17 +12,20 @@ #include <config.h> #include "support/std_ostream.h" +#include "support/lstrings.h" +#include "support/tostr.h" #include "paragraph.h" #include "sgml.h" +#include <map> + +using lyx::support::subst; using std::endl; using std::make_pair; using std::ostream; using std::pair; using std::string; - +using std::map; namespace sgml { @@ -138,4 +141,76 @@ unsigned int closeEnvTags(ostream & os, } +std::string cleanID(std::string const & orig, std::string const & allowed) +{ + // The standard DocBook SGML declaration only allows letters, + // digits, '-' and '.' in a name. + // Since users might change that declaration one has to cater + // for additional allowed characters. + // This routine replaces illegal characters by '-' or '.' + // and adds a number for uniqueness. + // If you know what you are doing, you can set allowed=="all" + // to disable this mangling. + + string::const_iterator it = orig.begin(); + string::const_iterator end = orig.end(); + + string content; + + if (allowed == "all") { + return orig; + } + + typedef map<string, string> MangledMap; + static MangledMap mangledNames; + static int mangleID = 1; + + MangledMap::const_iterator const known = mangledNames.find(orig); + if (known != mangledNames.end()) + return (*known).second; + + // make sure it starts with a letter + if (!isalpha(*it) && allowed.find(*it) >= allowed.size()) + content += "x"; + + bool mangle = false; + for (; it != end; ++it) { + char c = *it; + if (isalpha(c) || isdigit(c) || c == '-' || c == '.' || allowed.find(c) < allowed.size()) + content += c; + else if (c == '_' || c == ' ') { + mangle = true; + content += "-"; + } + else if (c == ':' || c == ',' || c == ';' || c == '!') { + mangle = true; + content += "."; + } + else { + mangle = true; + } + } + if (mangle) { + content += "-" + tostr(mangleID++); + } + else if (isdigit(content[content.size()-1])) { + content += "."; + } + + mangledNames[orig] = content; + + return content; +} + +std::string escapeEntities(std::string const & orig, char quote = '"') +{ + std::string result = subst(subst(orig,"&","&"),"<","<"); + if (quote == '"') + return subst(result, "\"", """); + else if (quote == '\'') + return subst(result,"'", "'"); + else + return result; +} } // namespace sgml Index: src/sgml.h =================================================================== RCS file: /cvs/lyx/lyx-devel/src/sgml.h,v retrieving revision 1.12 diff -u -p -r1.12 sgml.h --- src/sgml.h 2004/04/03 08:37:01 1.12 +++ src/sgml.h 2004/10/21 07:35:04 @@ -27,12 +27,12 @@ namespace sgml { */ std::pair<bool, std::string> escapeChar(char c); -/// FIXME +/// FIXME int openTag(std::ostream & os, lyx::depth_type depth, bool mixcont, std::string const & latexname, std::string const & latexparam = std::string()); -/// FIXME +/// FIXME int closeTag(std::ostream & os, lyx::depth_type depth, bool mixcont, std::string const & latexname); @@ -42,6 +42,12 @@ unsigned int closeEnvTags(std::ostream & std::string const & environment_inner_depth, std::string const & item_tag, lyx::depth_type total_depth); + +/// replaces illegal chars like ':' or '_' from SGML ID attributes +std::string cleanID(std::string const & orig, std::string const & allowed = std::string()); + +/// escapes & and < +std::string escapeEntities(std::string const & orig, char quote = '"'); } Index: src/insets/insetlabel.C =================================================================== RCS file: /cvs/lyx/lyx-devel/src/insets/insetlabel.C,v retrieving revision 1.95 diff -u -p -r1.95 insetlabel.C --- src/insets/insetlabel.C 2004/05/14 15:47:35 1.95 +++ src/insets/insetlabel.C 2004/10/21 07:35:13 @@ -20,6 +20,7 @@ #include "lyxtext.h" #include "paragraph.h" #include "pariterator.h" +#include "sgml.h" #include "frontends/LyXView.h" @@ -141,8 +142,8 @@ int InsetLabel::linuxdoc(Buffer const &, int InsetLabel::docbook(Buffer const &, ostream & os, - OutputParams const &) const + OutputParams const &) const { - os << "<!-- anchor id=\"" << getContents() << "\" -->"; + os << "<!-- anchor id=\"" << sgml::cleanID(getContents()) << "\" -->"; return 0; } Index: src/insets/insetref.C =================================================================== RCS file: /cvs/lyx/lyx-devel/src/insets/insetref.C,v retrieving revision 1.90 diff -u -p -r1.90 insetref.C --- src/insets/insetref.C 2004/09/25 12:26:06 1.90 +++ src/insets/insetref.C 2004/10/21 07:35:14 @@ -19,6 +19,7 @@ #include "gettext.h" #include "LaTeXFeatures.h" #include "outputparams.h" +#include "sgml.h" #include "frontends/LyXView.h" @@ -114,11 +115,11 @@ int InsetRef::docbook(Buffer const &, os OutputParams const & runparams) const { if (getOptions().empty() && runparams.flavor == OutputParams::XML) { - os << "<xref linkend=\"" << getContents() << "\" />"; + os << "<xref linkend=\"" << sgml::cleanID(getContents()) << "\"/>"; } else if (getOptions().empty()) { - os << "<xref linkend=\"" << getContents() << "\">"; + os << "<xref linkend=\"" << sgml::cleanID(getContents()) << "\">"; } else { - os << "<link linkend=\"" << getContents() + os << "<link linkend=\"" << sgml::cleanID(getContents()) << "\">" << getOptions() << "</link>"; } Index: src/mathed/math_hullinset.C =================================================================== RCS file: /cvs/lyx/lyx-devel/src/mathed/math_hullinset.C,v retrieving revision 1.153 diff -u -p -r1.153 math_hullinset.C --- src/mathed/math_hullinset.C 2004/10/17 20:06:35 1.153 +++ src/mathed/math_hullinset.C 2004/10/21 07:35:17 @@ -30,6 +30,7 @@ #include "lyx_main.h" #include "lyxrc.h" #include "outputparams.h" +#include "sgml.h" #include "textpainter.h" #include "undo.h" @@ -40,11 +41,15 @@ #include "graphics/PreviewImage.h" #include "graphics/PreviewLoader.h" +#include "support/lstrings.h" +#include "support/tostr.h" + #include <boost/bind.hpp> #include <sstream> using lyx::cap::grabAndEraseSelection; +using lyx::support::subst; using std::endl; using std::max; @@ -1122,7 +1127,6 @@ bool MathHullInset::getStatus(LCursor & #include "frontends/LyXView.h" #include "frontends/Dialogs.h" -#include "support/lstrings.h" #include "support/lyxlib.h" @@ -1342,25 +1346,45 @@ int MathHullInset::docbook(Buffer const name = "informalequation"; string bname = name; - if (! label(0).empty()) bname += " id=\"" + label(0)+ "\""; + if (!label(0).empty()) + bname += " id=\"" + sgml::cleanID(label(0)) + "\""; ms << MTag(bname.c_str()); + ostringstream ls; if (runparams.flavor == OutputParams::XML) { - ms << MTag("math"); - MathGridInset::mathmlize(ms); - ms << ETag("math"); - ms << MTag("alt role=\"tex\" "); - ostringstream ls; + ms << MTag("alt role=\"tex\" "); + // Workaround for db2latex: db2latex always includes equations with + // \ensuremath{} or \begin{display}\end{display} + // so we strip LyX' math environment WriteStream wi(ls, false, false); MathGridInset::write(wi); - ms << ls.str(); - ms << ETag("alt"); + ms << subst(subst(ls.str(), "&", "&"), "<", "<"); + ms << ETag("alt"); + ms << MTag("math"); + MathGridInset::mathmlize(ms); + ms << ETag("math"); } else { - ms << MTag("alt role=\"tex\" "); - res = latex(buf, ms.os(), runparams); - ms << ETag("alt"); - } - + ms << MTag("alt role=\"tex\""); + res = latex(buf, ls, runparams); + ms << subst(subst(ls.str(), "&", "&"), "<", "<"); + ms << ETag("alt"); + } + + ms << "<graphic fileref=\"eqn/"; + if ( !label(0).empty()) + ms << sgml::cleanID(label(0)); + else { + // Some arbitrary unique number for this os. + // Note that each call of math_hullinset::docbook() + // will increase the os position by at least 60 chars or more + ms << "anon"; + ms << tostr(os.tellp() / 40); + } + if (runparams.flavor == OutputParams::XML) + ms << "\"/>"; + else + ms << "\">"; + ms << ETag(name.c_str()); return ms.line() + res; } Index: src/mathed/ref_inset.C =================================================================== RCS file: /cvs/lyx/lyx-devel/src/mathed/ref_inset.C,v retrieving revision 1.46 diff -u -p -r1.46 ref_inset.C --- src/mathed/ref_inset.C 2004/04/18 19:57:58 1.46 +++ src/mathed/ref_inset.C 2004/10/21 07:35:17 @@ -21,6 +21,8 @@ #include "math_data.h" #include "math_factory.h" #include "math_support.h" +#include "outputparams.h" +#include "sgml.h" #include "frontends/LyXView.h" #include "frontends/Dialogs.h" @@ -131,17 +133,21 @@ int RefInset::plaintext(std::ostream & o int RefInset::linuxdoc(std::ostream & os, OutputParams const &) const { os << "<ref id=\"" << asString(cell(0)) - << "\" name=\"" << asString(cell(1)) << "\" >"; + << "\" name=\"" << asString(cell(1)) << "\">"; return 0; } -int RefInset::docbook(std::ostream & os, OutputParams const &) const +int RefInset::docbook(std::ostream & os, OutputParams const & runparams) const { if (cell(1).empty()) { - os << "<xref linkend=\"" << asString(cell(0)) << "\">"; + os << "<xref linkend=\"" << sgml::cleanID(asString(cell(0))); + if (runparams.flavor == OutputParams::XML) + os << "\"/>"; + else + os << "\">"; } else { - os << "<link linkend=\"" << asString(cell(0)) + os << "<link linkend=\"" << sgml::cleanID(asString(cell(0))) << "\">" << asString(cell(1)) << "</link>"; }