X-Git-Url: https://git.lyx.org/gitweb/?a=blobdiff_plain;f=src%2FBuffer.cpp;h=888fb93d9b16a7dbc19f0186b02ed28e3c730f01;hb=0c7bd9a57f2a308bb9659200eda3b7e45f8d5d3c;hp=115a542544e8353550c78f4f428d5b58c4058955;hpb=e8ffb0c97aa7c5a27dd3fcfc79a4ce13d8701762;p=lyx.git diff --git a/src/Buffer.cpp b/src/Buffer.cpp index 115a542544..888fb93d9b 100644 --- a/src/Buffer.cpp +++ b/src/Buffer.cpp @@ -57,6 +57,7 @@ #include "PDFOptions.h" #include "SpellChecker.h" #include "sgml.h" +#include "texstream.h" #include "TexRow.h" #include "Text.h" #include "TextClass.h" @@ -107,12 +108,12 @@ #include "support/types.h" #include "support/bind.h" -#include "support/shared_ptr.h" #include #include #include #include +#include #include #include #include @@ -236,8 +237,8 @@ public: /// positions of child buffers in the buffer typedef map BufferPositionMap; struct ScopeBuffer { - ScopeBuffer() {} - ScopeBuffer(DocIterator const & s,Buffer const * b) + ScopeBuffer() : buffer(0) {} + ScopeBuffer(DocIterator const & s, Buffer const * b) : scope(s), buffer(b) {} DocIterator scope; Buffer const * buffer; @@ -370,6 +371,10 @@ public: + (with_blanks ? blank_count_ : 0); } + // does the buffer contain tracked changes? (if so, we automatically + // display the review toolbar, for instance) + mutable bool tracked_changes_present_; + private: /// So we can force access via the accessors. mutable Buffer const * parent_buffer; @@ -442,6 +447,7 @@ Buffer::Impl::Impl(Buffer * owner, FileName const & file, bool readonly_, preview_file_ = cloned_buffer_->d->preview_file_; preview_format_ = cloned_buffer_->d->preview_format_; preview_error_ = cloned_buffer_->d->preview_error_; + tracked_changes_present_ = cloned_buffer_->d->tracked_changes_present_; } @@ -1033,7 +1039,10 @@ bool Buffer::readDocument(Lexer & lex) params().indiceslist().addDefault(B_("Index")); // read main text - d->old_position = originFilePath(); + if (FileName::isAbsolute(params().origin)) + d->old_position = params().origin; + else + d->old_position = filePath(); bool const res = text().read(lex, errorList, d->inset); d->old_position.clear(); @@ -1318,7 +1327,7 @@ FileName Buffer::getBackupName() const { fn.onlyPath().absFileName() : lyxrc.backupdir_path; string const fform = convert(d->file_format); - string const backname = fname + "-" + fform; + string const backname = fname + "-lyxformat-" + fform; FileName backup(addName(fpath, addExtension(backname, fext))); // limit recursion, just in case @@ -1389,9 +1398,8 @@ bool Buffer::save() const // proper location once that has been done successfully. that // way we preserve the original file if something goes wrong. string const justname = fileName().onlyFileNameWithoutExt(); - boost::scoped_ptr - tempfile(new TempFile(fileName().onlyPath(), - justname + "-XXXXXX.lyx")); + auto tempfile = make_unique(fileName().onlyPath(), + justname + "-XXXXXX.lyx"); bool const symlink = fileName().isSymLink(); if (!symlink) tempfile->setAutoRemove(false); @@ -1652,9 +1660,11 @@ bool Buffer::makeLaTeXFile(FileName const & fname, { OutputParams runparams = runparams_in; - // XeTeX with TeX fonts is only safe with ASCII encoding, - // but the "flavor" is not known in BufferParams::encoding(). - if (!params().useNonTeXFonts && (runparams.flavor == OutputParams::XETEX)) + // XeTeX with TeX fonts is only safe with ASCII encoding (see also #9740), + // Check here, because the "flavor" is not known in BufferParams::encoding() + // (power users can override this safety measure selecting "utf8-plain"). + if (!params().useNonTeXFonts && (runparams.flavor == OutputParams::XETEX) + && (runparams.encoding->name() != "utf8-plain")) runparams.encoding = encodings.fromLyXName("ascii"); string const encoding = runparams.encoding->iconvName(); @@ -1675,7 +1685,7 @@ bool Buffer::makeLaTeXFile(FileName const & fname, ErrorList & errorList = d->errorLists["Export"]; errorList.clear(); bool failed_export = false; - otexstream os(ofs, d->texrow); + otexstream os(ofs); // make sure we are ready to export // this needs to be done before we validate @@ -1685,7 +1695,6 @@ bool Buffer::makeLaTeXFile(FileName const & fname, updateMacroInstances(OutputUpdate); try { - os.texrow().reset(); writeLaTeXSource(os, original_path, runparams, output); } catch (EncodingException const & e) { @@ -1716,6 +1725,8 @@ bool Buffer::makeLaTeXFile(FileName const & fname, lyx_exit(1); } + d->texrow = move(os.texrow()); + ofs.close(); if (ofs.fail()) { failed_export = true; @@ -1740,8 +1751,10 @@ void Buffer::writeLaTeXSource(otexstream & os, OutputParams runparams = runparams_in; // XeTeX with TeX fonts is only safe with ASCII encoding, - // but the "flavor" is not known in BufferParams::encoding(). - if (!params().useNonTeXFonts && (runparams.flavor == OutputParams::XETEX)) + // Check here, because the "flavor" is not known in BufferParams::encoding() + // (power users can override this safety measure selecting "utf8-plain"). + if (!params().useNonTeXFonts && (runparams.flavor == OutputParams::XETEX) + && (runparams.encoding->name() != "utf8-plain")) runparams.encoding = encodings.fromLyXName("ascii"); // FIXME: when only the current paragraph is shown, this is ignored // (or not reached) and characters encodable in the current @@ -2207,8 +2220,8 @@ void Buffer::validate(LaTeXFeatures & features) const if (!features.runparams().is_child) params().validate(features); - for_each(paragraphs().begin(), paragraphs().end(), - bind(&Paragraph::validate, _1, ref(features))); + for (Paragraph const & p : paragraphs()) + p.validate(features); if (lyxerr.debugging(Debug::LATEX)) { features.showStruct(); @@ -2226,8 +2239,8 @@ void Buffer::getLabelList(vector & list) const list.clear(); shared_ptr toc = d->toc_backend.toc("label"); - TocIterator toc_it = toc->begin(); - TocIterator end = toc->end(); + Toc::const_iterator toc_it = toc->begin(); + Toc::const_iterator end = toc->end(); for (; toc_it != end; ++toc_it) { if (toc_it->depth() == 0) list.push_back(toc_it->str()); @@ -2762,12 +2775,16 @@ void Buffer::dispatch(FuncRequest const & func, DispatchResult & dr) break; case LFUN_CHANGES_TRACK: - undo().recordUndoBufferParams(CursorData()); + if (params().save_transient_properties) + undo().recordUndoBufferParams(CursorData()); params().track_changes = !params().track_changes; + if (!params().track_changes) + dr.forceChangesUpdate(); break; case LFUN_CHANGES_OUTPUT: - undo().recordUndoBufferParams(CursorData()); + if (params().save_transient_properties) + undo().recordUndoBufferParams(CursorData()); params().output_changes = !params().output_changes; if (params().output_changes) { bool dvipost = LaTeXFeatures::isAvailable("dvipost"); @@ -3029,12 +3046,21 @@ string Buffer::filePath() const } -string Buffer::originFilePath() const +DocFileName Buffer::getReferencedFileName(string const & fn) const { - if (FileName::isAbsolute(params().origin)) - return params().origin; + DocFileName result; + if (FileName::isAbsolute(fn) || !FileName::isAbsolute(params().origin)) + result.set(fn, filePath()); + else { + // filePath() ends with a path separator + FileName const test(filePath() + fn); + if (test.exists()) + result.set(fn, filePath()); + else + result.set(fn, params().origin); + } - return filePath(); + return result; } @@ -3633,11 +3659,11 @@ void Buffer::changeRefsIfUnique(docstring const & from, docstring const & to) } // returns NULL if id-to-row conversion is unsupported -auto_ptr Buffer::getSourceCode(odocstream & os, string const & format, - pit_type par_begin, pit_type par_end, - OutputWhat output, bool master) const +unique_ptr Buffer::getSourceCode(odocstream & os, string const & format, + pit_type par_begin, pit_type par_end, + OutputWhat output, bool master) const { - auto_ptr texrow(NULL); + unique_ptr texrow; OutputParams runparams(¶ms().encoding()); runparams.nice = true; runparams.flavor = params().getOutputFlavor(format); @@ -3691,14 +3717,13 @@ auto_ptr Buffer::getSourceCode(odocstream & os, string const & format, LaTeXFeatures features(*this, params(), runparams); params().validate(features); runparams.use_polyglossia = features.usePolyglossia(); - texrow.reset(new TexRow()); - texrow->newline(); - texrow->newline(); // latex or literate - otexstream ots(os, *texrow); - + otexstream ots(os); + // output above + ots.texrow().newlines(2); // the real stuff latexParagraphs(*this, text(), ots, runparams); + texrow = ots.releaseTexRow(); texrow->finalize(); // Restore the parenthood @@ -3734,13 +3759,13 @@ auto_ptr Buffer::getSourceCode(odocstream & os, string const & format, writeDocBookSource(os, absFileName(), runparams, output); } else { // latex or literate - texrow.reset(new TexRow()); - texrow->newline(); - texrow->newline(); - otexstream ots(os, *texrow); + otexstream ots(os); + // output above + ots.texrow().newlines(2); if (master) runparams.is_child = true; writeLaTeXSource(ots, string(), runparams, output); + texrow = ots.releaseTexRow(); texrow->finalize(); } } @@ -3827,7 +3852,7 @@ public: /// virtual shared_ptr clone() const { - return shared_ptr(new AutoSaveBuffer(*this)); + return make_shared(*this); } /// int start() @@ -4290,26 +4315,22 @@ Buffer::ExportStatus Buffer::preview(string const & format, bool includeall) con ExportStatus const status = doExport(format, true, false, result_file); FileName const previewFile(result_file); - LATTEST (isClone()); - d->cloned_buffer_->d->preview_file_ = previewFile; - d->cloned_buffer_->d->preview_format_ = format; - d->cloned_buffer_->d->preview_error_ = (status != ExportSuccess); + Impl * theimpl = isClone() ? d->cloned_buffer_->d : d; + theimpl->preview_file_ = previewFile; + theimpl->preview_format_ = format; + theimpl->preview_error_ = (status != ExportSuccess); if (status != ExportSuccess) return status; - if (previewFile.exists()) { - if (!formats.view(*this, previewFile, format)) - return PreviewError; - else - return PreviewSuccess; - } - else { - // Successful export but no output file? - // Probably a bug in error detection. - LATTEST (status != ExportSuccess); - return status; - } + if (previewFile.exists()) + return formats.view(*this, previewFile, format) ? + PreviewSuccess : PreviewError; + + // Successful export but no output file? + // Probably a bug in error detection. + LATTEST(status != ExportSuccess); + return status; } @@ -4570,6 +4591,7 @@ void Buffer::updateBuffer(UpdateScope scope, UpdateType utype) const // update all caches clearReferenceCache(); updateMacros(); + setChangesPresent(false); Buffer & cbuf = const_cast(*this); @@ -4597,6 +4619,11 @@ static depth_type getDepth(DocIterator const & it) if (!it[i].inset().inMathed()) depth += it[i].paragraph().getDepth() + 1; // remove 1 since the outer inset does not count + // we should have at least one non-math inset, so + // depth should nevery be 0. but maybe it is worth + // marking this, just in case. + LATTEST(depth > 0); + // coverity[INTEGER_OVERFLOW] return depth - 1; } @@ -4833,6 +4860,9 @@ void Buffer::updateBuffer(ParIterator & parit, UpdateType utype) const // set the counter for this paragraph d->setLabel(parit, utype); + // update change-tracking flag + parit->addChangesToBuffer(*this); + // now the insets InsetList::const_iterator iit = parit->insetList().begin(); InsetList::const_iterator end = parit->insetList().end(); @@ -5071,13 +5101,23 @@ void Buffer::checkMasterBuffer() string Buffer::includedFilePath(string const & name, string const & ext) const { + if (d->old_position.empty() || + equivalent(FileName(d->old_position), FileName(filePath()))) + return name; + bool isabsolute = FileName::isAbsolute(name); - // old_position already contains a trailing path separator - string const absname = isabsolute ? name : d->old_position + name; + // both old_position and filePath() end with a path separator + string absname = isabsolute ? name : d->old_position + name; + + // if old_position is set to origin, we need to do the equivalent of + // getReferencedFileName() (see readDocument()) + if (!isabsolute && d->old_position == params().origin) { + FileName const test(addExtension(filePath() + name, ext)); + if (test.exists()) + absname = filePath() + name; + } - if (d->old_position.empty() - || equivalent(FileName(d->old_position), FileName(filePath())) - || !FileName(addExtension(absname, ext)).exists()) + if (!FileName(addExtension(absname, ext)).exists()) return name; if (isabsolute) @@ -5087,4 +5127,29 @@ string Buffer::includedFilePath(string const & name, string const & ext) const from_utf8(filePath()))); } + +void Buffer::setChangesPresent(bool b) const +{ + d->tracked_changes_present_ = b; +} + + +bool Buffer::areChangesPresent() const +{ + return d->tracked_changes_present_; +} + + +void Buffer::updateChangesPresent() const +{ + LYXERR(Debug::CHANGES, "Buffer::updateChangesPresent"); + setChangesPresent(false); + ParConstIterator it = par_iterator_begin(); + ParConstIterator const end = par_iterator_end(); + for (; !areChangesPresent() && it != end; ++it) + it->addChangesToBuffer(*this); +} + + + } // namespace lyx