Embedding: when an inset with an embedded file is copied to another buffer, the embedded file needs to be copied, to an external file or to the temporary directory of that buffer. Otherwise, pasted insets will become invalid when the source buffer is closed and the embedded files are removed.

git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/trunk@23758 a592a061-630c-0410-9148-cb99ea01b6c8
This commit is contained in:
Bo Peng 2008-03-15 04:48:31 +00:00
parent 0a5b3e9a36
commit 5ffc0d19c1
9 changed files with 101 additions and 1 deletions

View File

@ -254,6 +254,64 @@ bool EmbeddedFile::updateFromExternalFile() const
}
EmbeddedFile EmbeddedFile::copyTo(Buffer const * buf)
{
EmbeddedFile file = EmbeddedFile(absFilename(), buf->filePath());
file.setEmbed(embedded());
file.enable(buf->embedded(), buf, false);
// use external file.
if (!embedded())
return file;
LYXERR(Debug::FILES, "Copy " << availableFile()
<< " to " << file.availableFile());
FileName from_file = availableFile();
FileName to_file = file.availableFile();
if (!from_file.exists()) {
// no from file
throw ExceptionMessage(ErrorException,
_("Failed to copy embedded file"),
bformat(_("Failed to embed file %1$s.\n"
"Please check whether the source file is available"),
from_utf8(absFilename())));
file.setEmbed(false);
return file;
}
// if destination file already exists ...
if (to_file.exists()) {
// no need to copy if the files are the same
if (checksum() == to_file.checksum())
return file;
// other wise, ask if overwrite
int const ret = Alert::prompt(
_("Update embedded file?"),
bformat(_("Embedded file %1$s already exists, do you want to overwrite it"),
from_utf8(to_file.absFilename())), 1, 1, _("&Overwrite"), _("&Cancel"));
if (ret != 0)
// if the user does not want to overwrite, we still consider it
// a successful operation.
return file;
}
// copy file
// need to make directory?
FileName path = to_file.onlyPath();
if (!path.isDirectory())
path.createPath();
if (from_file.copyTo(to_file))
return file;
throw ExceptionMessage(ErrorException,
_("Copy file failure"),
bformat(_("Cannot copy file %1$s to %2$s.\n"
"Please check whether the directory exists and is writeable."),
from_utf8(from_file.absFilename()), from_utf8(to_file.absFilename())));
return file;
}
void EmbeddedFile::updateInsets() const
{
vector<Inset const *>::const_iterator it = inset_list_.begin();
@ -414,7 +472,7 @@ void EmbeddedFileList::enable(bool flag, Buffer & buffer, bool updateFile)
for (it = begin(); it != it_end; ++it)
it->updateInsets();
if (!updateFile)
if (!updateFile || (count_external == 0 && count_embedded == 0))
return;
// show result

View File

@ -158,6 +158,8 @@ public:
bool extract() const;
/// update embedded file from external file, does not change embedding status
bool updateFromExternalFile() const;
/// copy an embedded file to another buffer
EmbeddedFile copyTo(Buffer const * buf);
///
/// After the embedding status is changed, update all insets related
/// to this file item. For example, a graphic inset may need to monitor

View File

@ -52,6 +52,18 @@ InsetBibtex::InsetBibtex(InsetCommandParams const & p)
{}
void InsetBibtex::setBuffer(Buffer & buffer)
{
if (buffer_) {
EmbeddedFileList::iterator it = bibfiles_.begin();
EmbeddedFileList::iterator it_end = bibfiles_.end();
for (; it != it_end; ++it)
*it = it->copyTo(&buffer);
}
Inset::setBuffer(buffer);
}
ParamInfo const & InsetBibtex::findInfo(string const & /* cmdName */)
{
static ParamInfo param_info_;

View File

@ -27,6 +27,8 @@ public:
///
InsetBibtex(InsetCommandParams const &);
///
void setBuffer(Buffer & buffer);
///
docstring screenLabel() const;
///
EDITABLE editable() const { return IS_EDITABLE; }

View File

@ -419,6 +419,14 @@ InsetExternal::~InsetExternal()
}
void InsetExternal::setBuffer(Buffer & buffer)
{
if (buffer_)
params_.filename = params_.filename.copyTo(&buffer);
Inset::setBuffer(buffer);
}
void InsetExternal::statusChanged() const
{
updateFrontend();

View File

@ -112,6 +112,8 @@ public:
///
~InsetExternal();
///
void setBuffer(Buffer & buffer);
///
InsetCode lyxCode() const { return EXTERNAL_CODE; }
///
EDITABLE editable() const { return IS_EDITABLE; }

View File

@ -154,6 +154,14 @@ InsetGraphics::~InsetGraphics()
}
void InsetGraphics::setBuffer(Buffer & buffer)
{
if (buffer_)
params_.filename = params_.filename.copyTo(&buffer);
Inset::setBuffer(buffer);
}
void InsetGraphics::doDispatch(Cursor & cur, FuncRequest & cmd)
{
switch (cmd.action) {

View File

@ -34,6 +34,8 @@ public:
///
~InsetGraphics();
///
void setBuffer(Buffer & buffer);
///
bool isLabeled() const { return true; }
void metrics(MetricsInfo &, Dimension &) const;
///

View File

@ -215,6 +215,12 @@ InsetInclude::~InsetInclude()
void InsetInclude::setBuffer(Buffer & buffer)
{
if (buffer_) {
EmbeddedFile file_from = includedFilename(*buffer_, params());
EmbeddedFile file_to = file_from.copyTo(&buffer);
if (file_to.embedded())
setParam("embed", from_utf8(file_to.inzipName()));
}
buffer_ = &buffer;
if (label_)
label_->setBuffer(buffer);