FreeCAD

Форк
0
/
DocumentObserver.cpp 
492 строки · 13.4 Кб
1
/***************************************************************************
2
 *   Copyright (c) 2008 Werner Mayer <wmayer[at]users.sourceforge.net>     *
3
 *                                                                         *
4
 *   This file is part of the FreeCAD CAx development system.              *
5
 *                                                                         *
6
 *   This library is free software; you can redistribute it and/or         *
7
 *   modify it under the terms of the GNU Library General Public           *
8
 *   License as published by the Free Software Foundation; either          *
9
 *   version 2 of the License, or (at your option) any later version.      *
10
 *                                                                         *
11
 *   This library  is distributed in the hope that it will be useful,      *
12
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
13
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
14
 *   GNU Library General Public License for more details.                  *
15
 *                                                                         *
16
 *   You should have received a copy of the GNU Library General Public     *
17
 *   License along with this library; see the file COPYING.LIB. If not,    *
18
 *   write to the Free Software Foundation, Inc., 59 Temple Place,         *
19
 *   Suite 330, Boston, MA  02111-1307, USA                                *
20
 *                                                                         *
21
 ***************************************************************************/
22

23

24
#include "PreCompiled.h"
25

26
#ifndef _PreComp_
27
# include <sstream>
28
#endif
29

30
#include <functional>
31

32
#include "DocumentObserver.h"
33
#include "Application.h"
34
#include "Document.h"
35
#include "ViewProviderDocumentObject.h"
36
#include <App/Document.h>
37

38

39
using namespace Gui;
40
namespace sp = std::placeholders;
41

42

43
DocumentT::DocumentT() = default;
44

45
DocumentT::DocumentT(Document* doc)
46
{
47
    document = doc->getDocument()->getName();
48
}
49

50
DocumentT::DocumentT(const std::string& name)
51
{
52
    document = name;
53
}
54

55
DocumentT::DocumentT(const DocumentT& doc)
56
{
57
    document = doc.document;
58
}
59

60
DocumentT::~DocumentT() = default;
61

62
void DocumentT::operator=(const DocumentT& doc)
63
{
64
    if (this == &doc)
65
        return;
66
    document = doc.document;
67
}
68

69
void DocumentT::operator=(const Document* doc)
70
{
71
    document = doc->getDocument()->getName();
72
}
73

74
void DocumentT::operator=(const std::string& name)
75
{
76
    document = name;
77
}
78

79
Document* DocumentT::getDocument() const
80
{
81
    return Application::Instance->getDocument(document.c_str());
82
}
83

84
std::string DocumentT::getDocumentName() const
85
{
86
    return document;
87
}
88

89
std::string DocumentT::getGuiDocumentPython() const
90
{
91
    std::stringstream str;
92
    Document* doc = Application::Instance->activeDocument();
93
    if (doc && document == doc->getDocument()->getName()) {
94
        str << "Gui.ActiveDocument";
95
    }
96
    else {
97
        str << "Gui.getDocument(\""
98
            << document
99
            << "\")";
100
    }
101
    return str.str();
102
}
103

104
std::string DocumentT::getAppDocumentPython() const
105
{
106
    std::stringstream str;
107
    Document* doc = Application::Instance->activeDocument();
108
    if (doc && document == doc->getDocument()->getName()) {
109
        str << "App.ActiveDocument";
110
    }
111
    else {
112
        str << "App.getDocument(\""
113
            << document
114
            << "\")";
115
    }
116
    return str.str();
117
}
118

119
// -----------------------------------------------------------------------------
120

121
ViewProviderT::ViewProviderT() = default;
122

123
ViewProviderT::ViewProviderT(const ViewProviderT& other)
124
{
125
    *this = other;
126
}
127

128
ViewProviderT::ViewProviderT(ViewProviderT &&other)
129
{
130
    *this = std::move(other);
131
}
132

133
ViewProviderT::ViewProviderT(const ViewProviderDocumentObject* obj)
134
{
135
    *this = obj;
136
}
137

138
ViewProviderT::~ViewProviderT() = default;
139

140
ViewProviderT & ViewProviderT::operator=(const ViewProviderT& obj)
141
{
142
    if (this == &obj)
143
        return *this;
144
    object = obj.object;
145
    document = obj.document;
146
    return *this;
147
}
148

149
ViewProviderT &ViewProviderT::operator=(ViewProviderT&& obj)
150
{
151
    if (this == &obj)
152
        return *this;
153
    object = std::move(obj.object);
154
    document = std::move(obj.document);
155
    return *this;
156
}
157

158
void ViewProviderT::operator=(const ViewProviderDocumentObject* obj)
159
{
160
    if (!obj) {
161
        object.clear();
162
        document.clear();
163
    }
164
    else {
165
        object = obj->getObject()->getNameInDocument();
166
        document = obj->getObject()->getDocument()->getName();
167
    }
168
}
169

170
bool ViewProviderT::operator==(const ViewProviderT &other) const {
171
    return document == other.document
172
        && object == other.object;
173
}
174

175
Document* ViewProviderT::getDocument() const
176
{
177
    return Application::Instance->getDocument(document.c_str());
178
}
179

180
const std::string& ViewProviderT::getDocumentName() const
181
{
182
    return document;
183
}
184

185
std::string ViewProviderT::getGuiDocumentPython() const
186
{
187
    DocumentT doct(document);
188
    return doct.getGuiDocumentPython();
189
}
190

191
std::string ViewProviderT::getAppDocumentPython() const
192
{
193
    DocumentT doct(document);
194
    return doct.getAppDocumentPython();
195
}
196

197
ViewProviderDocumentObject* ViewProviderT::getViewProvider() const
198
{
199
    ViewProviderDocumentObject* obj = nullptr;
200
    Document* doc = getDocument();
201
    if (doc) {
202
        obj = dynamic_cast<ViewProviderDocumentObject*>(doc->getViewProviderByName(object.c_str()));
203
    }
204
    return obj;
205
}
206

207
const std::string& ViewProviderT::getObjectName() const
208
{
209
    return object;
210
}
211

212
std::string ViewProviderT::getObjectPython() const
213
{
214
    std::stringstream str;
215
    Document* doc = Application::Instance->activeDocument();
216
    if (doc && document == doc->getDocument()->getName()) {
217
        str << "Gui.ActiveDocument.";
218
    }
219
    else {
220
        str << "Gui.getDocument(\""
221
            << document
222
            << "\").";
223
    }
224

225
    str << object;
226
    return str.str();
227
}
228

229
// -----------------------------------------------------------------------------
230

231
class DocumentWeakPtrT::Private {
232
public:
233
    Private(Gui::Document* doc) : _document(doc) {
234
        if (doc) {
235
            //NOLINTBEGIN
236
            connectApplicationDeletedDocument = doc->signalDeleteDocument.connect(std::bind
237
                (&Private::deletedDocument, this, sp::_1));
238
            //NOLINTEND
239
        }
240
    }
241

242
    void deletedDocument(const Gui::Document& doc) {
243
        if (_document == &doc)
244
            reset();
245
    }
246
    void reset() {
247
        connectApplicationDeletedDocument.disconnect();
248
        _document = nullptr;
249
    }
250

251
    Gui::Document* _document;
252
    using Connection = boost::signals2::scoped_connection;
253
    Connection connectApplicationDeletedDocument;
254
};
255

256
DocumentWeakPtrT::DocumentWeakPtrT(Gui::Document* doc) noexcept
257
  : d(new Private(doc))
258
{
259
}
260

261
DocumentWeakPtrT::~DocumentWeakPtrT() = default;
262

263
void DocumentWeakPtrT::reset() noexcept
264
{
265
    d->reset();
266
}
267

268
bool DocumentWeakPtrT::expired() const noexcept
269
{
270
    return (d->_document == nullptr);
271
}
272

273
Gui::Document* DocumentWeakPtrT::operator*() const noexcept
274
{
275
    return d->_document;
276
}
277

278
Gui::Document* DocumentWeakPtrT::operator->() const noexcept
279
{
280
    return d->_document;
281
}
282

283
// -----------------------------------------------------------------------------
284

285
class ViewProviderWeakPtrT::Private {
286
public:
287
    Private(ViewProviderDocumentObject* obj) : object(obj) {
288
        set(obj);
289
    }
290
    void deletedDocument(const Gui::Document& doc) {
291
        // When deleting document then there is no way to undo it
292
        if (object && object->getDocument() == &doc) {
293
            reset();
294
        }
295
    }
296
    void createdObject(const Gui::ViewProvider& obj) noexcept {
297
        // When undoing the removal
298
        if (object == &obj) {
299
            indocument = true;
300
        }
301
    }
302
    void deletedObject(const Gui::ViewProvider& obj) noexcept {
303
        if (object == &obj) {
304
            indocument = false;
305
        }
306
    }
307
    void reset() {
308
        connectApplicationDeletedDocument.disconnect();
309
        connectDocumentCreatedObject.disconnect();
310
        connectDocumentDeletedObject.disconnect();
311
        object = nullptr;
312
        indocument = false;
313
    }
314
    void set(ViewProviderDocumentObject* obj) {
315
        object = obj;
316
        try {
317
            if (obj) {
318
                //NOLINTBEGIN
319
                Gui::Document* doc = obj->getDocument();
320
                indocument = true;
321
                connectApplicationDeletedDocument = doc->signalDeleteDocument.connect(std::bind
322
                    (&Private::deletedDocument, this, sp::_1));
323
                connectDocumentCreatedObject = doc->signalNewObject.connect(std::bind
324
                    (&Private::createdObject, this, sp::_1));
325
                connectDocumentDeletedObject = doc->signalDeletedObject.connect(std::bind
326
                    (&Private::deletedObject, this, sp::_1));
327
                //NOLINTEND
328
            }
329
        }
330
        catch (const Base::RuntimeError&) {
331
            // getDocument() may raise an exception
332
            object = nullptr;
333
            indocument = false;
334
        }
335
    }
336
    ViewProviderDocumentObject* get() const {
337
        return indocument ? object : nullptr;
338
    }
339

340
    Gui::ViewProviderDocumentObject* object;
341
    bool indocument{false};
342
    using Connection = boost::signals2::scoped_connection;
343
    Connection connectApplicationDeletedDocument;
344
    Connection connectDocumentCreatedObject;
345
    Connection connectDocumentDeletedObject;
346
};
347

348
ViewProviderWeakPtrT::ViewProviderWeakPtrT(ViewProviderDocumentObject* obj)
349
  : d(new Private(obj))
350
{
351
}
352

353
ViewProviderWeakPtrT::~ViewProviderWeakPtrT() = default;
354

355
ViewProviderDocumentObject* ViewProviderWeakPtrT::_get() const noexcept
356
{
357
    return d->get();
358
}
359

360
void ViewProviderWeakPtrT::reset()
361
{
362
    d->reset();
363
}
364

365
bool ViewProviderWeakPtrT::expired() const noexcept
366
{
367
    return !d->indocument;
368
}
369

370
ViewProviderWeakPtrT& ViewProviderWeakPtrT::operator= (ViewProviderDocumentObject* p)
371
{
372
    d->reset();
373
    d->set(p);
374
    return *this;
375
}
376

377
ViewProviderDocumentObject* ViewProviderWeakPtrT::operator*() const noexcept
378
{
379
    return d->get();
380
}
381

382
ViewProviderDocumentObject* ViewProviderWeakPtrT::operator->() const noexcept
383
{
384
    return d->get();
385
}
386

387
bool ViewProviderWeakPtrT::operator== (const ViewProviderWeakPtrT& p) const noexcept
388
{
389
    return d->get() == p.d->get();
390
}
391

392
bool ViewProviderWeakPtrT::operator!= (const ViewProviderWeakPtrT& p) const noexcept
393
{
394
    return d->get() != p.d->get();
395
}
396

397
// -----------------------------------------------------------------------------
398

399
DocumentObserver::DocumentObserver() = default;
400

401
DocumentObserver::DocumentObserver(Document* doc)
402
{
403
    attachDocument(doc);
404
}
405

406
DocumentObserver::~DocumentObserver() = default;
407

408
void DocumentObserver::attachDocument(Document* doc)
409
{
410
    detachDocument();
411

412
    if (!doc)
413
        return;
414

415
    //NOLINTBEGIN
416
    this->connectDocumentCreatedObject = doc->signalNewObject.connect(std::bind
417
        (&DocumentObserver::slotCreatedObject, this, sp::_1));
418
    this->connectDocumentDeletedObject = doc->signalDeletedObject.connect(std::bind
419
        (&DocumentObserver::slotDeletedObject, this, sp::_1));
420
    this->connectDocumentChangedObject = doc->signalChangedObject.connect(std::bind
421
        (&DocumentObserver::slotChangedObject, this, sp::_1, sp::_2));
422
    this->connectDocumentRelabelObject = doc->signalRelabelObject.connect(std::bind
423
        (&DocumentObserver::slotRelabelObject, this, sp::_1));
424
    this->connectDocumentActivateObject = doc->signalActivatedObject.connect(std::bind
425
        (&DocumentObserver::slotActivatedObject, this, sp::_1));
426
    this->connectDocumentEditObject = doc->signalInEdit.connect(std::bind
427
        (&DocumentObserver::slotEnterEditObject, this, sp::_1));
428
    this->connectDocumentResetObject = doc->signalResetEdit.connect(std::bind
429
        (&DocumentObserver::slotResetEditObject, this, sp::_1));
430
    this->connectDocumentUndo = doc->signalUndoDocument.connect(std::bind
431
        (&DocumentObserver::slotUndoDocument, this, sp::_1));
432
    this->connectDocumentRedo = doc->signalRedoDocument.connect(std::bind
433
        (&DocumentObserver::slotRedoDocument, this, sp::_1));
434
    this->connectDocumentDelete = doc->signalDeleteDocument.connect(std::bind
435
        (&DocumentObserver::slotDeleteDocument, this, sp::_1));
436
    //NOLINTEND
437
}
438

439
void DocumentObserver::detachDocument()
440
{
441
    this->connectDocumentCreatedObject.disconnect();
442
    this->connectDocumentDeletedObject.disconnect();
443
    this->connectDocumentChangedObject.disconnect();
444
    this->connectDocumentRelabelObject.disconnect();
445
    this->connectDocumentActivateObject.disconnect();
446
    this->connectDocumentEditObject.disconnect();
447
    this->connectDocumentResetObject.disconnect();
448
    this->connectDocumentUndo.disconnect();
449
    this->connectDocumentRedo.disconnect();
450
    this->connectDocumentDelete.disconnect();
451
}
452

453
void DocumentObserver::slotUndoDocument(const Document& /*Doc*/)
454
{
455
}
456

457
void DocumentObserver::slotRedoDocument(const Document& /*Doc*/)
458
{
459
}
460

461
void DocumentObserver::slotDeleteDocument(const Document& /*Doc*/)
462
{
463
}
464

465
void DocumentObserver::slotCreatedObject(const ViewProviderDocumentObject& /*Obj*/)
466
{
467
}
468

469
void DocumentObserver::slotDeletedObject(const ViewProviderDocumentObject& /*Obj*/)
470
{
471
}
472

473
void DocumentObserver::slotChangedObject(const ViewProviderDocumentObject& /*Obj*/,
474
                                         const App::Property& /*Prop*/)
475
{
476
}
477

478
void DocumentObserver::slotRelabelObject(const ViewProviderDocumentObject& /*Obj*/)
479
{
480
}
481

482
void DocumentObserver::slotActivatedObject(const ViewProviderDocumentObject& /*Obj*/)
483
{
484
}
485

486
void DocumentObserver::slotEnterEditObject(const ViewProviderDocumentObject& /*Obj*/)
487
{
488
}
489

490
void DocumentObserver::slotResetEditObject(const ViewProviderDocumentObject& /*Obj*/)
491
{
492
}
493

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.