File: doc_view_acm_deconstruct.cpp

package info (click to toggle)
boost1.74 1.74.0-9
  • links: PTS, VCS
  • area: main
  • in suites: bullseye
  • size: 464,084 kB
  • sloc: cpp: 3,338,324; xml: 131,293; python: 33,088; ansic: 14,336; asm: 4,034; sh: 3,351; makefile: 1,193; perl: 1,036; yacc: 478; php: 212; ruby: 102; lisp: 24; sql: 13; csh: 6
file content (135 lines) | stat: -rw-r--r-- 3,520 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
// Document/View sample for Boost.Signals2.
// Expands on doc_view_acm.cpp example by using boost::signals2::deconstruct
// as a post-constructing factory function.
//
// Copyright Keith MacDonald 2005.
// Copyright Frank Mori Hess 2009.
//
// Use, modification and
// distribution is subject to the Boost Software License, Version
// 1.0. (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
// For more information, see http://www.boost.org

#include <iostream>
#include <string>
#include <boost/bind.hpp>
#include <boost/ref.hpp>
#include <boost/signals2/deconstruct.hpp>
#include <boost/signals2/signal.hpp>
#include <boost/shared_ptr.hpp>

class Document
{
public:
  typedef boost::signals2::signal<void ()>  signal_t;

public:
  Document()
  {}

  /* Connect a slot to the signal which will be emitted whenever
    text is appended to the document. */
  boost::signals2::connection connect(const signal_t::slot_type &subscriber)
  {
    return m_sig.connect(subscriber);
  }

  void append(const char* s)
  {
    m_text += s;
    m_sig();
  }

  const std::string& getText() const
  {
    return m_text;
  }

private:
  signal_t    m_sig;
  std::string m_text;
};

class TextView
{
public:
  /* This adl_postconstruct function will be found
  via argument-dependent lookup when using boost::signals2::deconstruct. */
  template<typename T>
    friend void adl_postconstruct(const boost::shared_ptr<T> &view_sp, TextView *view, Document& doc)
  {
    view->m_document = &doc;
    {
      typedef Document::signal_t::slot_type slot_type;
      slot_type myslot(&TextView::refresh, view);
      doc.connect(myslot.track(view_sp));
    }
  }

  void refresh() const
  {
    std::cout << "TextView: " << m_document->getText() << std::endl;
  }
private:
  // give boost::signals2::deconstruct access to private constructor
  friend class boost::signals2::deconstruct_access;
  // private constructor to force use of deconstruct
  TextView() : m_document(0)
  {}

  Document*               m_document;
};

class HexView
{
public:
  /* This adl_postconstruct function will be found
  via argument-dependent lookup when using boost::signals2::deconstruct. */
  template<typename T>
    friend void adl_postconstruct(const boost::shared_ptr<T> &view_sp, HexView *view, Document& doc)
  {
    view->m_document = &doc;
    {
      typedef Document::signal_t::slot_type slot_type;
      slot_type myslot(&HexView::refresh, view);
      doc.connect(myslot.track(view_sp));
    }
  }

  void refresh() const
  {
    const std::string&  s = m_document->getText();

    std::cout << "HexView:";

    for (std::string::const_iterator it = s.begin(); it != s.end(); ++it)
      std::cout << ' ' << std::hex << static_cast<int>(*it);

    std::cout << std::endl;
  }
private:
  // give boost::signals2::deconstruct access to private constructor
  friend class boost::signals2::deconstruct_access;
  // private constructor to force use of deconstruct
  HexView(): m_document(0)
  {}

  Document*               m_document;
};

namespace bs2 = boost::signals2;

int main(int argc, char* argv[])
{
  Document    doc;
  boost::shared_ptr<TextView> v1 = bs2::deconstruct<TextView>().postconstruct(boost::ref(doc));
  boost::shared_ptr<HexView> v2 = bs2::deconstruct<HexView>().postconstruct(boost::ref(doc));

  doc.append(argc >= 2 ? argv[1] : "Hello world!");

  v2.reset(); // destroy the HexView, automatically disconnecting
  doc.append("  HexView should no longer be connected.");

  return 0;
}