2002-09-05 11:31:30 +00:00
|
|
|
/**
|
2007-04-25 03:01:35 +00:00
|
|
|
* \file PreviewLoader.cpp
|
2002-09-05 15:14:23 +00:00
|
|
|
* This file is part of LyX, the document processor.
|
|
|
|
* Licence details can be found in the file COPYING.
|
2002-07-05 21:24:15 +00:00
|
|
|
*
|
2002-11-04 02:12:42 +00:00
|
|
|
* \author Angus Leeming
|
2002-09-05 11:31:30 +00:00
|
|
|
*
|
2003-08-23 00:17:00 +00:00
|
|
|
* Full author contact details are available in file CREDITS.
|
2002-07-05 21:24:15 +00:00
|
|
|
*/
|
|
|
|
|
|
|
|
#include <config.h>
|
|
|
|
|
|
|
|
#include "PreviewLoader.h"
|
|
|
|
#include "PreviewImage.h"
|
2004-04-16 14:34:41 +00:00
|
|
|
#include "GraphicsCache.h"
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2007-04-26 04:41:58 +00:00
|
|
|
#include "Buffer.h"
|
2007-05-28 07:43:15 +00:00
|
|
|
#include "BufferParams.h"
|
2007-04-26 04:41:58 +00:00
|
|
|
#include "Converter.h"
|
2007-05-28 07:43:15 +00:00
|
|
|
#include "Encoding.h"
|
2007-04-26 04:41:58 +00:00
|
|
|
#include "Format.h"
|
2007-05-28 07:43:15 +00:00
|
|
|
#include "LaTeXFeatures.h"
|
2007-04-26 04:41:58 +00:00
|
|
|
#include "LyXRC.h"
|
2007-05-28 07:43:15 +00:00
|
|
|
#include "output.h"
|
2007-04-26 04:41:58 +00:00
|
|
|
#include "OutputParams.h"
|
2007-05-28 07:43:15 +00:00
|
|
|
#include "TexRow.h"
|
2016-06-19 02:39:38 +00:00
|
|
|
#include "texstream.h"
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2006-10-12 14:10:13 +00:00
|
|
|
#include "frontends/Application.h" // hexName
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2007-11-29 19:19:39 +00:00
|
|
|
#include "support/convert.h"
|
|
|
|
#include "support/debug.h"
|
2007-12-17 16:04:46 +00:00
|
|
|
#include "support/FileName.h"
|
2002-07-05 21:24:15 +00:00
|
|
|
#include "support/filetools.h"
|
2007-11-29 19:19:39 +00:00
|
|
|
#include "support/ForkedCalls.h"
|
2003-05-23 13:54:09 +00:00
|
|
|
#include "support/lstrings.h"
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2014-07-05 09:19:34 +00:00
|
|
|
#include "support/TempFile.h"
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2016-07-10 15:50:19 +00:00
|
|
|
#include <atomic>
|
2002-07-05 21:24:15 +00:00
|
|
|
#include <fstream>
|
|
|
|
#include <iomanip>
|
2016-06-02 17:13:55 +00:00
|
|
|
#include <memory>
|
2016-07-30 19:46:29 +00:00
|
|
|
#include <mutex>
|
2016-06-02 17:13:55 +00:00
|
|
|
#include <sstream>
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2015-06-10 17:21:27 +00:00
|
|
|
#include <QTimer>
|
|
|
|
|
2007-12-12 10:16:00 +00:00
|
|
|
using namespace std;
|
2007-12-12 18:57:56 +00:00
|
|
|
using namespace lyx::support;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2010-04-22 11:16:58 +00:00
|
|
|
|
2003-09-08 00:33:41 +00:00
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
namespace {
|
|
|
|
|
2006-11-26 21:30:39 +00:00
|
|
|
typedef pair<string, FileName> SnippetPair;
|
2002-07-06 11:36:11 +00:00
|
|
|
|
2007-02-25 22:18:13 +00:00
|
|
|
// A list of all snippets to be converted to previews
|
2002-07-16 18:10:51 +00:00
|
|
|
typedef list<string> PendingSnippets;
|
2002-07-09 09:30:54 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
// Each item in the vector is a pair<snippet, image file name>.
|
2006-11-26 21:30:39 +00:00
|
|
|
typedef vector<SnippetPair> BitmapFile;
|
2002-07-09 09:30:54 +00:00
|
|
|
|
|
|
|
|
2014-07-05 09:19:34 +00:00
|
|
|
FileName const unique_tex_filename(FileName const & bufferpath)
|
2006-10-21 00:16:43 +00:00
|
|
|
{
|
2014-07-05 09:19:34 +00:00
|
|
|
TempFile tempfile(bufferpath, "lyxpreviewXXXXXX.tex");
|
|
|
|
tempfile.setAutoRemove(false);
|
|
|
|
return tempfile.name();
|
2006-10-21 00:16:43 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-09 09:30:54 +00:00
|
|
|
void setAscentFractions(vector<double> & ascent_fractions,
|
2006-11-26 21:30:39 +00:00
|
|
|
FileName const & metrics_file)
|
2006-10-21 00:16:43 +00:00
|
|
|
{
|
|
|
|
// If all else fails, then the images will have equal ascents and
|
|
|
|
// descents.
|
|
|
|
vector<double>::iterator it = ascent_fractions.begin();
|
|
|
|
vector<double>::iterator end = ascent_fractions.end();
|
|
|
|
fill(it, end, 0.5);
|
|
|
|
|
2006-11-26 21:30:39 +00:00
|
|
|
ifstream in(metrics_file.toFilesystemEncoding().c_str());
|
2006-10-21 00:16:43 +00:00
|
|
|
if (!in.good()) {
|
2007-11-28 22:12:03 +00:00
|
|
|
LYXERR(lyx::Debug::GRAPHICS, "setAscentFractions(" << metrics_file << ")\n"
|
|
|
|
<< "Unable to open file!");
|
2006-10-21 00:16:43 +00:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
bool error = false;
|
|
|
|
|
|
|
|
int snippet_counter = 1;
|
|
|
|
while (!in.eof() && it != end) {
|
|
|
|
string snippet;
|
|
|
|
int id;
|
|
|
|
double ascent_fraction;
|
|
|
|
|
|
|
|
in >> snippet >> id >> ascent_fraction;
|
|
|
|
|
|
|
|
if (!in.good())
|
|
|
|
// eof after all
|
|
|
|
break;
|
|
|
|
|
|
|
|
error = snippet != "Snippet";
|
|
|
|
if (error)
|
|
|
|
break;
|
|
|
|
|
|
|
|
error = id != snippet_counter;
|
|
|
|
if (error)
|
|
|
|
break;
|
|
|
|
|
|
|
|
*it = ascent_fraction;
|
|
|
|
|
|
|
|
++snippet_counter;
|
|
|
|
++it;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (error) {
|
2007-11-28 22:12:03 +00:00
|
|
|
LYXERR(lyx::Debug::GRAPHICS, "setAscentFractions(" << metrics_file << ")\n"
|
|
|
|
<< "Error reading file!\n");
|
2006-10-21 00:16:43 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2002-07-06 11:36:11 +00:00
|
|
|
|
2020-05-13 17:26:54 +00:00
|
|
|
std::function <bool (SnippetPair const &)> FindFirst(string const & comp)
|
2007-11-28 22:12:03 +00:00
|
|
|
{
|
2020-05-13 18:23:27 +00:00
|
|
|
return [&comp](SnippetPair const & sp) { return sp.first == comp; };
|
2020-05-13 17:26:54 +00:00
|
|
|
}
|
2002-07-06 11:36:11 +00:00
|
|
|
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
/// Store info on a currently executing, forked process.
|
2005-01-19 15:03:31 +00:00
|
|
|
class InProgress {
|
|
|
|
public:
|
2002-07-08 13:01:09 +00:00
|
|
|
///
|
|
|
|
InProgress() : pid(0) {}
|
|
|
|
///
|
2002-07-09 09:30:54 +00:00
|
|
|
InProgress(string const & filename_base,
|
2002-07-16 18:10:51 +00:00
|
|
|
PendingSnippets const & pending,
|
2002-07-09 09:30:54 +00:00
|
|
|
string const & to_format);
|
2002-07-17 16:56:42 +00:00
|
|
|
/// Remove any files left lying around and kill the forked process.
|
2002-07-08 13:01:09 +00:00
|
|
|
void stop() const;
|
|
|
|
|
|
|
|
///
|
2002-10-31 12:42:26 +00:00
|
|
|
string command;
|
|
|
|
///
|
2006-11-26 21:30:39 +00:00
|
|
|
FileName metrics_file;
|
2002-07-16 18:10:51 +00:00
|
|
|
///
|
|
|
|
BitmapFile snippets;
|
2020-05-13 17:26:54 +00:00
|
|
|
///
|
|
|
|
pid_t pid;
|
2002-07-08 13:01:09 +00:00
|
|
|
};
|
|
|
|
|
2002-10-31 12:42:26 +00:00
|
|
|
typedef map<pid_t, InProgress> InProgressProcesses;
|
2002-07-16 18:10:51 +00:00
|
|
|
|
|
|
|
typedef InProgressProcesses::value_type InProgressProcess;
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2017-07-23 11:11:54 +00:00
|
|
|
} // namespace
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2006-10-21 00:16:43 +00:00
|
|
|
|
2003-07-04 08:23:23 +00:00
|
|
|
namespace lyx {
|
|
|
|
namespace graphics {
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2017-05-28 11:25:53 +00:00
|
|
|
class PreviewLoader::Impl {
|
2005-01-19 15:03:31 +00:00
|
|
|
public:
|
2002-07-05 21:24:15 +00:00
|
|
|
///
|
|
|
|
Impl(PreviewLoader & p, Buffer const & b);
|
2002-07-08 13:01:09 +00:00
|
|
|
/// Stop any InProgress items still executing.
|
2002-07-06 12:38:44 +00:00
|
|
|
~Impl();
|
|
|
|
///
|
2002-07-05 21:24:15 +00:00
|
|
|
PreviewImage const * preview(string const & latex_snippet) const;
|
|
|
|
///
|
|
|
|
PreviewLoader::Status status(string const & latex_snippet) const;
|
|
|
|
///
|
|
|
|
void add(string const & latex_snippet);
|
|
|
|
///
|
|
|
|
void remove(string const & latex_snippet);
|
2010-07-21 14:28:38 +00:00
|
|
|
/// \p wait whether to wait for the process to complete or, instead,
|
|
|
|
/// to do it in the background.
|
2010-07-21 13:19:52 +00:00
|
|
|
void startLoading(bool wait = false);
|
2015-06-10 17:21:27 +00:00
|
|
|
///
|
|
|
|
void refreshPreviews();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-17 16:56:42 +00:00
|
|
|
/// Emit this signal when an image is ready for display.
|
2017-05-28 11:25:53 +00:00
|
|
|
signals2::signal<void(PreviewImage const &)> imageReady;
|
2002-07-17 16:56:42 +00:00
|
|
|
|
2002-08-02 16:30:58 +00:00
|
|
|
Buffer const & buffer() const { return buffer_; }
|
|
|
|
|
2016-11-05 00:00:44 +00:00
|
|
|
lyx::Converter const * setConverter(string const & from);
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
private:
|
2007-11-29 19:19:39 +00:00
|
|
|
/// Called by the ForkedCall process that generated the bitmap files.
|
2002-10-31 12:42:26 +00:00
|
|
|
void finishedGenerating(pid_t, int);
|
2002-07-05 21:24:15 +00:00
|
|
|
///
|
2020-11-30 22:00:40 +00:00
|
|
|
void dumpPreamble(otexstream &, Flavor) const;
|
2002-07-05 21:24:15 +00:00
|
|
|
///
|
2006-10-19 16:51:30 +00:00
|
|
|
void dumpData(odocstream &, BitmapFile const &) const;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-06 11:36:11 +00:00
|
|
|
/** cache_ allows easy retrieval of already-generated images
|
2002-07-05 21:24:15 +00:00
|
|
|
* using the LaTeX snippet as the identifier.
|
|
|
|
*/
|
2016-06-02 17:13:55 +00:00
|
|
|
typedef std::shared_ptr<PreviewImage> PreviewImagePtr;
|
2002-07-05 21:24:15 +00:00
|
|
|
///
|
2002-07-06 11:36:11 +00:00
|
|
|
typedef map<string, PreviewImagePtr> Cache;
|
2002-07-05 21:24:15 +00:00
|
|
|
///
|
|
|
|
Cache cache_;
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
/** pending_ stores the LaTeX snippets in anticipation of them being
|
|
|
|
* sent to the converter.
|
2002-07-05 21:24:15 +00:00
|
|
|
*/
|
2002-07-16 18:10:51 +00:00
|
|
|
PendingSnippets pending_;
|
2002-07-06 12:38:44 +00:00
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
/** in_progress_ stores all forked processes so that we can proceed
|
|
|
|
* thereafter.
|
|
|
|
*/
|
2002-07-16 18:10:51 +00:00
|
|
|
InProgressProcesses in_progress_;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
///
|
|
|
|
PreviewLoader & parent_;
|
|
|
|
///
|
|
|
|
Buffer const & buffer_;
|
2015-04-21 21:57:53 +00:00
|
|
|
///
|
|
|
|
mutable int font_scaling_factor_;
|
2015-06-10 17:21:27 +00:00
|
|
|
///
|
2015-07-21 22:56:34 +00:00
|
|
|
mutable int fg_color_;
|
|
|
|
///
|
|
|
|
mutable int bg_color_;
|
|
|
|
///
|
2015-06-10 17:21:27 +00:00
|
|
|
QTimer * delay_refresh_;
|
2015-06-21 09:21:59 +00:00
|
|
|
///
|
2020-05-19 21:08:11 +00:00
|
|
|
Trackable trackable_;
|
|
|
|
///
|
2015-06-21 09:21:59 +00:00
|
|
|
bool finished_generating_;
|
2002-07-09 09:30:54 +00:00
|
|
|
|
|
|
|
/// We don't own this
|
2007-03-20 21:53:01 +00:00
|
|
|
static lyx::Converter const * pconverter_;
|
2017-05-28 11:25:53 +00:00
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
};
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2007-03-20 21:53:01 +00:00
|
|
|
lyx::Converter const * PreviewLoader::Impl::pconverter_;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
|
2006-10-21 00:16:43 +00:00
|
|
|
//
|
2002-07-08 13:01:09 +00:00
|
|
|
// The public interface, defined in PreviewLoader.h
|
2006-10-21 00:16:43 +00:00
|
|
|
//
|
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
PreviewLoader::PreviewLoader(Buffer const & b)
|
|
|
|
: pimpl_(new Impl(*this, b))
|
|
|
|
{}
|
|
|
|
|
|
|
|
|
|
|
|
PreviewLoader::~PreviewLoader()
|
2007-11-21 23:47:47 +00:00
|
|
|
{
|
|
|
|
delete pimpl_;
|
|
|
|
}
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
|
|
|
|
PreviewImage const * PreviewLoader::preview(string const & latex_snippet) const
|
|
|
|
{
|
|
|
|
return pimpl_->preview(latex_snippet);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
PreviewLoader::Status PreviewLoader::status(string const & latex_snippet) const
|
|
|
|
{
|
|
|
|
return pimpl_->status(latex_snippet);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-17 16:56:42 +00:00
|
|
|
void PreviewLoader::add(string const & latex_snippet) const
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
|
|
|
pimpl_->add(latex_snippet);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-17 16:56:42 +00:00
|
|
|
void PreviewLoader::remove(string const & latex_snippet) const
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
|
|
|
pimpl_->remove(latex_snippet);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2010-07-21 13:19:52 +00:00
|
|
|
void PreviewLoader::startLoading(bool wait) const
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
2010-07-21 13:19:52 +00:00
|
|
|
pimpl_->startLoading(wait);
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
|
|
|
|
2002-07-17 16:56:42 +00:00
|
|
|
|
2015-06-10 17:21:27 +00:00
|
|
|
void PreviewLoader::refreshPreviews()
|
|
|
|
{
|
|
|
|
pimpl_->refreshPreviews();
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2017-05-28 11:25:53 +00:00
|
|
|
signals2::connection PreviewLoader::connect(slot const & slot) const
|
2002-07-17 16:56:42 +00:00
|
|
|
{
|
|
|
|
return pimpl_->imageReady.connect(slot);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void PreviewLoader::emitSignal(PreviewImage const & pimage) const
|
|
|
|
{
|
|
|
|
pimpl_->imageReady(pimage);
|
|
|
|
}
|
|
|
|
|
2002-08-02 16:30:58 +00:00
|
|
|
|
|
|
|
Buffer const & PreviewLoader::buffer() const
|
|
|
|
{
|
|
|
|
return pimpl_->buffer();
|
|
|
|
}
|
|
|
|
|
2003-07-04 08:23:23 +00:00
|
|
|
} // namespace graphics
|
|
|
|
} // namespace lyx
|
2002-07-08 13:01:09 +00:00
|
|
|
|
|
|
|
|
|
|
|
// The details of the Impl
|
|
|
|
// =======================
|
|
|
|
|
|
|
|
namespace {
|
|
|
|
|
2020-05-23 03:43:44 +00:00
|
|
|
class IncrementedFileName {
|
|
|
|
public:
|
|
|
|
IncrementedFileName(string const & to_format,
|
|
|
|
string const & filename_base)
|
|
|
|
: to_format_(to_format), base_(filename_base), counter_(1)
|
|
|
|
{}
|
|
|
|
|
|
|
|
SnippetPair const operator()(string const & snippet)
|
2002-07-16 18:10:51 +00:00
|
|
|
{
|
|
|
|
ostringstream os;
|
2020-05-23 03:43:44 +00:00
|
|
|
os << base_ << counter_++ << '.' << to_format_;
|
|
|
|
string const file_name = os.str();
|
|
|
|
return make_pair(snippet, FileName(file_name));
|
|
|
|
}
|
|
|
|
|
|
|
|
private:
|
|
|
|
string const & to_format_;
|
|
|
|
string const & base_;
|
|
|
|
int counter_;
|
|
|
|
};
|
2002-07-16 18:10:51 +00:00
|
|
|
|
2002-07-17 16:56:42 +00:00
|
|
|
|
2002-07-09 09:30:54 +00:00
|
|
|
InProgress::InProgress(string const & filename_base,
|
2002-07-16 18:10:51 +00:00
|
|
|
PendingSnippets const & pending,
|
2002-07-09 09:30:54 +00:00
|
|
|
string const & to_format)
|
2020-05-13 17:26:54 +00:00
|
|
|
: metrics_file(filename_base + ".metrics"),
|
|
|
|
snippets(pending.size()), pid(0)
|
2002-07-09 09:30:54 +00:00
|
|
|
{
|
2002-07-16 18:10:51 +00:00
|
|
|
PendingSnippets::const_iterator pit = pending.begin();
|
|
|
|
PendingSnippets::const_iterator pend = pending.end();
|
|
|
|
BitmapFile::iterator sit = snippets.begin();
|
2002-07-09 09:30:54 +00:00
|
|
|
|
2007-12-12 19:28:07 +00:00
|
|
|
transform(pit, pend, sit,
|
2002-09-04 10:15:56 +00:00
|
|
|
IncrementedFileName(to_format, filename_base));
|
2002-07-09 09:30:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
void InProgress::stop() const
|
|
|
|
{
|
|
|
|
if (pid)
|
2007-12-12 19:57:42 +00:00
|
|
|
ForkedCallsController::kill(pid, 0);
|
2002-07-08 13:01:09 +00:00
|
|
|
|
|
|
|
if (!metrics_file.empty())
|
2007-11-28 09:01:49 +00:00
|
|
|
metrics_file.removeFile();
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile::const_iterator vit = snippets.begin();
|
|
|
|
BitmapFile::const_iterator vend = snippets.end();
|
2002-07-08 13:01:09 +00:00
|
|
|
for (; vit != vend; ++vit) {
|
|
|
|
if (!vit->second.empty())
|
2007-11-28 09:01:49 +00:00
|
|
|
vit->second.removeFile();
|
2002-07-08 13:01:09 +00:00
|
|
|
}
|
|
|
|
}
|
2002-07-17 16:56:42 +00:00
|
|
|
|
2017-07-23 11:11:54 +00:00
|
|
|
} // namespace
|
2002-07-08 13:01:09 +00:00
|
|
|
|
|
|
|
|
2003-07-04 08:23:23 +00:00
|
|
|
namespace lyx {
|
|
|
|
namespace graphics {
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-09 09:30:54 +00:00
|
|
|
PreviewLoader::Impl::Impl(PreviewLoader & p, Buffer const & b)
|
2015-06-21 09:21:59 +00:00
|
|
|
: parent_(p), buffer_(b), finished_generating_(true)
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
2015-04-21 21:57:53 +00:00
|
|
|
font_scaling_factor_ = int(buffer_.fontScalingFactor());
|
2015-09-04 19:24:01 +00:00
|
|
|
if (theApp()) {
|
2020-12-10 12:32:55 +00:00
|
|
|
fg_color_ = convert(theApp()->hexName(foregroundColor()), 16);
|
|
|
|
bg_color_ = convert(theApp()->hexName(backgroundColor()), 16);
|
2015-09-04 19:24:01 +00:00
|
|
|
} else {
|
|
|
|
fg_color_ = 0x0;
|
|
|
|
bg_color_ = 0xffffff;
|
|
|
|
}
|
2011-09-11 18:23:15 +00:00
|
|
|
if (!pconverter_)
|
2010-09-21 16:34:30 +00:00
|
|
|
pconverter_ = setConverter("lyxpreview");
|
2015-06-10 17:21:27 +00:00
|
|
|
|
|
|
|
delay_refresh_ = new QTimer(&parent_);
|
|
|
|
delay_refresh_->setSingleShot(true);
|
|
|
|
QObject::connect(delay_refresh_, SIGNAL(timeout()),
|
|
|
|
&parent_, SLOT(refreshPreviews()));
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2016-11-05 00:00:44 +00:00
|
|
|
lyx::Converter const * PreviewLoader::Impl::setConverter(string const & from)
|
|
|
|
{
|
|
|
|
typedef vector<string> FmtList;
|
|
|
|
FmtList const & loadableFormats = graphics::Cache::get().loadableFormats();
|
|
|
|
FmtList::const_iterator it = loadableFormats.begin();
|
|
|
|
FmtList::const_iterator const end = loadableFormats.end();
|
|
|
|
|
|
|
|
for (; it != end; ++it) {
|
|
|
|
string const to = *it;
|
|
|
|
if (from == to)
|
|
|
|
continue;
|
|
|
|
|
|
|
|
lyx::Converter const * ptr = lyx::theConverters().getConverter(from, to);
|
|
|
|
if (ptr)
|
|
|
|
return ptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Show the error only once. This is thread-safe.
|
|
|
|
static nullptr_t no_conv = [&]{
|
|
|
|
LYXERR0("PreviewLoader::startLoading()\n"
|
|
|
|
<< "No converter from \"" << from
|
|
|
|
<< "\" format has been defined.");
|
|
|
|
return nullptr;
|
|
|
|
} ();
|
|
|
|
|
|
|
|
return no_conv;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-06 12:38:44 +00:00
|
|
|
PreviewLoader::Impl::~Impl()
|
|
|
|
{
|
2015-06-10 18:12:31 +00:00
|
|
|
delete delay_refresh_;
|
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
InProgressProcesses::iterator ipit = in_progress_.begin();
|
|
|
|
InProgressProcesses::iterator ipend = in_progress_.end();
|
2002-07-06 12:38:44 +00:00
|
|
|
|
2007-11-29 19:56:25 +00:00
|
|
|
for (; ipit != ipend; ++ipit)
|
2002-07-08 13:01:09 +00:00
|
|
|
ipit->second.stop();
|
|
|
|
}
|
2002-07-06 12:38:44 +00:00
|
|
|
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
PreviewImage const *
|
|
|
|
PreviewLoader::Impl::preview(string const & latex_snippet) const
|
|
|
|
{
|
2015-04-21 21:57:53 +00:00
|
|
|
int fs = int(buffer_.fontScalingFactor());
|
2015-09-04 19:24:01 +00:00
|
|
|
int fg = 0x0;
|
|
|
|
int bg = 0xffffff;
|
|
|
|
if (theApp()) {
|
2020-12-10 12:32:55 +00:00
|
|
|
fg = convert(theApp()->hexName(foregroundColor()), 16);
|
|
|
|
bg = convert(theApp()->hexName(backgroundColor()), 16);
|
2015-09-04 19:24:01 +00:00
|
|
|
}
|
2015-07-21 22:56:34 +00:00
|
|
|
if (font_scaling_factor_ != fs || fg_color_ != fg || bg_color_ != bg) {
|
|
|
|
// Schedule refresh of all previews on zoom or color changes.
|
2015-06-10 17:21:27 +00:00
|
|
|
// The previews are regenerated only after the zoom factor
|
|
|
|
// has not been changed for about 1 second.
|
2015-07-21 22:56:34 +00:00
|
|
|
fg_color_ = fg;
|
|
|
|
bg_color_ = bg;
|
2015-06-10 17:21:27 +00:00
|
|
|
delay_refresh_->start(1000);
|
2015-04-21 21:57:53 +00:00
|
|
|
}
|
2015-06-21 09:21:59 +00:00
|
|
|
// Don't try to access the cache until we are done.
|
|
|
|
if (delay_refresh_->isActive() || !finished_generating_)
|
2020-05-13 17:18:32 +00:00
|
|
|
return nullptr;
|
2020-05-19 21:08:11 +00:00
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
Cache::const_iterator it = cache_.find(latex_snippet);
|
2020-05-13 17:18:32 +00:00
|
|
|
return (it == cache_.end()) ? nullptr : it->second.get();
|
2002-07-06 12:38:44 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2015-06-10 17:21:27 +00:00
|
|
|
void PreviewLoader::Impl::refreshPreviews()
|
|
|
|
{
|
|
|
|
font_scaling_factor_ = int(buffer_.fontScalingFactor());
|
2015-06-21 15:21:19 +00:00
|
|
|
// Reschedule refresh until the previous process completed.
|
|
|
|
if (!finished_generating_) {
|
|
|
|
delay_refresh_->start(1000);
|
|
|
|
return;
|
|
|
|
}
|
2015-06-10 17:21:27 +00:00
|
|
|
Cache::const_iterator cit = cache_.begin();
|
|
|
|
Cache::const_iterator cend = cache_.end();
|
|
|
|
while (cit != cend)
|
|
|
|
parent_.remove((cit++)->first);
|
2015-06-21 09:21:59 +00:00
|
|
|
finished_generating_ = false;
|
2015-06-10 17:21:27 +00:00
|
|
|
buffer_.updatePreviews();
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
namespace {
|
|
|
|
|
2020-05-13 17:18:32 +00:00
|
|
|
std::function<bool (InProgressProcess const &)> FindSnippet(string const & s)
|
|
|
|
{
|
2020-05-13 18:23:27 +00:00
|
|
|
return [&s](InProgressProcess const & process) {
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile const & snippets = process.second.snippets;
|
2004-01-31 15:30:24 +00:00
|
|
|
BitmapFile::const_iterator beg = snippets.begin();
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile::const_iterator end = snippets.end();
|
2020-05-13 17:18:32 +00:00
|
|
|
return find_if(beg, end, FindFirst(s)) != end;
|
|
|
|
};
|
|
|
|
}
|
2002-07-16 18:10:51 +00:00
|
|
|
|
2017-07-23 11:11:54 +00:00
|
|
|
} // namespace
|
2002-07-16 18:10:51 +00:00
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
PreviewLoader::Status
|
|
|
|
PreviewLoader::Impl::status(string const & latex_snippet) const
|
|
|
|
{
|
|
|
|
Cache::const_iterator cit = cache_.find(latex_snippet);
|
|
|
|
if (cit != cache_.end())
|
2002-07-08 13:01:09 +00:00
|
|
|
return Ready;
|
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
PendingSnippets::const_iterator pit = pending_.begin();
|
|
|
|
PendingSnippets::const_iterator pend = pending_.end();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
pit = find(pit, pend, latex_snippet);
|
2002-07-09 09:30:54 +00:00
|
|
|
if (pit != pend)
|
2002-07-08 13:01:09 +00:00
|
|
|
return InQueue;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
InProgressProcesses::const_iterator ipit = in_progress_.begin();
|
|
|
|
InProgressProcesses::const_iterator ipend = in_progress_.end();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
ipit = find_if(ipit, ipend, FindSnippet(latex_snippet));
|
|
|
|
if (ipit != ipend)
|
|
|
|
return Processing;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
return NotFound;
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void PreviewLoader::Impl::add(string const & latex_snippet)
|
|
|
|
{
|
2002-07-09 09:30:54 +00:00
|
|
|
if (!pconverter_ || status(latex_snippet) != NotFound)
|
2002-07-05 21:24:15 +00:00
|
|
|
return;
|
|
|
|
|
2007-12-12 19:57:42 +00:00
|
|
|
string const snippet = trim(latex_snippet);
|
2002-08-02 16:30:58 +00:00
|
|
|
if (snippet.empty())
|
|
|
|
return;
|
|
|
|
|
2007-11-15 20:04:51 +00:00
|
|
|
LYXERR(Debug::GRAPHICS, "adding snippet:\n" << snippet);
|
2002-08-01 17:28:59 +00:00
|
|
|
|
2002-08-02 16:30:58 +00:00
|
|
|
pending_.push_back(snippet);
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
namespace {
|
|
|
|
|
2020-10-21 07:23:43 +00:00
|
|
|
std::function<void (InProgressProcess &)> EraseSnippet(string const & s)
|
|
|
|
{
|
2020-05-13 18:23:27 +00:00
|
|
|
return [&s](InProgressProcess & process) {
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile & snippets = process.second.snippets;
|
|
|
|
BitmapFile::iterator it = snippets.begin();
|
|
|
|
BitmapFile::iterator end = snippets.end();
|
|
|
|
|
2020-05-13 17:18:32 +00:00
|
|
|
it = find_if(it, end, FindFirst(s));
|
2002-07-16 18:10:51 +00:00
|
|
|
if (it != end)
|
|
|
|
snippets.erase(it, it+1);
|
2020-05-13 17:18:32 +00:00
|
|
|
};
|
2020-10-21 07:23:43 +00:00
|
|
|
}
|
2002-07-16 18:10:51 +00:00
|
|
|
|
2017-07-23 11:11:54 +00:00
|
|
|
} // namespace
|
2002-07-16 18:10:51 +00:00
|
|
|
|
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
void PreviewLoader::Impl::remove(string const & latex_snippet)
|
|
|
|
{
|
|
|
|
Cache::iterator cit = cache_.find(latex_snippet);
|
|
|
|
if (cit != cache_.end())
|
|
|
|
cache_.erase(cit);
|
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
PendingSnippets::iterator pit = pending_.begin();
|
|
|
|
PendingSnippets::iterator pend = pending_.end();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
pending_.erase(std::remove(pit, pend, latex_snippet), pend);
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
InProgressProcesses::iterator ipit = in_progress_.begin();
|
|
|
|
InProgressProcesses::iterator ipend = in_progress_.end();
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2007-12-12 19:28:07 +00:00
|
|
|
for_each(ipit, ipend, EraseSnippet(latex_snippet));
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2003-09-14 19:59:52 +00:00
|
|
|
while (ipit != ipend) {
|
2002-07-16 18:10:51 +00:00
|
|
|
InProgressProcesses::iterator curr = ipit++;
|
|
|
|
if (curr->second.snippets.empty())
|
2002-07-05 21:24:15 +00:00
|
|
|
in_progress_.erase(curr);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2010-07-21 13:19:52 +00:00
|
|
|
void PreviewLoader::Impl::startLoading(bool wait)
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
2002-07-09 09:30:54 +00:00
|
|
|
if (pending_.empty() || !pconverter_)
|
2002-07-08 13:01:09 +00:00
|
|
|
return;
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2003-10-22 13:15:18 +00:00
|
|
|
// Only start the process off after the buffer is loaded from file.
|
2007-10-20 10:03:45 +00:00
|
|
|
if (!buffer_.isFullyLoaded())
|
2003-10-22 13:15:18 +00:00
|
|
|
return;
|
|
|
|
|
2007-11-15 20:04:51 +00:00
|
|
|
LYXERR(Debug::GRAPHICS, "PreviewLoader::startLoading()");
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
// As used by the LaTeX file and by the resulting image files
|
2014-07-05 09:19:34 +00:00
|
|
|
FileName const directory(buffer_.temppath());
|
2003-06-30 23:56:22 +00:00
|
|
|
|
2014-07-05 09:19:34 +00:00
|
|
|
FileName const latexfile = unique_tex_filename(directory);
|
|
|
|
string const filename_base = removeExtension(latexfile.absFileName());
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2002-07-06 11:36:11 +00:00
|
|
|
// Create an InProgress instance to place in the map of all
|
|
|
|
// such processes if it starts correctly.
|
2014-12-07 17:35:28 +00:00
|
|
|
InProgress inprogress(filename_base, pending_, pconverter_->to());
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2002-09-04 10:15:56 +00:00
|
|
|
// clear pending_, so we're ready to start afresh.
|
|
|
|
pending_.clear();
|
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
// Output the LaTeX file.
|
2007-05-28 07:43:15 +00:00
|
|
|
// we use the encoding of the buffer
|
|
|
|
Encoding const & enc = buffer_.params().encoding();
|
2008-11-16 12:21:29 +00:00
|
|
|
ofdocstream of;
|
2007-12-29 18:04:43 +00:00
|
|
|
try { of.reset(enc.iconvName()); }
|
2012-09-17 08:01:26 +00:00
|
|
|
catch (iconv_codecvt_facet_exception const & e) {
|
2007-12-29 18:04:43 +00:00
|
|
|
LYXERR0("Caught iconv exception: " << e.what()
|
|
|
|
<< "\nUnable to create LaTeX file: " << latexfile);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2016-06-19 02:39:38 +00:00
|
|
|
otexstream os(of);
|
2007-05-28 07:43:15 +00:00
|
|
|
OutputParams runparams(&enc);
|
|
|
|
LaTeXFeatures features(buffer_, buffer_.params(), runparams);
|
|
|
|
|
|
|
|
if (!openFileWrite(of, latexfile))
|
|
|
|
return;
|
|
|
|
|
2004-02-25 12:00:53 +00:00
|
|
|
if (!of) {
|
2007-11-15 20:04:51 +00:00
|
|
|
LYXERR(Debug::GRAPHICS, "PreviewLoader::startLoading()\n"
|
|
|
|
<< "Unable to create LaTeX file\n" << latexfile);
|
2004-02-25 12:00:53 +00:00
|
|
|
return;
|
|
|
|
}
|
2002-07-10 09:09:37 +00:00
|
|
|
of << "\\batchmode\n";
|
2015-04-09 14:29:59 +00:00
|
|
|
|
2015-11-03 23:36:41 +00:00
|
|
|
// Set \jobname of previews to the document name (see bug 9627)
|
|
|
|
of << "\\def\\jobname{"
|
2020-11-19 11:24:04 +00:00
|
|
|
<< from_utf8(changeExtension(buffer_.latexName(), ""))
|
2015-11-03 23:36:41 +00:00
|
|
|
<< "}\n";
|
|
|
|
|
2015-04-09 14:29:59 +00:00
|
|
|
LYXERR(Debug::LATEX, "Format = " << buffer_.params().getDefaultOutputFormat());
|
|
|
|
string latexparam = "";
|
2015-04-27 10:27:42 +00:00
|
|
|
bool docformat = !buffer_.params().default_output_format.empty()
|
|
|
|
&& buffer_.params().default_output_format != "default";
|
|
|
|
// Use LATEX flavor if the document does not specify a specific
|
|
|
|
// output format (see bug 9371).
|
2020-11-30 22:00:40 +00:00
|
|
|
Flavor flavor = docformat
|
2015-04-27 10:27:42 +00:00
|
|
|
? buffer_.params().getOutputFlavor()
|
2020-11-30 22:00:40 +00:00
|
|
|
: Flavor::LaTeX;
|
2015-04-09 14:29:59 +00:00
|
|
|
if (buffer_.params().encoding().package() == Encoding::japanese) {
|
|
|
|
latexparam = " --latex=platex";
|
2020-11-30 22:00:40 +00:00
|
|
|
flavor = Flavor::LaTeX;
|
2015-04-09 14:29:59 +00:00
|
|
|
}
|
|
|
|
else if (buffer_.params().useNonTeXFonts) {
|
2020-11-30 22:00:40 +00:00
|
|
|
if (flavor == Flavor::LuaTeX)
|
2015-04-09 14:29:59 +00:00
|
|
|
latexparam = " --latex=lualatex";
|
|
|
|
else {
|
2020-11-30 22:00:40 +00:00
|
|
|
flavor = Flavor::XeTeX;
|
2015-04-09 14:29:59 +00:00
|
|
|
latexparam = " --latex=xelatex";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
switch (flavor) {
|
2020-11-30 22:00:40 +00:00
|
|
|
case Flavor::PdfLaTeX:
|
2015-04-09 14:29:59 +00:00
|
|
|
latexparam = " --latex=pdflatex";
|
|
|
|
break;
|
2020-11-30 22:00:40 +00:00
|
|
|
case Flavor::XeTeX:
|
2015-04-09 14:29:59 +00:00
|
|
|
latexparam = " --latex=xelatex";
|
|
|
|
break;
|
2020-11-30 22:00:40 +00:00
|
|
|
case Flavor::LuaTeX:
|
2015-04-09 14:29:59 +00:00
|
|
|
latexparam = " --latex=lualatex";
|
|
|
|
break;
|
2020-11-30 22:00:40 +00:00
|
|
|
case Flavor::DviLuaTeX:
|
2015-04-09 14:29:59 +00:00
|
|
|
latexparam = " --latex=dvilualatex";
|
|
|
|
break;
|
|
|
|
default:
|
2020-11-30 22:00:40 +00:00
|
|
|
flavor = Flavor::LaTeX;
|
2015-04-09 14:29:59 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
dumpPreamble(os, flavor);
|
2007-05-28 07:43:15 +00:00
|
|
|
// handle inputenc etc.
|
2020-05-08 17:32:08 +00:00
|
|
|
// I think this is already handled by dumpPreamble(): Kornel
|
2015-04-09 14:29:59 +00:00
|
|
|
// buffer_.params().writeEncodingPreamble(os, features);
|
2002-07-05 21:24:15 +00:00
|
|
|
of << "\n\\begin{document}\n";
|
2002-07-06 11:36:11 +00:00
|
|
|
dumpData(of, inprogress.snippets);
|
2002-07-05 21:24:15 +00:00
|
|
|
of << "\n\\end{document}\n";
|
|
|
|
of.close();
|
2007-05-28 07:43:15 +00:00
|
|
|
if (of.fail()) {
|
2007-11-15 20:04:51 +00:00
|
|
|
LYXERR(Debug::GRAPHICS, "PreviewLoader::startLoading()\n"
|
|
|
|
<< "File was not closed properly.");
|
2007-05-28 07:43:15 +00:00
|
|
|
return;
|
|
|
|
}
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
// The conversion command.
|
|
|
|
ostringstream cs;
|
2014-12-07 17:35:28 +00:00
|
|
|
cs << pconverter_->command()
|
2011-09-11 18:22:43 +00:00
|
|
|
<< " " << quoteName(latexfile.toFilesystemEncoding())
|
2015-04-21 21:57:53 +00:00
|
|
|
<< " --dpi " << font_scaling_factor_;
|
2012-12-13 19:16:50 +00:00
|
|
|
|
2017-05-28 11:25:53 +00:00
|
|
|
// FIXME XHTML
|
2012-12-13 19:16:50 +00:00
|
|
|
// The colors should be customizable.
|
|
|
|
if (!buffer_.isExporting()) {
|
|
|
|
ColorCode const fg = PreviewLoader::foregroundColor();
|
|
|
|
ColorCode const bg = PreviewLoader::backgroundColor();
|
2017-05-28 11:25:53 +00:00
|
|
|
cs << " --fg " << theApp()->hexName(fg)
|
2012-12-13 19:16:50 +00:00
|
|
|
<< " --bg " << theApp()->hexName(bg);
|
|
|
|
}
|
|
|
|
|
2015-04-09 14:29:59 +00:00
|
|
|
cs << latexparam;
|
2017-01-01 09:49:22 +00:00
|
|
|
cs << " --bibtex=" << quoteName(buffer_.params().bibtexCommand());
|
2011-09-11 18:22:59 +00:00
|
|
|
if (buffer_.params().bufferFormat() == "lilypond-book")
|
|
|
|
cs << " --lilypond";
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2014-01-31 03:59:33 +00:00
|
|
|
string const command = cs.str();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2010-07-21 13:19:52 +00:00
|
|
|
if (wait) {
|
Fix bug #4812 (Layout in local directory lost on Save As, Copying)
The "save-as" part of the bug is fixed by extending the \textclass tag
such that, if a local layout file is used, its path relative to the
document directory is now stored together with the name. If a relative
path cannot be used, an absolute one is used but, in this case, the
document is not usable on a different platform.
The "copy" part is fixed by introducing a new \origin tag, which is
written when the file is saved. This tag stores the absolute path of
the document directory. If the document is manually copied to a
different location, the local layout file is retrivied by using
\origin (which is only updated on save).
This new tag may prove useful also for locating other files when the
document is manually moved to a different directory.
As in the original implementation the files needed for the layout
(for example, a latex class) had to be in the same directory as the
layout file, this directory has also to be added to TEXINPUTS.
2015-05-13 19:40:51 +00:00
|
|
|
ForkedCall call(buffer_.filePath(), buffer_.layoutPos());
|
2010-07-21 13:19:52 +00:00
|
|
|
int ret = call.startScript(ForkedProcess::Wait, command);
|
2020-03-28 23:12:25 +00:00
|
|
|
// PID_MAX_LIMIT is 2^22 so we start one after that
|
|
|
|
static atomic_int fake((1 << 22) + 1);
|
2010-07-21 13:19:52 +00:00
|
|
|
int pid = fake++;
|
|
|
|
inprogress.pid = pid;
|
|
|
|
inprogress.command = command;
|
|
|
|
in_progress_[pid] = inprogress;
|
|
|
|
finishedGenerating(pid, ret);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
// Initiate the conversion from LaTeX to bitmap images files.
|
2017-05-28 11:25:53 +00:00
|
|
|
ForkedCall::sigPtr convert_ptr = make_shared<ForkedCall::sig>();
|
2018-01-03 18:58:50 +00:00
|
|
|
convert_ptr->connect(ForkedProcess::slot([this](pid_t pid, int retval){
|
|
|
|
finishedGenerating(pid, retval);
|
|
|
|
}).track_foreign(trackable_.p()));
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2011-09-24 01:32:35 +00:00
|
|
|
ForkedCall call(buffer_.filePath());
|
2007-11-29 19:19:39 +00:00
|
|
|
int ret = call.startScript(command, convert_ptr);
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
if (ret != 0) {
|
2007-11-15 20:04:51 +00:00
|
|
|
LYXERR(Debug::GRAPHICS, "PreviewLoader::startLoading()\n"
|
|
|
|
<< "Unable to start process\n" << command);
|
2002-07-06 11:36:11 +00:00
|
|
|
return;
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2002-07-06 12:50:09 +00:00
|
|
|
// Store the generation process in a list of all such processes
|
2002-07-06 12:38:44 +00:00
|
|
|
inprogress.pid = call.pid();
|
2002-10-31 12:42:26 +00:00
|
|
|
inprogress.command = command;
|
|
|
|
in_progress_[inprogress.pid] = inprogress;
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2014-10-18 13:30:58 +00:00
|
|
|
double PreviewLoader::displayPixelRatio() const
|
|
|
|
{
|
|
|
|
return buffer().params().display_pixel_ratio;
|
|
|
|
}
|
|
|
|
|
2002-10-31 12:42:26 +00:00
|
|
|
void PreviewLoader::Impl::finishedGenerating(pid_t pid, int retval)
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
2002-10-31 12:42:26 +00:00
|
|
|
// Paranoia check!
|
|
|
|
InProgressProcesses::iterator git = in_progress_.find(pid);
|
|
|
|
if (git == in_progress_.end()) {
|
|
|
|
lyxerr << "PreviewLoader::finishedGenerating(): unable to find "
|
|
|
|
"data for PID " << pid << endl;
|
2015-06-23 00:39:48 +00:00
|
|
|
finished_generating_ = true;
|
2002-10-31 12:42:26 +00:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
string const command = git->second.command;
|
2002-07-05 21:24:15 +00:00
|
|
|
string const status = retval > 0 ? "failed" : "succeeded";
|
2007-11-15 20:04:51 +00:00
|
|
|
LYXERR(Debug::GRAPHICS, "PreviewLoader::finishedInProgress("
|
2002-07-05 21:24:15 +00:00
|
|
|
<< retval << "): processing " << status
|
2007-11-15 20:04:51 +00:00
|
|
|
<< " for " << command);
|
2015-06-23 00:39:48 +00:00
|
|
|
if (retval > 0) {
|
|
|
|
in_progress_.erase(git);
|
|
|
|
finished_generating_ = true;
|
2002-07-05 21:24:15 +00:00
|
|
|
return;
|
2015-06-23 00:39:48 +00:00
|
|
|
}
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
// Read the metrics file, if it exists
|
2002-07-09 09:30:54 +00:00
|
|
|
vector<double> ascent_fractions(git->second.snippets.size());
|
|
|
|
setAscentFractions(ascent_fractions, git->second.metrics_file);
|
2002-07-08 13:01:09 +00:00
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
// Add these newly generated bitmap files to the cache and
|
|
|
|
// start loading them into LyX.
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile::const_iterator it = git->second.snippets.begin();
|
|
|
|
BitmapFile::const_iterator end = git->second.snippets.end();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2007-12-12 19:28:07 +00:00
|
|
|
list<PreviewImagePtr> newimages;
|
2002-07-15 11:08:46 +00:00
|
|
|
|
2020-05-13 17:18:32 +00:00
|
|
|
size_t metrics_counter = 0;
|
2002-07-09 09:30:54 +00:00
|
|
|
for (; it != end; ++it, ++metrics_counter) {
|
2002-07-05 21:24:15 +00:00
|
|
|
string const & snip = it->first;
|
2006-11-26 21:30:39 +00:00
|
|
|
FileName const & file = it->second;
|
2002-07-09 09:30:54 +00:00
|
|
|
double af = ascent_fractions[metrics_counter];
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2011-01-20 23:39:08 +00:00
|
|
|
// Add the image to the cache only if it's actually present
|
2015-04-26 17:08:16 +00:00
|
|
|
// and not empty (an empty image is signaled by af < 0)
|
|
|
|
if (af >= 0 && file.isReadableFile()) {
|
2011-01-20 23:39:08 +00:00
|
|
|
PreviewImagePtr ptr(new PreviewImage(parent_, snip, file, af));
|
|
|
|
cache_[snip] = ptr;
|
|
|
|
|
|
|
|
newimages.push_back(ptr);
|
|
|
|
}
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
}
|
|
|
|
|
2002-07-08 13:01:09 +00:00
|
|
|
// Remove the item from the list of still-executing processes.
|
2002-07-05 21:24:15 +00:00
|
|
|
in_progress_.erase(git);
|
2002-07-15 11:08:46 +00:00
|
|
|
|
|
|
|
// Tell the outside world
|
2007-12-12 19:28:07 +00:00
|
|
|
list<PreviewImagePtr>::const_reverse_iterator
|
2003-02-25 11:20:59 +00:00
|
|
|
nit = newimages.rbegin();
|
2007-12-12 19:28:07 +00:00
|
|
|
list<PreviewImagePtr>::const_reverse_iterator
|
2003-02-25 11:20:59 +00:00
|
|
|
nend = newimages.rend();
|
2002-07-15 11:08:46 +00:00
|
|
|
for (; nit != nend; ++nit) {
|
2002-07-17 16:56:42 +00:00
|
|
|
imageReady(*nit->get());
|
2002-07-15 11:08:46 +00:00
|
|
|
}
|
2015-06-21 09:21:59 +00:00
|
|
|
finished_generating_ = true;
|
2002-07-05 21:24:15 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2020-11-30 22:00:40 +00:00
|
|
|
void PreviewLoader::Impl::dumpPreamble(otexstream & os, Flavor flavor) const
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
|
|
|
// Dump the preamble only.
|
2020-11-29 23:03:35 +00:00
|
|
|
LYXERR(Debug::LATEX, "dumpPreamble, flavor == " << static_cast<int>(flavor));
|
2010-06-15 18:26:38 +00:00
|
|
|
OutputParams runparams(&buffer_.params().encoding());
|
2015-04-09 14:29:59 +00:00
|
|
|
runparams.flavor = flavor;
|
2003-05-22 21:10:22 +00:00
|
|
|
runparams.nice = true;
|
2003-05-23 09:23:03 +00:00
|
|
|
runparams.moving_arg = true;
|
2003-05-23 08:59:47 +00:00
|
|
|
runparams.free_spacing = true;
|
2013-09-29 12:14:15 +00:00
|
|
|
runparams.is_child = buffer_.parent();
|
2011-10-29 20:14:48 +00:00
|
|
|
buffer_.writeLaTeXSource(os, buffer_.filePath(), runparams, Buffer::OnlyPreamble);
|
2002-07-05 21:24:15 +00:00
|
|
|
|
2003-01-21 17:54:03 +00:00
|
|
|
// FIXME! This is a HACK! The proper fix is to control the 'true'
|
|
|
|
// passed to WriteStream below:
|
2007-02-25 22:18:13 +00:00
|
|
|
// int InsetMathNest::latex(Buffer const &, odocstream & os,
|
|
|
|
// OutputParams const & runparams) const
|
2003-01-21 17:54:03 +00:00
|
|
|
// {
|
2003-05-23 09:23:03 +00:00
|
|
|
// WriteStream wi(os, runparams.moving_arg, true);
|
2003-01-21 17:54:03 +00:00
|
|
|
// par_->write(wi);
|
|
|
|
// return wi.line();
|
|
|
|
// }
|
|
|
|
os << "\n"
|
|
|
|
<< "\\def\\lyxlock{}\n"
|
|
|
|
<< "\n";
|
|
|
|
|
2007-02-25 22:18:13 +00:00
|
|
|
// All equation labels appear as "(#)" + preview.sty's rendering of
|
2002-07-10 09:09:37 +00:00
|
|
|
// the label name
|
|
|
|
if (lyxrc.preview_hashed_labels)
|
|
|
|
os << "\\renewcommand{\\theequation}{\\#}\n";
|
|
|
|
|
2002-07-05 21:24:15 +00:00
|
|
|
// Use the preview style file to ensure that each snippet appears on a
|
|
|
|
// fresh page.
|
2008-07-02 14:42:04 +00:00
|
|
|
// Also support PDF output (automatically generated e.g. when
|
2010-02-24 10:47:35 +00:00
|
|
|
// \usepackage[pdftex]{hyperref} is used and XeTeX.
|
2002-07-05 21:24:15 +00:00
|
|
|
os << "\n"
|
2011-10-03 16:43:33 +00:00
|
|
|
<< "\\usepackage[active,delayed,showlabels,lyx]{preview}\n"
|
2002-07-05 21:24:15 +00:00
|
|
|
<< "\n";
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2006-10-19 16:51:30 +00:00
|
|
|
void PreviewLoader::Impl::dumpData(odocstream & os,
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile const & vec) const
|
2002-07-05 21:24:15 +00:00
|
|
|
{
|
2002-07-06 11:36:11 +00:00
|
|
|
if (vec.empty())
|
2002-07-05 21:24:15 +00:00
|
|
|
return;
|
|
|
|
|
2002-07-16 18:10:51 +00:00
|
|
|
BitmapFile::const_iterator it = vec.begin();
|
|
|
|
BitmapFile::const_iterator end = vec.end();
|
2002-07-05 21:24:15 +00:00
|
|
|
|
|
|
|
for (; it != end; ++it) {
|
2006-10-19 16:51:30 +00:00
|
|
|
// FIXME UNICODE
|
2002-07-05 21:24:15 +00:00
|
|
|
os << "\\begin{preview}\n"
|
2006-10-21 00:16:43 +00:00
|
|
|
<< from_utf8(it->first)
|
2002-07-05 21:24:15 +00:00
|
|
|
<< "\n\\end{preview}\n\n";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2003-07-04 08:23:23 +00:00
|
|
|
} // namespace graphics
|
|
|
|
} // namespace lyx
|
2015-06-10 17:21:27 +00:00
|
|
|
|
|
|
|
#include "moc_PreviewLoader.cpp"
|