On Sat, Apr 22, 2006 at 11:49:36PM -0500, Bo Peng wrote: > Dear developers, > > Attached is a complete patch that, under windows, > > 1. configure.py generates "auto" as viewers. > > 2. when no user specified viewer exists, the default viewer through > windows ShellExecute will be used. > > Windows users will never again need to worry about viewers. > > Will be applied to 1.5.x if no objection is heard. Someone may want to > change configure.m4 so that this can be applied to 1.4.x as well.
Please, attached find your patch augmented with the support for cygwin. Basically, I had to move a little down the inclusion of the Windows include files in filetools.C to avoid compiler errors, and added an utility function to os_cygwin.C which copies the cygwin environment to the Windows environment before calling ShellExecute(). If/when you'll modify it, I'll review it again for cygwin adaptation. Good work, Bo! -- Enrico
Index: src/format.C =================================================================== --- src/format.C (revision 13716) +++ src/format.C (working copy) @@ -35,6 +35,7 @@ using lyx::support::quoteName; using lyx::support::subst; using lyx::support::Systemcall; +using lyx::support::autoViewFile; using std::string; using std::distance; @@ -223,13 +224,15 @@ if (format && format->viewer().empty() && format->isChildFormat()) format = getFormat(format->parentFormat()); - if (!format || format->viewer().empty()) { -// I believe this is the wrong place to show alerts, it should be done by -// the caller (this should be "utility" code) - Alert::error(_("Cannot view file"), - bformat(_("No information for viewing %1$s"), - prettyName(format_name))); - return false; + + // auto viewer is the default setting under windows + if (!format || format->viewer().empty() || format->viewer() == "auto") { + if (!autoViewFile(filename, "open")) { + Alert::error(_("Cannot view file"), + _("No default viewer for viewing ") + filename); + return false; + } + return true; } string command = libScriptSearch(format->viewer()); @@ -279,13 +282,15 @@ if (format && format->editor().empty() && format->isChildFormat()) format = getFormat(format->parentFormat()); - if (!format || format->editor().empty()) { -// I believe this is the wrong place to show alerts, it should be done by -// the caller (this should be "utility" code) - Alert::error(_("Cannot edit file"), - bformat(_("No information for editing %1$s"), - prettyName(format_name))); - return false; + + // auto editor is the default setting under windows + if (!format || format->editor().empty() || format->editor() == "auto") { + if (!autoViewFile(filename, "edit")) { + Alert::error(_("Cannot edit file"), + _("No default editor for editing " + filename)); + return false; + } + return true; } string command = format->editor(); Index: src/support/os.h =================================================================== --- src/support/os.h (revision 13716) +++ src/support/os.h (working copy) @@ -80,6 +80,23 @@ */ void cygwin_path_fix(bool use_cygwin_paths); +#if defined(__CYGWIN__) || defined(__CYGWIN32__) +enum PathStyle { + posix, + windows +}; + +/// Converts a path to a target style. +std::string convert_path(std::string const & p, PathStyle const & target); + +/// Converts a path list to a target style. +std::string convert_path_list(std::string const & p, PathStyle const & target); + +/// Copy cygwin environment variables to the Windows environment +/// if they're not already there. +void setup_windows_environment(void); +#endif + } // namespace os } // namespace support } // namespace lyx Index: src/support/filetools.C =================================================================== --- src/support/filetools.C (revision 13716) +++ src/support/filetools.C (working copy) @@ -51,6 +51,11 @@ #include <fstream> #include <sstream> +#if defined(_WIN32) || defined(__CYGWIN__) +# include <windef.h> +# include <shellapi.h> +#endif + #ifndef CXX_GLOBAL_CSTD using std::fgetc; using std::isalnum; @@ -1225,5 +1230,33 @@ return cmp; } + +bool autoViewFile(string const & filename, string const & mode) +{ +#if defined(_WIN32) || defined(__CYGWIN__) + lyxerr[Debug::FILES] << mode << " file: " << filename << std::endl; + + // reference: http://msdn.microsoft.com/library/default.asp?url=/library/en-us/shellcc + // /platform/shell/reference/functions/shellexecute.asp +# ifdef __CYGWIN__ + string const converted_path = + os::convert_path(filename, os::PathStyle(os::windows)); + char const * const win_path = converted_path.c_str(); + // Need to sync the Windows environment + os::setup_windows_environment(); +# else + char const * const win_path = filename.c_str(); +# endif + int const res = reinterpret_cast<int>(ShellExecute(NULL, mode.c_str(), + win_path, NULL, NULL, 1)); + return res > 32; +#else + // currently, no default viewer is tried for non-windows system + // support for KDE/Gnome/Macintosh may be added later + return false; +#endif +} + + } //namespace support } // namespace lyx Index: src/support/os_cygwin.C =================================================================== --- src/support/os_cygwin.C (revision 13716) +++ src/support/os_cygwin.C (working copy) @@ -86,13 +86,9 @@ (!contains(p, '\\') && (p.length() <= 1 || p[1] == ':')); } +} // namespace anon -enum PathStyle { - posix, - windows -}; - string convert_path(string const & p, PathStyle const & target) { char path_buf[PATH_MAX]; @@ -139,9 +135,7 @@ return subst(p, '\\', '/'); } -} // namespace anon - string external_path(string const & p) { return convert_path(p, cygwin_path_fix_ ? PathStyle(windows) @@ -199,6 +193,49 @@ } +// Copy cygwin environment variables to the Windows environment +// if they're not already there. +void setup_windows_environment(void) +{ + char **envp = environ; + char curval[2]; + string var; + string val; + bool temp_seen = false; + + while (envp && *envp) { + val = split(*envp++, var, '='); + + if (var == "TEMP") + temp_seen = true; + + if (GetEnvironmentVariable(var.c_str(), curval, 2) == 0 + && GetLastError() == ERROR_ENVVAR_NOT_FOUND) { + /* Convert to Windows style where necessary */ + if (var == "PATH" || var == "LD_LIBRARY_PATH") { + string const winpathlist = + convert_path_list(val, PathStyle(windows)); + if (!winpathlist.empty()) { + SetEnvironmentVariable(var.c_str(), + winpathlist.c_str()); + } + } else if (var == "HOME" || var == "TMPDIR" || + var == "TMP" || var == "TEMP") { + string const winpath = + convert_path(val, PathStyle(windows)); + SetEnvironmentVariable(var.c_str(), winpath.c_str()); + } else { + SetEnvironmentVariable(var.c_str(), val.c_str()); + } + } + } + if (!temp_seen) { + string const winpath = convert_path("/tmp", PathStyle(windows)); + SetEnvironmentVariable("TEMP", winpath.c_str()); + } +} + + // returns a string suitable to be passed to popen when // reading a pipe char const * popen_read_mode() Index: src/support/filetools.h =================================================================== --- src/support/filetools.h (revision 13716) +++ src/support/filetools.h (working copy) @@ -266,6 +266,13 @@ cmd_ret const runCommand(std::string const & cmd); +/** view a file, with given command and parameter. + * \param filename + * \param mode "open" or "edit" + * \returns whether or not the file is viewed (or edited) successfully. + */ +bool autoViewFile(std::string const & filename, std::string const & mode="open"); + } // namespace support } // namespace lyx Index: lib/configure.py =================================================================== --- lib/configure.py (revision 13716) +++ lib/configure.py (working copy) @@ -262,6 +262,55 @@ ''') +def autoFormatEntries(): + ''' Use auto for windows system (\Format entries) ''' + addToRC(r'''\Format tgif obj Tgif "" "auto" "auto" +\Format fig fig FIG "" "auto" "auto" +\Format agr agr Grace "" "auto" "auto" +\Format fen fen FEN "" "auto" "auto" +\Format bmp bmp BMP "" "auto" "auto" +\Format gif gif GIF "" "auto" "auto" +\Format jpg jpg JPEG "" "auto" "auto" +\Format pbm pbm PBM "" "auto" "auto" +\Format pgm pgm PGM "" "auto" "auto" +\Format png png PNG "" "auto" "auto" +\Format ppm ppm PPM "" "auto" "auto" +\Format tiff tif TIFF "" "auto" "auto" +\Format xbm xbm XBM "" "auto" "auto" +\Format xpm xpm XPM "" "auto" "auto" +\Format asciichess asc "Plain text (chess output)" "" "" "auto" +\Format asciiimage asc "Plain text (image)" "" "" "auto" +\Format asciixfig asc "Plain text (Xfig output)" "" "" "auto" +\Format dateout tmp "date (output)" "" "" "auto" +\Format docbook sgml DocBook B "" "auto" +\Format docbook-xml xml "Docbook (XML)" "" "" "auto" +\Format literate nw NoWeb N "" "auto" +\Format latex tex "TeX (latex)" l "" "auto" +\Format linuxdoc sgml LinuxDoc x "" "auto" +\Format pdflatex tex "TeX (pdflatex)" "" "" "auto" +\Format text txt "Plain text" a "" "auto" +\Format textparagraph txt "Plain text (paragraphs)" "" "auto" "auto" +\Format eps eps EPS "" "auto" "" +\Format ps ps Postscript t "auto" "" +\Format pdf pdf "PDF (ps2pdf)" P "auto" "auto" +\Format pdf2 pdf "PDF (pdflatex)" F "auto" "auto" +\Format pdf3 pdf "PDF (dvipdfm)" m "auto" "auto" +\Format dvi dvi DVI D "auto" "" +\Format html html HTML H "auto" "auto" +\Format date "" "date command" "" "" "" +\Format fax "" Fax "" "" "" +\Format lyx lyx LyX "" "" "" +\Format lyx13x lyx13 "LyX 1.3.x" "" "" "" +\Format lyxpreview lyxpreview "LyX Preview" "" "" "" +\Format pdftex pdftex_t PDFTEX "" "" "" +\Format program "" Program "" "" "" +\Format pstex pstex_t PSTEX "" "" "" +\Format sxw sxw "OpenOffice.Org Writer" O "" "" +\Format word doc "MS Word" W "auto" "auto" +\Format wordhtml html "MS Word (HTML)" "" "auto" "auto" +''') + + def checkConverterEntries(): ''' Check all converters (\converter entries) ''' checkProg('the pdflatex program', ['pdflatex $$i'], @@ -696,7 +745,10 @@ ''') # check latex LATEX = checkLatex() - checkFormatEntries() + if os.name == 'nt' or sys.platform == 'cygwin': + autoFormatEntries() + else: + checkFormatEntries() checkConverterEntries() (chk_linuxdoc, bool_linuxdoc, linuxdoc_cmd) = checkLinuxDoc() (chk_docbook, bool_docbook, docbook_cmd) = checkDocBook()