Le 08/04/2017 à 23:05, Jean-Marc Lasgouttes a écrit :

Also, I do not understand this (I know it is the same as the old code)
+    explicit Inset(Inset const &) : buffer_(0) {}

What is this good for? The semantics look quite broken to me. Is this
even used? (I guess we should make it private to find out).

Like in InsetMathHull and InsetMathNest, I imagine that this is meant to
implement some sort of cache that one invalidates on copy. It is used in
all the Inset*::clone functions for a start.

operator= on the other hand is used nowhere, so the difference does not matter. In the attached I even undefine it.

FileName:
This would be automatically copyable and movable if not for the use of
the pointer to implementation.

What is the problem with the pointer?

For motivations see for instance
<https://oliora.github.io/2015/12/29/pimpl-and-rule-of-zero.html>.

As long as the implementation does
not contain a backpointer, I would say that copying the pointer (and
setting to null in the original?

This is what I propose to do automatically.

Is this supposed to go through a
destructor at some time?)

Yes, one must be careful about custom destructors with move
operators. There is no magic ensuring that the destructor is not
called after a move.

should be good enough to won the contents.

There is a solution here:
<https://oliora.github.io/2015/12/29/pimpl-and-rule-of-zero.html>. If we
used spimpl.h from there, then all the custom destructor and copies
could be removed, and the moves would be generated automatically. In
fact this could be used to simplify other copyable classes with a
pointer to implementation. Do you think the Boost license allow its
inclusion in src/support?

I have to take a look.

Thanks.


InsetMathNest and InsetMathHull:
To do this one should define a template cached<X> that
consists in X where the copy is overridden to reset the value (assuming
it is very important to do this).

I really do not know what this thing is.


I am thinking about something along the lines of the attached patches.
But to be clear, one should not expect any performance gain. Only some
review, clarification, and simplification of the code.

Speaking of review, I found that setMouseHover was never used, making
the variable useless. What do you think?

Guillaume
>From 9e0a2bc9ca8b496b5af488634eef905a9f837170 Mon Sep 17 00:00:00 2001
From: Guillaume MM <g...@lyx.org>
Date: Sun, 9 Apr 2017 21:43:33 +0200
Subject: [PATCH 1/3] InsetMathHull: let move operators be defined
 automatically

---
 src/CutAndPaste.cpp              |  11 +++--
 src/mathed/InsetMathHull.cpp     | 101 ++++++++++++++-------------------------
 src/mathed/InsetMathHull.h       |  19 ++++----
 src/mathed/InsetMathNest.cpp     |  33 +++++--------
 src/mathed/InsetMathNest.h       |  26 +++++-----
 src/mathed/InsetMathRef.cpp      |   4 +-
 src/mathed/MathMacro.cpp         |  11 -----
 src/mathed/MathMacroTemplate.cpp |   4 +-
 src/support/unique_ptr.h         |  29 +++++++++++
 9 files changed, 113 insertions(+), 125 deletions(-)

diff --git a/src/CutAndPaste.cpp b/src/CutAndPaste.cpp
index 17dbdc6..e625ebe 100644
--- a/src/CutAndPaste.cpp
+++ b/src/CutAndPaste.cpp
@@ -252,16 +252,17 @@ pasteSelectionHelper(DocIterator const & cur, ParagraphList const & parlist,
 		case MATH_HULL_CODE: {
 			// check for equation labels and resolve duplicates
 			InsetMathHull * ins = it->asInsetMath()->asHullInset();
-			std::vector<InsetLabel *> labels = ins->getLabels();
+			std::vector<std::unique_ptr<InsetLabel>> const & labels =
+				ins->getLabels();
 			for (size_t i = 0; i != labels.size(); ++i) {
 				if (!labels[i])
 					continue;
-				InsetLabel * lab = labels[i];
-				docstring const oldname = lab->getParam("name");
-				lab->updateLabel(oldname);
+				InsetLabel & lab = *labels[i];
+				docstring const oldname = lab.getParam("name");
+				lab.updateLabel(oldname);
 				// We need to update the buffer reference cache.
 				need_update = true;
-				docstring const newname = lab->getParam("name");
+				docstring const newname = lab.getParam("name");
 				if (oldname == newname)
 					continue;
 				// adapt the references
diff --git a/src/mathed/InsetMathHull.cpp b/src/mathed/InsetMathHull.cpp
index 38cdd26..d5b9318 100644
--- a/src/mathed/InsetMathHull.cpp
+++ b/src/mathed/InsetMathHull.cpp
@@ -195,12 +195,10 @@ docstring hullName(HullType type)
 	return from_ascii("none");
 }
 
-static InsetLabel * dummy_pointer = 0;
-
 InsetMathHull::InsetMathHull(Buffer * buf)
 	: InsetMathGrid(buf, 1, 1), type_(hullNone), numbered_(1, NUMBER),
-	  numbers_(1, empty_docstring()), label_(1, dummy_pointer),
-	  preview_(new RenderPreview(this))
+	  numbers_(1, empty_docstring()), label_(1),
+	  preview_(make_unique<RenderPreview>(this))
 {
 	//lyxerr << "sizeof InsetMath: " << sizeof(InsetMath) << endl;
 	//lyxerr << "sizeof MetricsInfo: " << sizeof(MetricsInfo) << endl;
@@ -214,8 +212,8 @@ InsetMathHull::InsetMathHull(Buffer * buf)
 
 InsetMathHull::InsetMathHull(Buffer * buf, HullType type)
 	: InsetMathGrid(buf, getCols(type), 1), type_(type), numbered_(1, NUMBER),
-	  numbers_(1, empty_docstring()), label_(1, dummy_pointer),
-	  preview_(new RenderPreview(this))
+	  numbers_(1, empty_docstring()), label_(1),
+	  preview_(make_unique<RenderPreview>(this))
 {
 	buffer_ = buf;
 	initMath();
@@ -225,42 +223,23 @@ InsetMathHull::InsetMathHull(Buffer * buf, HullType type)
 
 InsetMathHull::InsetMathHull(InsetMathHull const & other) : InsetMathGrid(other)
 {
-	operator=(other);
-}
-
-
-InsetMathHull::~InsetMathHull()
-{
-	for (size_t i = 0; i < label_.size(); ++i)
-		delete label_[i];
-}
-
-
-Inset * InsetMathHull::clone() const
-{
-	return new InsetMathHull(*this);
-}
-
-
-InsetMathHull & InsetMathHull::operator=(InsetMathHull const & other)
-{
-	if (this == &other)
-		return *this;
-	InsetMathGrid::operator=(other);
 	type_  = other.type_;
 	numbered_ = other.numbered_;
 	numbers_ = other.numbers_;
 	buffer_ = other.buffer_;
-	for (size_t i = 0; i < label_.size(); ++i)
-		delete label_[i];
-	label_ = other.label_;
-	for (size_t i = 0; i != label_.size(); ++i) {
-		if (label_[i])
-			label_[i] = new InsetLabel(*label_[i]);
-	}
-	preview_.reset(new RenderPreview(*other.preview_, this));
-
-	return *this;
+	for (size_t i = 0; i < other.label_.size(); ++i)
+		if (other.label_[i])
+			label_[i] = make_unique<InsetLabel>(*other.label_[i]);
+	preview_ = make_unique<RenderPreview>(*other.preview_, this);
+}
+
+
+InsetMathHull::~InsetMathHull() = default;
+
+
+Inset * InsetMathHull::clone() const
+{
+	return new InsetMathHull(*this);
 }
 
 
@@ -881,7 +860,7 @@ bool InsetMathHull::notifyCursorLeaves(Cursor const & old, Cursor & cur)
 docstring InsetMathHull::label(row_type row) const
 {
 	LASSERT(row < nrows(), return docstring());
-	if (InsetLabel * il = label_[row])
+	if (unique_ptr<InsetLabel> const & il = label_[row])
 		return il->screenLabel();
 	return docstring();
 }
@@ -891,10 +870,9 @@ void InsetMathHull::label(row_type row, docstring const & label)
 {
 	//lyxerr << "setting label '" << label << "' for row " << row << endl;
 	if (label_[row]) {
-		if (label.empty()) {
-			delete label_[row];
-			label_[row] = dummy_pointer;
-		} else {
+		if (label.empty())
+			label_[row] = nullptr;
+		else {
 			if (buffer_)
 				label_[row]->updateLabelAndRefs(label);
 			else
@@ -904,7 +882,7 @@ void InsetMathHull::label(row_type row, docstring const & label)
 	}
 	InsetCommandParams p(LABEL_CODE);
 	p["name"] = label;
-	label_[row] = new InsetLabel(buffer_, p);
+	label_[row] = make_unique<InsetLabel>(buffer_, p);
 	if (buffer_)
 		label_[row]->setBuffer(buffer());
 }
@@ -913,10 +891,8 @@ void InsetMathHull::label(row_type row, docstring const & label)
 void InsetMathHull::numbered(row_type row, Numbered num)
 {
 	numbered_[row] = num;
-	if (!numbered(row) && label_[row]) {
-		delete label_[row];
-		label_[row] = 0;
-	}
+	if (!numbered(row) && label_[row])
+		label_[row] = nullptr;
 }
 
 
@@ -1243,7 +1219,7 @@ void InsetMathHull::addRow(row_type row)
 
 	bool numbered = numberedType();
 	// Move the number and raw pointer, do not call label() (bug 7511)
-	InsetLabel * label = dummy_pointer;
+	unique_ptr<InsetLabel> label;
 	docstring number = empty_docstring();
 	if (type_ == hullMultline) {
 		if (row + 1 == nrows())  {
@@ -1256,7 +1232,7 @@ void InsetMathHull::addRow(row_type row)
 
 	numbered_.insert(numbered_.begin() + row + 1, numbered ? NUMBER : NONUMBER);
 	numbers_.insert(numbers_.begin() + row + 1, number);
-	label_.insert(label_.begin() + row + 1, label);
+	label_.insert(label_.begin() + row + 1, move(label));
 	InsetMathGrid::addRow(row);
 }
 
@@ -1292,7 +1268,6 @@ void InsetMathHull::delRow(row_type row)
 		row--;
 	numbered_.erase(numbered_.begin() + row);
 	numbers_.erase(numbers_.begin() + row);
-	delete label_[row];
 	label_.erase(label_.begin() + row);
 }
 
@@ -1329,19 +1304,16 @@ void InsetMathHull::glueall(HullType type)
 	MathData ar;
 	for (idx_type i = 0; i < nargs(); ++i)
 		ar.append(cell(i));
-	InsetLabel * label = 0;
-	if (type == hullEquation) {
+	unique_ptr<InsetLabel> tmp_label;
+	if (type == hullEquation)
 		// preserve first non-empty label
-		for (row_type row = 0; row < nrows(); ++row) {
-			if (label_[row]) {
-				label = label_[row];
-				label_[row] = 0;
+		for (unique_ptr<InsetLabel> & i : label_)
+			if (i) {
+				swap(i, tmp_label);
 				break;
 			}
-		}
-	}
 	*this = InsetMathHull(buffer_, hullSimple);
-	label_[0] = label;
+	label_[0] = move(tmp_label);
 	cell(0) = ar;
 	setDefaults();
 }
@@ -2300,7 +2272,7 @@ void InsetMathHull::read(Lexer & lex)
 {
 	MathAtom at;
 	mathed_parse_normal(buffer_, at, lex, Parse::TRACKMACRO);
-	operator=(*at->asHullInset());
+	operator=(move(*at->asHullInset()));
 }
 
 
@@ -2309,7 +2281,7 @@ bool InsetMathHull::readQuiet(Lexer & lex)
 	MathAtom at;
 	bool success = mathed_parse_normal(buffer_, at, lex, Parse::QUIET);
 	if (success)
-		operator=(*at->asHullInset());
+		operator=(move(*at->asHullInset()));
 	return success;
 }
 
@@ -2547,10 +2519,9 @@ docstring InsetMathHull::xhtml(XHTMLStream & xs, OutputParams const & op) const
 	// we output all the labels just at the beginning of the equation.
 	// this should be fine.
 	for (size_t i = 0; i != label_.size(); ++i) {
-		InsetLabel const * const il = label_[i];
-		if (!il)
+		if (!label_[i])
 			continue;
-		il->xhtml(xs, op);
+		label_[i]->xhtml(xs, op);
 	}
 
 	// FIXME Eventually we would like to do this inset by inset.
diff --git a/src/mathed/InsetMathHull.h b/src/mathed/InsetMathHull.h
index bae2653..b9e96ec 100644
--- a/src/mathed/InsetMathHull.h
+++ b/src/mathed/InsetMathHull.h
@@ -31,6 +31,14 @@ class RenderPreview;
 /// This provides an interface between "LyX insets" and "LyX math insets"
 class InsetMathHull : public InsetMathGrid {
 public:
+	~InsetMathHull();//override
+	InsetMathHull(InsetMathHull &&) = default;
+	InsetMathHull & operator=(InsetMathHull &&) = default;
+protected:
+	explicit InsetMathHull(InsetMathHull const &);
+	InsetMathHull & operator=(InsetMathHull const &) = delete;
+
+public:
 	/// How a line is numbered
 	enum Numbered {
 		/// not numbered, LaTeX code \\nonumber if line differs from inset
@@ -44,8 +52,7 @@ public:
 	InsetMathHull(Buffer * buf);
 	///
 	InsetMathHull(Buffer * buf, HullType type);
-	///
-	virtual ~InsetMathHull();
+
 	///
 	void setBuffer(Buffer &);
 	///
@@ -54,8 +61,6 @@ public:
 	void addToToc(DocIterator const & di, bool output_active,
 				  UpdateType utype, TocBackend & backend) const;
 	///
-	InsetMathHull & operator=(InsetMathHull const &);
-	///
 	mode_type currentMode() const;
 	///
 	void metrics(MetricsInfo & mi, Dimension & dim) const;
@@ -72,7 +77,7 @@ public:
 	///
 	void label(row_type row, docstring const & label);
 	///
-	std::vector<InsetLabel *> const & getLabels() { return label_; }
+	std::vector<std::unique_ptr<InsetLabel>> const & getLabels() { return label_; }
 	///
 	ColorCode backgroundColor(PainterInfo const &) const;
 	///
@@ -193,8 +198,6 @@ public:
 	bool confirmDeletion() const { return nargs() != 1 || !cell(0).empty(); }
 
 protected:
-	InsetMathHull(InsetMathHull const &);
-
 	virtual void doDispatch(Cursor & cur, FuncRequest & cmd);
 
 	/// do we want to handle this event?
@@ -268,7 +271,7 @@ private:
 	///
 	std::vector<docstring> numbers_;
 	///
-	std::vector<InsetLabel *> label_;
+	std::vector<std::unique_ptr<InsetLabel>> label_;
 	///
 	unique_ptr<RenderPreview> preview_;
 	///
diff --git a/src/mathed/InsetMathNest.cpp b/src/mathed/InsetMathNest.cpp
index 596e32a..3358a9e 100644
--- a/src/mathed/InsetMathNest.cpp
+++ b/src/mathed/InsetMathNest.cpp
@@ -90,28 +90,12 @@ InsetMathNest::InsetMathNest(Buffer * buf, idx_type nargs)
 }
 
 
-InsetMathNest::InsetMathNest(InsetMathNest const & inset)
-	: InsetMath(inset), cells_(inset.cells_), lock_(inset.lock_)
-{}
-
-
 InsetMathNest::~InsetMathNest()
 {
-	map<BufferView const *, bool>::iterator it = mouse_hover_.begin();
-	map<BufferView const *, bool>::iterator end = mouse_hover_.end();
-	for (; it != end; ++it)
-		if (it->second)
-			it->first->clearLastInset(this);
-}
-
-
-InsetMathNest & InsetMathNest::operator=(InsetMathNest const & inset)
-{
-	cells_ = inset.cells_;
-	lock_ = inset.lock_;
-	mouse_hover_.clear();
-	InsetMath::operator=(inset);
-	return *this;
+	if (mouse_hover_)
+		for (pair<BufferView const *, bool> p : *mouse_hover_)
+			if (p.second)
+				p.first->clearLastInset(this);
 }
 
 
@@ -385,11 +369,18 @@ void InsetMathNest::latex(otexstream & os, OutputParams const & runparams) const
 bool InsetMathNest::setMouseHover(BufferView const * bv, bool mouse_hover)
 	const
 {
-	mouse_hover_[bv] = mouse_hover;
+	if (mouse_hover_)
+		(*mouse_hover_)[bv] = mouse_hover;
 	return true;
 }
 
 
+bool InsetMathNest::mouseHovered(BufferView const * bv) const
+{
+	return mouse_hover_ && (*mouse_hover_)[bv];
+}
+
+
 bool InsetMathNest::notifyCursorLeaves(Cursor const & /*old*/, Cursor & /*cur*/)
 {
 	// FIXME: look here
diff --git a/src/mathed/InsetMathNest.h b/src/mathed/InsetMathNest.h
index 51670a2..b393dfe 100644
--- a/src/mathed/InsetMathNest.h
+++ b/src/mathed/InsetMathNest.h
@@ -17,6 +17,8 @@
 
 #include <map>
 
+#include "support/unique_ptr.h"
+
 namespace lyx {
 
 /** Abstract base class for all math objects that contain nested items.
@@ -26,10 +28,18 @@ namespace lyx {
 
 class InsetMathNest : public InsetMath {
 public:
+	///
+	~InsetMathNest();//override
+	InsetMathNest(InsetMathNest &&) = default;
+	InsetMathNest & operator=(InsetMathNest &&) = default;
+protected:
+	explicit InsetMathNest(InsetMathNest const &) = default;
+	InsetMathNest & operator=(InsetMathNest const &) = delete;
+
+public:
 	/// nestinsets have a fixed size to start with
 	InsetMathNest(Buffer * buf, idx_type ncells);
-	///
-	virtual ~InsetMathNest();
+
 	///
 	void setBuffer(Buffer &);
 
@@ -107,8 +117,7 @@ public:
 	///
 	bool setMouseHover(BufferView const * bv, bool mouse_hover) const;
 	///
-	bool mouseHovered(BufferView const * bv) const 
-		{ return mouse_hover_[bv]; }
+	bool mouseHovered(BufferView const * bv) const;
 
 	///
 	bool completionSupported(Cursor const &) const;
@@ -134,11 +143,6 @@ public:
 
 protected:
 	///
-	InsetMathNest(InsetMathNest const & inset);
-	///
-	InsetMathNest & operator=(InsetMathNest const &);
-
-	///
 	virtual void doDispatch(Cursor & cur, FuncRequest & cmd);
 	/// do we want to handle this event?
 	bool getStatus(Cursor & cur, FuncRequest const & cmd,
@@ -192,8 +196,8 @@ protected:
 	/// if the inset is locked, it can't be entered with the cursor
 	bool lock_;
 	///
-	mutable std::map<BufferView const *, bool> mouse_hover_;
-};	
+	cache_ptr<std::map<BufferView const *, bool>> mouse_hover_;
+};
 
 
 
diff --git a/src/mathed/InsetMathRef.cpp b/src/mathed/InsetMathRef.cpp
index 22807f1..e911d13 100644
--- a/src/mathed/InsetMathRef.cpp
+++ b/src/mathed/InsetMathRef.cpp
@@ -67,7 +67,7 @@ void InsetMathRef::doDispatch(Cursor & cur, FuncRequest & cmd)
 			MathData ar;
 			if (createInsetMath_fromDialogStr(cmd.argument(), ar)) {
 				cur.recordUndo();
-				*this = *ar[0].nucleus()->asRefInset();
+				*this = move(*ar[0].nucleus()->asRefInset());
 				break;
 			}
 		}
@@ -229,7 +229,7 @@ void InsetMathRef::changeTarget(docstring const & target)
 	Buffer & buf = buffer();
 	if (createInsetMath_fromDialogStr(
 	    from_utf8(InsetCommand::params2string(icp)), ar)) {
-		*this = *ar[0].nucleus()->asRefInset();
+		*this = move(*ar[0].nucleus()->asRefInset());
 		// FIXME audit setBuffer calls
 		setBuffer(buf);
 	}
diff --git a/src/mathed/MathMacro.cpp b/src/mathed/MathMacro.cpp
index 4bd14d6..edfaca7 100644
--- a/src/mathed/MathMacro.cpp
+++ b/src/mathed/MathMacro.cpp
@@ -303,17 +303,6 @@ MathMacro::MathMacro(MathMacro const & that)
 }
 
 
-MathMacro & MathMacro::operator=(MathMacro const & that)
-{
-	if (&that == this)
-		return *this;
-	InsetMathNest::operator=(that);
-	*d = *that.d;
-	d->updateChildren(this);
-	return *this;
-}
-
-
 MathMacro::~MathMacro()
 {
 	delete d;
diff --git a/src/mathed/MathMacroTemplate.cpp b/src/mathed/MathMacroTemplate.cpp
index d4cf4cf..8b0b6a2 100644
--- a/src/mathed/MathMacroTemplate.cpp
+++ b/src/mathed/MathMacroTemplate.cpp
@@ -436,7 +436,7 @@ bool MathMacroTemplate::fromString(docstring const & str)
 		// The macro template does not make sense after this.
 		return false;
 	}
-	operator=( *(ar[0]->asMacroTemplate()) );
+	operator=(move(*ar[0]->asMacroTemplate()));
 
 	updateLook();
 	return true;
@@ -1157,7 +1157,7 @@ void MathMacroTemplate::read(Lexer & lex)
 		lyxerr << "Read: " << to_utf8(asString(ar)) << endl;
 		return;
 	}
-	operator=( *(ar[0]->asMacroTemplate()) );
+	operator=(move(*(ar[0]->asMacroTemplate())));
 
 	updateLook();
 }
diff --git a/src/support/unique_ptr.h b/src/support/unique_ptr.h
index f9e049c..eb8582a 100644
--- a/src/support/unique_ptr.h
+++ b/src/support/unique_ptr.h
@@ -71,4 +71,33 @@ make_unique(Args&&...) = delete;
 
 #endif // definition of make_unique
 
+
+namespace lyx {
+
+// A copyable unique_ptr that does nothing on copy. Use the enclosed object
+// default constructor for default constructor and for copy creation. The idea
+// is that if the pointer is null then it means that the object that contains it
+// has been moved from. Note: I am not sure that using cache_ptr is good
+// design, but it improves on the old code.
+template<class X>
+class cache_ptr : public unique_ptr<X> {
+#if !(defined(__GNUC__) && (__GNUC__ == 4) && (__GNUC_MINOR__ == 6))
+	static_assert(std::is_default_constructible<X>::value,
+	              "cache_ptr only stores default-constructible objects!");
+#endif
+public:
+	cache_ptr() : unique_ptr<X>(make_unique<X>()) {}
+	cache_ptr(unique_ptr<X> p) : unique_ptr<X>(move(p)) {}
+	cache_ptr(cache_ptr &&) = default;
+	cache_ptr & operator=(cache_ptr &&) = default;
+	cache_ptr(cache_ptr const &) : cache_ptr() {}
+	cache_ptr & operator=(cache_ptr const &)
+	{
+		operator=(cache_ptr());
+		return *this;
+	}
+};
+
+} // namespace lyx
+
 #endif // LYX_UNIQUE_PTR_H
-- 
2.7.4

>From 10f116c799906de719cd032b8507c771b4d2dc5b Mon Sep 17 00:00:00 2001
From: Guillaume MM <g...@lyx.org>
Date: Sun, 2 Apr 2017 19:58:44 +0200
Subject: [PATCH 2/3] Review and clarification of the copy policy of Inset

Fix coverity's suggestion to define a move constructor

It is still deleted sometimes, see FIXMEs.
---
 src/insets/Inset.h             | 18 +++++++++++++-----
 src/insets/InsetBibitem.h      | 14 +++++++++++---
 src/insets/InsetBibtex.h       | 13 ++++++++++---
 src/insets/InsetCitation.h     | 13 +++++++++++--
 src/insets/InsetCollapsable.h  | 15 +++++++++++----
 src/insets/InsetCommand.cpp    | 14 --------------
 src/insets/InsetCommand.h      | 17 +++++++++++------
 src/insets/InsetExternal.h     | 18 +++++++++++-------
 src/insets/InsetFlex.h         | 11 +++++++----
 src/insets/InsetGraphics.h     | 17 +++++++++++------
 src/insets/InsetIPA.cpp        | 16 ----------------
 src/insets/InsetIPA.h          | 24 ++++++++++++------------
 src/insets/InsetIPAMacro.cpp   |  4 ----
 src/insets/InsetIPAMacro.h     |  2 --
 src/insets/InsetInclude.h      | 21 +++++++++++----------
 src/insets/InsetListings.h     | 13 +++++++++++--
 src/insets/InsetNote.h         | 13 +++++++++++--
 src/insets/InsetPhantom.h      | 13 +++++++++++--
 src/insets/InsetPreview.cpp    | 16 ----------------
 src/insets/InsetPreview.h      | 12 ++++++------
 src/insets/InsetRef.h          | 11 +++++++----
 src/insets/InsetScript.cpp     |  5 -----
 src/insets/InsetScript.h       |  2 --
 src/insets/InsetTabular.h      | 15 +++++++++++----
 src/insets/InsetText.h         |  8 ++++++--
 src/insets/InsetWrap.h         | 13 +++++++++++--
 src/mathed/InsetMathSpace.cpp  |  2 +-
 src/mathed/MathMacro.h         | 17 +++++++++++------
 src/mathed/MathMacroTemplate.h |  4 ++--
 29 files changed, 207 insertions(+), 154 deletions(-)

diff --git a/src/insets/Inset.h b/src/insets/Inset.h
index 3d93904..8ad2e04 100644
--- a/src/insets/Inset.h
+++ b/src/insets/Inset.h
@@ -85,6 +85,18 @@ static int const TOC_ENTRY_LENGTH = 120;
 
 class Inset {
 public:
+	/// virtual base class destructor
+	virtual ~Inset() {}
+	/// default move operators
+	Inset(Inset &&) = default;
+	Inset & operator=(Inset &&) = default;
+protected:
+	/// explicit copy idiom
+	/// use copy-then-move-assign instead of copy assignment
+	explicit Inset(Inset const &) : buffer_(0) {}
+	Inset & operator=(Inset const &) = delete;
+
+public:
 	///
 	enum EntryDirection {
 		ENTRY_DIRECTION_IGNORE,
@@ -104,9 +116,6 @@ public:
 	/// type for column numbers
 	typedef size_t     col_type;
 
-	/// virtual base class destructor
-	virtual ~Inset() {}
-
 	/// change associated Buffer
 	virtual void setBuffer(Buffer & buffer);
 	/// reset associated Buffer to null value
@@ -589,8 +598,7 @@ public:
 
 protected:
 	/// Constructors
-	Inset(Buffer * buf) : buffer_(buf) {}
-	Inset(Inset const &) : buffer_(0) {}
+	explicit Inset(Buffer * buf) : buffer_(buf) {}
 
 	/// replicate ourselves
 	friend class InsetList;
diff --git a/src/insets/InsetBibitem.h b/src/insets/InsetBibitem.h
index 41497e1..7efde9c 100644
--- a/src/insets/InsetBibitem.h
+++ b/src/insets/InsetBibitem.h
@@ -34,11 +34,19 @@ class InsetBibitem : public InsetCommand
 {
 public:
 	///
+	~InsetBibitem();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetBibitem(InsetBibitem &&) = delete;
+	InsetBibitem & operator=(InsetBibitem &&) = delete;
+protected:
+	explicit InsetBibitem(InsetBibitem const &) = default;
+	InsetBibitem & operator=(InsetBibitem const &) = delete;
+
+public:
+	///
 	InsetBibitem(Buffer *, InsetCommandParams const &);
 	///
-	~InsetBibitem();
-
-	///
 	void updateCommand(docstring const & new_key, bool dummy = false);
 
 	/// \name Public functions inherited from Inset class
diff --git a/src/insets/InsetBibtex.h b/src/insets/InsetBibtex.h
index 4f6f68c..a0a794e 100644
--- a/src/insets/InsetBibtex.h
+++ b/src/insets/InsetBibtex.h
@@ -28,11 +28,18 @@ namespace support {
 class InsetBibtex : public InsetCommand {
 public:
 	///
+	~InsetBibtex();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetBibtex(InsetBibtex &&) = delete;
+	InsetBibtex & operator=(InsetBibtex &&) = delete;
+protected:
+	explicit InsetBibtex(InsetBibtex const &) = default;
+	InsetBibtex & operator=(InsetBibtex const &) = delete;
+
+public:
 	InsetBibtex(Buffer *, InsetCommandParams const &);
 	///
-	~InsetBibtex();
-
-	///
 	support::FileNamePairList getBibFiles() const;
 	///
 	bool addDatabase(docstring const &);
diff --git a/src/insets/InsetCitation.h b/src/insets/InsetCitation.h
index 18a9305..c46c978 100644
--- a/src/insets/InsetCitation.h
+++ b/src/insets/InsetCitation.h
@@ -29,9 +29,18 @@ class InsetCitation : public InsetCommand
 {
 public:
 	///
+	~InsetCitation();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetCitation(InsetCitation &&) = delete;
+	InsetCitation & operator=(InsetCitation &&) = delete;
+protected:
+	explicit InsetCitation(InsetCitation const &) = default;
+	InsetCitation & operator=(InsetCitation const &) = delete;
+
+public:
+	///
 	InsetCitation(Buffer * buf, InsetCommandParams const &);
-	///
-	~InsetCitation();
 
 	///
 	bool addKey(std::string const & key);
diff --git a/src/insets/InsetCollapsable.h b/src/insets/InsetCollapsable.h
index a426db0..a009d04 100644
--- a/src/insets/InsetCollapsable.h
+++ b/src/insets/InsetCollapsable.h
@@ -33,12 +33,19 @@ namespace frontend { class Painter; }
 class InsetCollapsable : public InsetText {
 public:
 	///
+	~InsetCollapsable();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetCollapsable(InsetCollapsable &&) = delete;
+	InsetCollapsable & operator=(InsetCollapsable &&) = delete;
+protected:
+	explicit InsetCollapsable(InsetCollapsable const & rhs);
+	InsetCollapsable & operator=(InsetCollapsable const &) = delete;
+
+public:
+	///
 	InsetCollapsable(Buffer *, InsetText::UsePlain = InsetText::PlainLayout);
 	///
-	InsetCollapsable(InsetCollapsable const & rhs);
-	///
-	virtual ~InsetCollapsable();
-	///
 	InsetCollapsable * asInsetCollapsable() { return this; }
 	///
 	InsetCollapsable const * asInsetCollapsable() const { return this; }
diff --git a/src/insets/InsetCommand.cpp b/src/insets/InsetCommand.cpp
index fe10466..b23c116 100644
--- a/src/insets/InsetCommand.cpp
+++ b/src/insets/InsetCommand.cpp
@@ -67,20 +67,6 @@ InsetCommand::InsetCommand(InsetCommand const & rhs)
 {}
 
 
-InsetCommand & InsetCommand::operator=(InsetCommand const & rhs)
-{
-	if (&rhs == this)
-		return *this;
-
-	Inset::operator=(rhs);
-	p_ = rhs.p_;
-	mouse_hover_.clear();
-	button_ = RenderButton();
-
-	return *this;
-}
-
-
 InsetCommand::~InsetCommand()
 {
 	if (p_.code() != NO_CODE)
diff --git a/src/insets/InsetCommand.h b/src/insets/InsetCommand.h
index 78e6d7f..82a4d60 100644
--- a/src/insets/InsetCommand.h
+++ b/src/insets/InsetCommand.h
@@ -35,14 +35,19 @@ class InsetCommand : public Inset
 {
 public:
 	///
+	~InsetCommand();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetCommand(InsetCommand &&) = delete;
+	InsetCommand & operator=(InsetCommand &&) = delete;
+protected:
+	explicit InsetCommand(InsetCommand const & rhs);
+	InsetCommand & operator=(InsetCommand const &) = delete;
+
+public:
+	///
 	InsetCommand(Buffer *, InsetCommandParams const &);
 	///
-	InsetCommand(InsetCommand const & rhs);
-	///
-	InsetCommand & operator=(InsetCommand const & rhs);
-	///
-	virtual ~InsetCommand();
-	///
 	InsetCommand * asInsetCommand() { return this; }
 	///
 	InsetCommand const * asInsetCommand() const { return this; }
diff --git a/src/insets/InsetExternal.h b/src/insets/InsetExternal.h
index 5eca664..19fcccc 100644
--- a/src/insets/InsetExternal.h
+++ b/src/insets/InsetExternal.h
@@ -92,14 +92,20 @@ class RenderBase;
 ///
 class InsetExternal : public Inset, public boost::signals2::trackable
 {
-	// Disable assignment operator, since it is not used, and it is too
-	// complicated to implement it consistently with the copy constructor
-	InsetExternal & operator=(InsetExternal const &);
+public:
+	///
+	~InsetExternal();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetExternal(InsetExternal &&) = delete;
+	InsetExternal & operator=(InsetExternal &&) = delete;
+protected:
+	explicit InsetExternal(InsetExternal const &);
+	InsetExternal & operator=(InsetExternal const &) = delete;
+
 public:
 	InsetExternal(Buffer *);
 	///
-	~InsetExternal();
-	///
 	static void string2params(std::string const &, Buffer const &,
 				  InsetExternalParams &);
 	///
@@ -124,8 +130,6 @@ public:
 				  UpdateType utype, TocBackend & backend) const;
 private:
 	///
-	InsetExternal(InsetExternal const &);
-	///
 	InsetCode lyxCode() const { return EXTERNAL_CODE; }
 	///
 	bool hasSettings() const { return true; }
diff --git a/src/insets/InsetFlex.h b/src/insets/InsetFlex.h
index 8277002..221f9f6 100644
--- a/src/insets/InsetFlex.h
+++ b/src/insets/InsetFlex.h
@@ -22,6 +22,13 @@ namespace lyx {
 */
 class InsetFlex : public InsetCollapsable {
 public:
+	InsetFlex(InsetFlex &&) = default;
+	InsetFlex & operator=(InsetFlex &&) = default;
+protected:
+	explicit InsetFlex(InsetFlex const &);
+	InsetFlex & operator=(InsetFlex const &) = delete;
+
+public:
 	///
 	InsetFlex(Buffer *, std::string const & layoutName);
 	///
@@ -46,10 +53,6 @@ public:
 	///
 	void updateBuffer(ParIterator const & it, UpdateType utype);
 
-protected:
-	///
-	InsetFlex(InsetFlex const &);
-
 private:
 	///
 	Inset * clone() const { return new InsetFlex(*this); }
diff --git a/src/insets/InsetGraphics.h b/src/insets/InsetGraphics.h
index 88ded43..f72737e 100644
--- a/src/insets/InsetGraphics.h
+++ b/src/insets/InsetGraphics.h
@@ -34,11 +34,19 @@ class InsetGraphics : public Inset
 {
 public:
 	///
+	~InsetGraphics();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetGraphics(InsetGraphics &&) = delete;
+	InsetGraphics & operator=(InsetGraphics &&) = delete;
+protected:
+	explicit InsetGraphics(InsetGraphics const &);
+	InsetGraphics & operator=(InsetGraphics const &) = delete;
+
+public:
+	///
 	InsetGraphics(Buffer * buf);
 	///
-	~InsetGraphics();
-
-	///
 	static void string2params(std::string const & data,
 				  Buffer const & buffer,
 				  InsetGraphicsParams &);
@@ -59,9 +67,6 @@ public:
 
 private:
 	///
-	InsetGraphics(InsetGraphics const &);
-
-	///
 	bool isLabeled() const { return true; }
 	void metrics(MetricsInfo &, Dimension &) const;
 	///
diff --git a/src/insets/InsetIPA.cpp b/src/insets/InsetIPA.cpp
index 29ed000..f307ad0 100644
--- a/src/insets/InsetIPA.cpp
+++ b/src/insets/InsetIPA.cpp
@@ -44,10 +44,6 @@ InsetIPA::InsetIPA(Buffer * buf)
 }
 
 
-InsetIPA::~InsetIPA() 
-{}
-
-
 InsetIPA::InsetIPA(InsetIPA const & other)
 	: InsetText(other)
 {
@@ -55,18 +51,6 @@ InsetIPA::InsetIPA(InsetIPA const & other)
 }
 
 
-InsetIPA & InsetIPA::operator=(InsetIPA const & other)
-{
-	if (&other == this)
-		return *this;
-
-	InsetText::operator=(other);
-	preview_.reset(new RenderPreview(*other.preview_, this));
-
-	return *this;
-}
-
-
 void InsetIPA::write(ostream & os) const
 {
 	os << "IPA" << "\n";
diff --git a/src/insets/InsetIPA.h b/src/insets/InsetIPA.h
index 84db92e..ced4530 100644
--- a/src/insets/InsetIPA.h
+++ b/src/insets/InsetIPA.h
@@ -29,16 +29,16 @@ namespace graphics {
 
 /// An IPA inset with instant preview
 class InsetIPA : public InsetText {
-	
+public:
+	InsetIPA(InsetIPA &&) = default;
+	InsetIPA & operator=(InsetIPA &&) = default;
+protected:
+	explicit InsetIPA(InsetIPA const &);
+	InsetIPA & operator=(InsetIPA const &) = delete;
+
 public:
 	///
 	InsetIPA(Buffer *);
-	///
-	~InsetIPA();
-	///
-	InsetIPA(InsetIPA const & other);
-	///
-	InsetIPA & operator=(InsetIPA const & other);
 
 	/// \name Methods inherited from Inset class
 	//@{
@@ -47,11 +47,11 @@ public:
 	bool neverIndent() const { return true; }
 
 	bool forceLocalFontSwitch() const { return true; }
-	
+
 	InsetCode lyxCode() const { return IPA_CODE; }
-	
+
 	docstring layoutName() const { return from_ascii("IPA"); }
-	
+
 	bool descendable(BufferView const & /*bv*/) const { return true; }
 
 	void metrics(MetricsInfo & mi, Dimension & dim) const;
@@ -73,7 +73,7 @@ public:
 	void write(std::ostream & os) const;
 
 	void edit(Cursor & cur, bool front, EntryDirection entry_from);
-	
+
 	///
 	void latex(otexstream &, OutputParams const &) const;
 	///
@@ -85,7 +85,7 @@ public:
 	///
 	bool insetAllowed(InsetCode code) const;
 	//@}
-	
+
 protected:
 	/// Retrieves the preview state. Returns true if preview
 	/// is enabled and the preview image is availabled.
diff --git a/src/insets/InsetIPAMacro.cpp b/src/insets/InsetIPAMacro.cpp
index 7852486..bed0a19 100644
--- a/src/insets/InsetIPAMacro.cpp
+++ b/src/insets/InsetIPAMacro.cpp
@@ -133,10 +133,6 @@ InsetIPADeco::InsetIPADeco(Buffer * buf, string const & label)
 }
 
 
-InsetIPADeco::~InsetIPADeco()
-{}
-
-
 docstring InsetIPADeco::layoutName() const
 {
 	return from_ascii("IPADeco:" + ipadecotranslator().find(params_.type));
diff --git a/src/insets/InsetIPAMacro.h b/src/insets/InsetIPAMacro.h
index c29fc49..12052bc 100644
--- a/src/insets/InsetIPAMacro.h
+++ b/src/insets/InsetIPAMacro.h
@@ -51,8 +51,6 @@ public:
 	///
 	InsetIPADeco(Buffer *, std::string const &);
 	///
-	~InsetIPADeco();
-	///
 	static std::string params2string(InsetIPADecoParams const &);
 	///
 	static void string2params(std::string const &, InsetIPADecoParams &);
diff --git a/src/insets/InsetInclude.h b/src/insets/InsetInclude.h
index e616f55..d79f3fa 100644
--- a/src/insets/InsetInclude.h
+++ b/src/insets/InsetInclude.h
@@ -36,15 +36,20 @@ namespace support {
 
 /// for including tex/lyx files
 class InsetInclude : public InsetCommand {
-	// Disable assignment operator, since it is not used, and cannot be
-	// implemented consistently with the copy constructor, because
-	// include_label is const.
-	InsetInclude & operator=(InsetInclude const &);
+public:
+	///
+	~InsetInclude();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetInclude(InsetInclude &&) = delete;
+	InsetInclude & operator=(InsetInclude &&) = delete;
+protected:
+	explicit InsetInclude(InsetInclude const &);
+	InsetInclude & operator=(InsetInclude const &) = delete;
+
 public:
 	///
 	InsetInclude(Buffer * buf, InsetCommandParams const &);
-	///
-	~InsetInclude();
 
 	///
 	void setChildBuffer(Buffer * buffer);
@@ -127,10 +132,6 @@ public:
 	static bool isCompatibleCommand(std::string const & s);
 	//@}
 
-protected:
-	///
-	InsetInclude(InsetInclude const &);
-
 private:
 	/** Slot receiving a signal that the external file has changed
 	 *  and the preview should be regenerated.
diff --git a/src/insets/InsetListings.h b/src/insets/InsetListings.h
index 902fa04..d1c5f17 100644
--- a/src/insets/InsetListings.h
+++ b/src/insets/InsetListings.h
@@ -31,10 +31,19 @@ class InsetListings : public InsetCaptionable
 {
 public:
 	///
+	~InsetListings();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetListings(InsetListings &&) = delete;
+	InsetListings & operator=(InsetListings &&) = delete;
+protected:
+	explicit InsetListings(InsetListings const &) = default;
+	InsetListings & operator=(InsetListings const &) = delete;
+
+public:
+	///
 	InsetListings(Buffer *, InsetListingsParams const & par = InsetListingsParams());
 	///
-	~InsetListings();
-	///
 	static void string2params(std::string const &, InsetListingsParams &);
 	///
 	static std::string params2string(InsetListingsParams const &);
diff --git a/src/insets/InsetNote.h b/src/insets/InsetNote.h
index d6cc0a6..f2190ac 100644
--- a/src/insets/InsetNote.h
+++ b/src/insets/InsetNote.h
@@ -47,10 +47,19 @@ class InsetNote : public InsetCollapsable
 {
 public:
 	///
+	~InsetNote();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetNote(InsetNote &&) = delete;
+	InsetNote & operator=(InsetNote &&) = delete;
+protected:
+	explicit InsetNote(InsetNote const &) = default;
+	InsetNote & operator=(InsetNote const &) = delete;
+
+public:
+	///
 	InsetNote(Buffer *, std::string const &);
 	///
-	~InsetNote();
-	///
 	static std::string params2string(InsetNoteParams const &);
 	///
 	static void string2params(std::string const &, InsetNoteParams &);
diff --git a/src/insets/InsetPhantom.h b/src/insets/InsetPhantom.h
index 42c3da1..7f9fdff 100644
--- a/src/insets/InsetPhantom.h
+++ b/src/insets/InsetPhantom.h
@@ -47,10 +47,19 @@ class InsetPhantom : public InsetCollapsable
 {
 public:
 	///
+	~InsetPhantom();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetPhantom(InsetPhantom &&) = delete;
+	InsetPhantom & operator=(InsetPhantom &&) = delete;
+protected:
+	explicit InsetPhantom(InsetPhantom const &) = default;
+	InsetPhantom & operator=(InsetPhantom const &) = delete;
+
+public:
+	///
 	InsetPhantom(Buffer *, std::string const &);
 	///
-	~InsetPhantom();
-	///
 	static std::string params2string(InsetPhantomParams const &);
 	///
 	static void string2params(std::string const &, InsetPhantomParams &);
diff --git a/src/insets/InsetPreview.cpp b/src/insets/InsetPreview.cpp
index c306ae9..e7e0383 100644
--- a/src/insets/InsetPreview.cpp
+++ b/src/insets/InsetPreview.cpp
@@ -43,10 +43,6 @@ InsetPreview::InsetPreview(Buffer * buf)
 }
 
 
-InsetPreview::~InsetPreview()
-{}
-
-
 InsetPreview::InsetPreview(InsetPreview const & other)
 	: InsetText(other)
 {
@@ -54,18 +50,6 @@ InsetPreview::InsetPreview(InsetPreview const & other)
 }
 
 
-InsetPreview & InsetPreview::operator=(InsetPreview const & other)
-{
-	if (&other == this)
-		return *this;
-
-	InsetText::operator=(other);
-	preview_.reset(new RenderPreview(*other.preview_, this));
-
-	return *this;
-}
-
-
 void InsetPreview::write(ostream & os) const
 {
 	os << "Preview" << "\n";
diff --git a/src/insets/InsetPreview.h b/src/insets/InsetPreview.h
index f0808d7..a8fce20 100644
--- a/src/insets/InsetPreview.h
+++ b/src/insets/InsetPreview.h
@@ -29,16 +29,16 @@ namespace graphics {
 
 /// An inset with an instant preview
 class InsetPreview : public InsetText {
+public:
+	InsetPreview(InsetPreview &&) = default;
+	InsetPreview & operator=(InsetPreview &&) = default;
+protected:
+	explicit InsetPreview(InsetPreview const &);
+	InsetPreview & operator=(InsetPreview const &) = delete;
 
 public:
 	///
 	InsetPreview(Buffer *);
-	///
-	~InsetPreview();
-	///
-	InsetPreview(InsetPreview const & other);
-	///
-	InsetPreview & operator=(InsetPreview const & other);
 
 	/// \name Methods inherited from Inset class
 	//@{
diff --git a/src/insets/InsetRef.h b/src/insets/InsetRef.h
index 1af1790..1ed5e6c 100644
--- a/src/insets/InsetRef.h
+++ b/src/insets/InsetRef.h
@@ -20,6 +20,13 @@ namespace lyx {
 /// The reference inset
 class InsetRef : public InsetCommand {
 public:
+	InsetRef(InsetRef &&) = default;
+	InsetRef & operator=(InsetRef &&) = default;
+protected:
+	explicit InsetRef(InsetRef const &);
+	InsetRef & operator=(InsetRef const &) = delete;
+
+public:
 	struct type_info {
 		///
 		std::string latex_name;
@@ -95,10 +102,6 @@ public:
 	docstring screenLabel() const { return screen_label_; }
 	//@}
 
-protected:
-	///
-	InsetRef(InsetRef const &);
-
 private:
 	/// \name Private functions inherited from Inset class
 	//@{
diff --git a/src/insets/InsetScript.cpp b/src/insets/InsetScript.cpp
index fec226f..aa49b4e 100644
--- a/src/insets/InsetScript.cpp
+++ b/src/insets/InsetScript.cpp
@@ -140,11 +140,6 @@ InsetScript::InsetScript(Buffer * buf, string const & label)
 }
 
 
-InsetScript::~InsetScript()
-{
-}
-
-
 docstring InsetScript::layoutName() const
 {
 	return from_ascii("Script:" + scripttranslator().find(params_.type));
diff --git a/src/insets/InsetScript.h b/src/insets/InsetScript.h
index 3107b62..ba5f3bf 100644
--- a/src/insets/InsetScript.h
+++ b/src/insets/InsetScript.h
@@ -52,8 +52,6 @@ public:
 	///
 	InsetScript(Buffer *, std::string const &);
 	///
-	~InsetScript();
-	///
 	static std::string params2string(InsetScriptParams const &);
 	///
 	static void string2params(std::string const &, InsetScriptParams &);
diff --git a/src/insets/InsetTabular.h b/src/insets/InsetTabular.h
index bdd21af..a5dcca5 100644
--- a/src/insets/InsetTabular.h
+++ b/src/insets/InsetTabular.h
@@ -849,11 +849,20 @@ class InsetTabular : public Inset
 {
 public:
 	///
+	~InsetTabular();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetTabular(InsetTabular &&) = delete;
+	InsetTabular & operator=(InsetTabular &&) = delete;
+protected:
+	explicit InsetTabular(InsetTabular const &);
+	InsetTabular & operator=(InsetTabular const &) = delete;
+
+public:
+	///
 	InsetTabular(Buffer *, row_type rows = 1,
 		     col_type columns = 1);
 	///
-	~InsetTabular();
-	///
 	void setBuffer(Buffer & buffer);
 
 	///
@@ -1006,8 +1015,6 @@ public:
 
 private:
 	///
-	InsetTabular(InsetTabular const &);
-	///
 	void doDispatch(Cursor & cur, FuncRequest & cmd);
 	///
 	bool getFeatureStatus(Cursor & cur, std::string const & s,
diff --git a/src/insets/InsetText.h b/src/insets/InsetText.h
index eb52bc8..0a71b35 100644
--- a/src/insets/InsetText.h
+++ b/src/insets/InsetText.h
@@ -33,6 +33,12 @@ class TocBuilder;
  */
 class InsetText : public Inset {
 public:
+	InsetText(InsetText &&) = default;
+	InsetText & operator=(InsetText &&) = default;
+	explicit InsetText(InsetText const &);
+	InsetText & operator=(InsetText const &) = delete;
+
+public:
 	enum UsePlain {
 		DefaultLayout,
 		PlainLayout
@@ -43,8 +49,6 @@ public:
 	/// usePlainLayout() from within the constructor.
 	explicit InsetText(Buffer * buffer, UsePlain type = DefaultLayout);
 	///
-	InsetText(InsetText const &);
-	///
 	void setBuffer(Buffer &);
 
 	///
diff --git a/src/insets/InsetWrap.h b/src/insets/InsetWrap.h
index 588a3bc..0f38eb9 100644
--- a/src/insets/InsetWrap.h
+++ b/src/insets/InsetWrap.h
@@ -44,9 +44,18 @@ public:
 class InsetWrap : public InsetCaptionable {
 public:
 	///
-	InsetWrap(Buffer *, std::string const &);
-	///
 	~InsetWrap();
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	InsetWrap(InsetWrap &&) = delete;
+	InsetWrap & operator=(InsetWrap &&) = delete;
+protected:
+	explicit InsetWrap(InsetWrap const &) = default;
+	InsetWrap & operator=(InsetWrap const &) = delete;
+
+public:
+	///
+	InsetWrap(Buffer *, std::string const &);
 	///
 	InsetWrapParams const & params() const { return params_; }
 	///
diff --git a/src/mathed/InsetMathSpace.cpp b/src/mathed/InsetMathSpace.cpp
index 0adce6f..454ad08 100644
--- a/src/mathed/InsetMathSpace.cpp
+++ b/src/mathed/InsetMathSpace.cpp
@@ -322,7 +322,7 @@ void InsetMathSpace::doDispatch(Cursor & cur, FuncRequest & cmd)
 			MathData ar;
 			if (createInsetMath_fromDialogStr(cmd.argument(), ar)) {
 				cur.recordUndo();
-				*this = *ar[0].nucleus()->asSpaceInset();
+				*this = move(*ar[0].nucleus()->asSpaceInset());
 				break;
 			}
 		}
diff --git a/src/mathed/MathMacro.h b/src/mathed/MathMacro.h
index 0d4ba34..57a112a 100644
--- a/src/mathed/MathMacro.h
+++ b/src/mathed/MathMacro.h
@@ -24,15 +24,20 @@ namespace lyx {
 /// This class contains the data for a macro.
 class MathMacro : public InsetMathNest {
 public:
+	///
+	~MathMacro();//override
+	// FIXME: non-trivial destructor should be moved to a unique_ptr before
+	// enabling default move operators
+	MathMacro(MathMacro &&) = delete;
+	MathMacro & operator=(MathMacro &&) = delete;
+protected:
+	explicit MathMacro(MathMacro const &);
+	MathMacro & operator=(MathMacro const &) = delete;
+
+public:
 	/// A macro can be built from an existing template
 	MathMacro(Buffer * buf, docstring const & name);
 	///
-	MathMacro(MathMacro const &);
-	///
-	MathMacro & operator=(MathMacro const &);
-	///
-	~MathMacro();
-	///
 	virtual MathMacro * asMacro() { return this; }
 	///
 	virtual MathMacro const * asMacro() const { return this; }
diff --git a/src/mathed/MathMacroTemplate.h b/src/mathed/MathMacroTemplate.h
index 56fe0ec..09effc1 100644
--- a/src/mathed/MathMacroTemplate.h
+++ b/src/mathed/MathMacroTemplate.h
@@ -82,7 +82,7 @@ public:
 	/// Remove everything from the name which makes it invalid 
 	/// and return true iff it is valid.
 	bool fixNameAndCheckIfValid();
-	
+
 	/// request "external features"
 	virtual void validate(LaTeXFeatures &) const;
 
@@ -116,7 +116,7 @@ protected:
 private:
 	friend class InsetLabelBox;
 	friend class DisplayLabelBox;
-	
+
 	///
 	virtual Inset * clone() const;
 
-- 
2.7.4

>From 31bb8fac2505f8d0bb18d60b853f14a684590b0f Mon Sep 17 00:00:00 2001
From: Guillaume MM <g...@lyx.org>
Date: Mon, 10 Apr 2017 00:32:10 +0200
Subject: [PATCH 3/3] Remove custom copy constructors: case of mouse_hover_

FIXME: no need for set???
---
 src/BufferView.cpp              |  8 ++---
 src/BufferView.h                |  2 +-
 src/Makefile.am                 | 21 +++++++------
 src/insets/InsetCollapsable.cpp | 68 ++++++++++++++---------------------------
 src/insets/InsetCollapsable.h   | 25 +++++----------
 src/insets/InsetCommand.cpp     | 23 +-------------
 src/insets/InsetCommand.h       |  7 ++---
 src/insets/InsetExternal.cpp    | 15 +--------
 src/insets/InsetExternal.h      |  6 ++--
 src/mathed/InsetMathNest.cpp    | 23 ++------------
 src/mathed/InsetMathNest.h      | 18 +++--------
 11 files changed, 60 insertions(+), 156 deletions(-)

diff --git a/src/BufferView.cpp b/src/BufferView.cpp
index 80bea84..d14ed4e 100644
--- a/src/BufferView.cpp
+++ b/src/BufferView.cpp
@@ -2187,13 +2187,9 @@ void BufferView::updateHoveredInset() const
 }
 
 
-void BufferView::clearLastInset(Inset * inset) const
+void BufferView::clearLastInset() const
 {
-	if (d->last_inset_ != inset) {
-		LYXERR0("Wrong last_inset!");
-		LATTEST(false);
-	}
-	d->last_inset_ = 0;
+	d->last_inset_ = nullptr;
 }
 
 
diff --git a/src/BufferView.h b/src/BufferView.h
index ee2de82..0099c38 100644
--- a/src/BufferView.h
+++ b/src/BufferView.h
@@ -336,7 +336,7 @@ public:
 	/// Associate an inset associated with given dialog name.
 	void editInset(std::string const & name, Inset * inset);
 	///
-	void clearLastInset(Inset * inset) const;
+	void clearLastInset() const;
 	/// Is the mouse hovering a clickable inset or element?
 	bool clickableInset() const;
 	///
diff --git a/src/Makefile.am b/src/Makefile.am
index 5bf8f3b..6905eaf 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -566,9 +566,6 @@ SOURCEFILESINSETS = \
 	insets/ExternalSupport.cpp \
 	insets/ExternalTemplate.cpp \
 	insets/ExternalTransforms.cpp \
-	insets/RenderButton.cpp \
-	insets/RenderGraphic.cpp \
-	insets/RenderPreview.cpp \
 	insets/Inset.cpp \
 	insets/InsetArgument.cpp \
 	insets/InsetBibitem.cpp \
@@ -618,16 +615,17 @@ SOURCEFILESINSETS = \
 	insets/InsetText.cpp \
 	insets/InsetTOC.cpp \
 	insets/InsetVSpace.cpp \
-	insets/InsetWrap.cpp
+	insets/InsetWrap.cpp \
+	insets/MouseHover.cpp \
+	insets/RenderButton.cpp \
+	insets/RenderGraphic.cpp \
+	insets/RenderPreview.cpp
+
 
 HEADERFILESINSETS = \
 	insets/ExternalSupport.h \
 	insets/ExternalTemplate.h \
 	insets/ExternalTransforms.h \
-	insets/RenderBase.h \
-	insets/RenderButton.h \
-	insets/RenderGraphic.h \
-	insets/RenderPreview.h \
 	insets/Inset.h \
 	insets/InsetArgument.h \
 	insets/InsetBibitem.h \
@@ -678,7 +676,12 @@ HEADERFILESINSETS = \
 	insets/InsetText.h \
 	insets/InsetTOC.h \
 	insets/InsetVSpace.h \
-	insets/InsetWrap.h
+	insets/InsetWrap.h \
+	insets/MouseHover.h \
+	insets/RenderBase.h \
+	insets/RenderButton.h \
+	insets/RenderGraphic.h \
+	insets/RenderPreview.h
 
 lyxinsets.cpp:
 	$(AM_V_GEN)for file in $(SOURCEFILESINSETS) ; do echo '#include "'$${file}'"' ; done >$@
diff --git a/src/insets/InsetCollapsable.cpp b/src/insets/InsetCollapsable.cpp
index 92802b9..9dd0f21 100644
--- a/src/insets/InsetCollapsable.cpp
+++ b/src/insets/InsetCollapsable.cpp
@@ -49,30 +49,11 @@ InsetCollapsable::InsetCollapsable(Buffer * buf, InsetText::UsePlain ltype)
 }
 
 
-// The sole purpose of this copy constructor is to make sure
-// that the view_ map is not copied and remains empty.
-InsetCollapsable::InsetCollapsable(InsetCollapsable const & rhs)
-	: InsetText(rhs),
-	  status_(rhs.status_),
-	  labelstring_(rhs.labelstring_)
-{}
-
-
-InsetCollapsable::~InsetCollapsable()
-{
-	map<BufferView const *, View>::iterator it = view_.begin();
-	map<BufferView const *, View>::iterator end = view_.end();
-	for (; it != end; ++it)
-		if (it->second.mouse_hover_)
-			it->first->clearLastInset(this);
-}
-
-
 InsetCollapsable::CollapseStatus InsetCollapsable::status(BufferView const & bv) const
 {
 	if (decoration() == InsetLayout::CONGLOMERATE)
 		return status_;
-	return view_[&bv].auto_open_ ? Open : status_;
+	return (*view_)[&bv].auto_open_ ? Open : status_;
 }
 
 
@@ -81,7 +62,7 @@ InsetCollapsable::Geometry InsetCollapsable::geometry(BufferView const & bv) con
 	switch (decoration()) {
 	case InsetLayout::CLASSIC:
 		if (status(bv) == Open)
-			return view_[&bv].openinlined_ ? LeftButton : TopButton;
+			return (*view_)[&bv].openinlined_ ? LeftButton : TopButton;
 		return ButtonOnly;
 
 	case InsetLayout::MINIMALISTIC:
@@ -155,7 +136,9 @@ Dimension InsetCollapsable::dimensionCollapsed(BufferView const & bv) const
 
 void InsetCollapsable::metrics(MetricsInfo & mi, Dimension & dim) const
 {
-	view_[mi.base.bv].auto_open_ = mi.base.bv->cursor().isInside(this);
+	LBUFERR(view_);
+	View & view = (*view_)[mi.base.bv];
+	view.auto_open_ = mi.base.bv->cursor().isInside(this);
 
 	FontInfo tmpfont = mi.base.font;
 	mi.base.font = getFont();
@@ -190,7 +173,7 @@ void InsetCollapsable::metrics(MetricsInfo & mi, Dimension & dim) const
 	case LeftButton:
 	case ButtonOnly:
 		if (hasFixedWidth()){
-			int const mindim = view_[&bv].button_dim_.x2 - view_[&bv].button_dim_.x1;
+			int const mindim = view.button_dim_.x2 - view.button_dim_.x1;
 			if (mi.base.textwidth < mindim)
 				mi.base.textwidth = mindim;
 		}
@@ -198,8 +181,8 @@ void InsetCollapsable::metrics(MetricsInfo & mi, Dimension & dim) const
 		if (geometry(bv) == TopButton || geometry(bv) == LeftButton) {
 			Dimension textdim;
 			InsetText::metrics(mi, textdim);
-			view_[&bv].openinlined_ = (textdim.wid + dim.wid) < mi.base.textwidth;
-			if (view_[&bv].openinlined_) {
+			view.openinlined_ = (textdim.wid + dim.wid) < mi.base.textwidth;
+			if (view.openinlined_) {
 				// Correct for button width.
 				dim.wid += textdim.wid;
 				dim.des = max(dim.des - textdim.asc + dim.asc, textdim.des);
@@ -216,19 +199,14 @@ void InsetCollapsable::metrics(MetricsInfo & mi, Dimension & dim) const
 }
 
 
-bool InsetCollapsable::setMouseHover(BufferView const * bv, bool mouse_hover)
-	const
-{
-	view_[bv].mouse_hover_ = mouse_hover;
-	return true;
-}
-
-
 void InsetCollapsable::draw(PainterInfo & pi, int x, int y) const
 {
+	LBUFERR(view_);
+	View & view = (*view_)[pi.base.bv];
 	BufferView const & bv = *pi.base.bv;
 
-	view_[&bv].auto_open_ = bv.cursor().isInside(this);
+
+	view.auto_open_ = bv.cursor().isInside(this);
 
 	Changer dummy = pi.base.font.change(getFont(), true);
 
@@ -238,25 +216,25 @@ void InsetCollapsable::draw(PainterInfo & pi, int x, int y) const
 	if (geometry(bv) == TopButton ||
 	    geometry(bv) == LeftButton ||
 	    geometry(bv) == ButtonOnly) {
-		view_[&bv].button_dim_.x1 = x + 0;
-		view_[&bv].button_dim_.x2 = x + dimc.width();
-		view_[&bv].button_dim_.y1 = y - dimc.asc;
-		view_[&bv].button_dim_.y2 = y + dimc.des;
+		view.button_dim_.x1 = x + 0;
+		view.button_dim_.x2 = x + dimc.width();
+		view.button_dim_.y1 = y - dimc.asc;
+		view.button_dim_.y2 = y + dimc.des;
 
 		FontInfo labelfont = getLabelfont();
 		labelfont.setColor(labelColor());
 		labelfont.realize(pi.base.font);
 		pi.pain.buttonText(x, y, buttonLabel(bv), labelfont,
-		                   view_[&bv].mouse_hover_);
+		                   mouse_hover_->hovered(&bv));
 		// Draw the change tracking cue on the label, unless RowPainter already
 		// takes care of it.
 		if (canPaintChange(bv))
 			pi.change_.paintCue(pi, x, y, x + dimc.width(), labelfont);
 	} else {
-		view_[&bv].button_dim_.x1 = 0;
-		view_[&bv].button_dim_.y1 = 0;
-		view_[&bv].button_dim_.x2 = 0;
-		view_[&bv].button_dim_.y2 = 0;
+		view.button_dim_.x1 = 0;
+		view.button_dim_.y1 = 0;
+		view.button_dim_.x2 = 0;
+		view.button_dim_.y2 = 0;
 	}
 
 	Dimension const textdim = dimensionHelper(bv);
@@ -409,7 +387,7 @@ bool InsetCollapsable::descendable(BufferView const & bv) const
 
 bool InsetCollapsable::clickable(BufferView const & bv, int x, int y) const
 {
-	return view_[&bv].button_dim_.contains(x, y);
+	return (*view_)[&bv].button_dim_.contains(x, y);
 }
 
 
@@ -446,7 +424,7 @@ Inset * InsetCollapsable::editXY(Cursor & cur, int x, int y)
 {
 	//lyxerr << "InsetCollapsable: edit xy" << endl;
 	if (geometry(cur.bv()) == ButtonOnly
-	    || (view_[&cur.bv()].button_dim_.contains(x, y)
+	    || ((*view_)[&cur.bv()].button_dim_.contains(x, y)
 	        && geometry(cur.bv()) != NoButton))
 		return this;
 	cur.push(*this);
diff --git a/src/insets/InsetCollapsable.h b/src/insets/InsetCollapsable.h
index a009d04..3410c67 100644
--- a/src/insets/InsetCollapsable.h
+++ b/src/insets/InsetCollapsable.h
@@ -16,6 +16,8 @@
 
 #include "InsetText.h"
 
+#include "MouseHover.h"
+
 #include "Box.h"
 
 #include <map>
@@ -33,17 +35,6 @@ namespace frontend { class Painter; }
 class InsetCollapsable : public InsetText {
 public:
 	///
-	~InsetCollapsable();//override
-	// FIXME: non-trivial destructor should be moved to a unique_ptr before
-	// enabling default move operators
-	InsetCollapsable(InsetCollapsable &&) = delete;
-	InsetCollapsable & operator=(InsetCollapsable &&) = delete;
-protected:
-	explicit InsetCollapsable(InsetCollapsable const & rhs);
-	InsetCollapsable & operator=(InsetCollapsable const &) = delete;
-
-public:
-	///
 	InsetCollapsable(Buffer *, InsetText::UsePlain = InsetText::PlainLayout);
 	///
 	InsetCollapsable * asInsetCollapsable() { return this; }
@@ -142,8 +133,6 @@ public:
 	///
 	bool getStatus(Cursor &, FuncRequest const &, FuncStatus &) const;
 	///
-	bool setMouseHover(BufferView const * bv, bool mouse_hover) const;
-	///
 	ColorCode backgroundColor(PainterInfo const &) const
 		{ return getLayout().bgcolor(); }
 	///
@@ -183,16 +172,16 @@ private:
 		/// The dimension of the inset button
 		Box button_dim_;
 		/// a substatus of the Open status, determined automatically in metrics
-		bool openinlined_;
+		bool openinlined_ = false;
 		/// the inset will automatically open when the cursor is inside. This is
 		/// dependent on the bufferview, compare with MathMacro::editing_.
-		bool auto_open_;
-		/// changes color when mouse enters/leaves this inset
-		bool mouse_hover_;
+		bool auto_open_ = false;
 	};
 
 	///
-	mutable std::map<BufferView const *, View> view_;
+	cache_ptr<std::map<BufferView const *, View>> view_;
+	///
+	cache_ptr<MouseHover> mouse_hover_;
 };
 
 } // namespace lyx
diff --git a/src/insets/InsetCommand.cpp b/src/insets/InsetCommand.cpp
index b23c116..d5b59d2 100644
--- a/src/insets/InsetCommand.cpp
+++ b/src/insets/InsetCommand.cpp
@@ -60,23 +60,10 @@ InsetCommand::InsetCommand(Buffer * buf, InsetCommandParams const & p)
 {}
 
 
-// The sole purpose of this copy constructor is to make sure
-// that the mouse_hover_ map is not copied and remains empty.
-InsetCommand::InsetCommand(InsetCommand const & rhs)
-	: Inset(rhs), p_(rhs.p_)
-{}
-
-
 InsetCommand::~InsetCommand()
 {
 	if (p_.code() != NO_CODE)
 		hideDialogs(insetName(p_.code()), this);
-
-	map<BufferView const *, bool>::iterator it = mouse_hover_.begin();
-	map<BufferView const *, bool>::iterator end = mouse_hover_.end();
-	for (; it != end; ++it)
-		if (it->second)
-			it->first->clearLastInset(this);
 }
 
 
@@ -88,17 +75,9 @@ void InsetCommand::metrics(MetricsInfo & mi, Dimension & dim) const
 }
 
 
-bool InsetCommand::setMouseHover(BufferView const * bv, bool mouse_hover)
-	const
-{
-	mouse_hover_[bv] = mouse_hover;
-	return true;
-}
-
-
 void InsetCommand::draw(PainterInfo & pi, int x, int y) const
 {
-	button_.setRenderState(mouse_hover_[pi.base.bv]);
+	button_.setRenderState(mouse_hover_->hovered(pi.base.bv));
 	button_.draw(pi, x, y);
 }
 
diff --git a/src/insets/InsetCommand.h b/src/insets/InsetCommand.h
index 82a4d60..25fa315 100644
--- a/src/insets/InsetCommand.h
+++ b/src/insets/InsetCommand.h
@@ -15,6 +15,7 @@
 
 #include "Inset.h"
 #include "InsetCommandParams.h"
+#include "MouseHover.h"
 #include "RenderButton.h"
 
 
@@ -41,7 +42,7 @@ public:
 	InsetCommand(InsetCommand &&) = delete;
 	InsetCommand & operator=(InsetCommand &&) = delete;
 protected:
-	explicit InsetCommand(InsetCommand const & rhs);
+	explicit InsetCommand(InsetCommand const & rhs) = default;
 	InsetCommand & operator=(InsetCommand const &) = delete;
 
 public:
@@ -94,8 +95,6 @@ public:
 	///
 	void validate(LaTeXFeatures & features) const;
 	///
-	bool setMouseHover(BufferView const * bv, bool mouse_hover) const;
-	///
 	bool clickable(BufferView const &, int, int) const { return hasSettings(); }
 	//@}
 
@@ -149,7 +148,7 @@ private:
 	///
 	InsetCommandParams p_;
 	/// changes color when mouse enters/leaves this inset
-	mutable std::map<BufferView const *, bool> mouse_hover_;
+	cache_ptr<MouseHover> mouse_hover_;
 	///
 	mutable RenderButton button_;
 };
diff --git a/src/insets/InsetExternal.cpp b/src/insets/InsetExternal.cpp
index 8efdd3e..a9e05e0 100644
--- a/src/insets/InsetExternal.cpp
+++ b/src/insets/InsetExternal.cpp
@@ -437,19 +437,6 @@ InsetExternal::InsetExternal(InsetExternal const & other)
 InsetExternal::~InsetExternal()
 {
 	hideDialogs("external", this);
-
-	map<BufferView const *, bool>::iterator it = mouse_hover_.begin();
-	map<BufferView const *, bool>::iterator end = mouse_hover_.end();
-	for (; it != end; ++it)
-		if (it->second)
-			it->first->clearLastInset(this);
-}
-
-
-bool InsetExternal::setMouseHover(BufferView const * bv, bool mouse_hover) const
-{
-	mouse_hover_[bv] = mouse_hover;
-	return true;
 }
 
 
@@ -534,7 +521,7 @@ void InsetExternal::metrics(MetricsInfo & mi, Dimension & dim) const
 void InsetExternal::draw(PainterInfo & pi, int x, int y) const
 {
 	if (renderer_->asButton())
-		renderer_->setRenderState(mouse_hover_[pi.base.bv]);
+		renderer_->setRenderState(mouse_hover_->hovered(pi.base.bv));
 	renderer_->draw(pi, x, y);
 }
 
diff --git a/src/insets/InsetExternal.h b/src/insets/InsetExternal.h
index 19fcccc..7549e9e 100644
--- a/src/insets/InsetExternal.h
+++ b/src/insets/InsetExternal.h
@@ -16,6 +16,8 @@
 
 #include "ExternalTemplate.h"
 
+#include "MouseHover.h"
+
 #include "support/FileName.h"
 #include "support/unique_ptr.h"
 
@@ -122,8 +124,6 @@ public:
 	///
 	std::string contextMenuName() const;
 	///
-	bool setMouseHover(BufferView const * bv, bool mouse_hover) const;
-	///
 	bool clickable(BufferView const &, int, int) const { return true; }
 	///
 	void addToToc(DocIterator const & di, bool output_active,
@@ -175,7 +175,7 @@ private:
 	/// The thing that actually draws the image on LyX's screen.
 	unique_ptr<RenderBase> renderer_;
 	/// changes color of the button when mouse enters/leaves this inset
-	mutable std::map<BufferView const *, bool> mouse_hover_;
+	cache_ptr<MouseHover> mouse_hover_;
 };
 
 } // namespace lyx
diff --git a/src/mathed/InsetMathNest.cpp b/src/mathed/InsetMathNest.cpp
index 3358a9e..0f76e38 100644
--- a/src/mathed/InsetMathNest.cpp
+++ b/src/mathed/InsetMathNest.cpp
@@ -90,15 +90,6 @@ InsetMathNest::InsetMathNest(Buffer * buf, idx_type nargs)
 }
 
 
-InsetMathNest::~InsetMathNest()
-{
-	if (mouse_hover_)
-		for (pair<BufferView const *, bool> p : *mouse_hover_)
-			if (p.second)
-				p.first->clearLastInset(this);
-}
-
-
 void InsetMathNest::setBuffer(Buffer & buffer)
 {
 	InsetMath::setBuffer(buffer);
@@ -366,18 +357,10 @@ void InsetMathNest::latex(otexstream & os, OutputParams const & runparams) const
 }
 
 
-bool InsetMathNest::setMouseHover(BufferView const * bv, bool mouse_hover)
-	const
+MouseHover & InsetMathNest::mouseHover() const
 {
-	if (mouse_hover_)
-		(*mouse_hover_)[bv] = mouse_hover;
-	return true;
-}
-
-
-bool InsetMathNest::mouseHovered(BufferView const * bv) const
-{
-	return mouse_hover_ && (*mouse_hover_)[bv];
+	LBUFERR(mouse_hover_);
+	return *mouse_hover_;
 }
 
 
diff --git a/src/mathed/InsetMathNest.h b/src/mathed/InsetMathNest.h
index b393dfe..d3f43b1 100644
--- a/src/mathed/InsetMathNest.h
+++ b/src/mathed/InsetMathNest.h
@@ -15,6 +15,8 @@
 #include "InsetMath.h"
 #include "MathData.h"
 
+#include "insets/MouseHover.h"
+
 #include <map>
 
 #include "support/unique_ptr.h"
@@ -28,15 +30,6 @@ namespace lyx {
 
 class InsetMathNest : public InsetMath {
 public:
-	///
-	~InsetMathNest();//override
-	InsetMathNest(InsetMathNest &&) = default;
-	InsetMathNest & operator=(InsetMathNest &&) = default;
-protected:
-	explicit InsetMathNest(InsetMathNest const &) = default;
-	InsetMathNest & operator=(InsetMathNest const &) = delete;
-
-public:
 	/// nestinsets have a fixed size to start with
 	InsetMathNest(Buffer * buf, idx_type ncells);
 
@@ -115,9 +108,7 @@ public:
 	///
 	void latex(otexstream & os, OutputParams const & runparams) const;
 	///
-	bool setMouseHover(BufferView const * bv, bool mouse_hover) const;
-	///
-	bool mouseHovered(BufferView const * bv) const;
+	MouseHover & mouseHover() const;
 
 	///
 	bool completionSupported(Cursor const &) const;
@@ -196,10 +187,9 @@ protected:
 	/// if the inset is locked, it can't be entered with the cursor
 	bool lock_;
 	///
-	cache_ptr<std::map<BufferView const *, bool>> mouse_hover_;
+	cache_ptr<MouseHover> mouse_hover_;
 };
 
 
-
 } // namespace lyx
 #endif
-- 
2.7.4

Reply via email to