Skip to content

Commit 40c61c9

Browse files
committed
docs/manual/libsigc_manual.xml: Update signal and slot syntax
Update the syntax of template parameters. sigc::signal<void,int> -> sigc::signal<void(int)>. The old syntax is deprecated. Mention lambda expressions. Although sigc::retype() is a template function, no template parameters shall be specified when it's called. See #59
1 parent 691d830 commit 40c61c9

File tree

1 file changed

+37
-24
lines changed

1 file changed

+37
-24
lines changed

docs/manual/libsigc_manual.xml

Lines changed: 37 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -29,24 +29,24 @@
2929
application using that toolkit should handle the user clicking on it.</para>
3030

3131
<para>In C the callbacks are generally handled by the application calling a
32-
'register' function and passing a pointer to a function and a <literal remap="tt">void *</literal>
32+
'register' function and passing a pointer to a function and a <literal remap="tt">void*</literal>
3333
argument, eg.</para>
3434

3535
<programlisting>
36-
void clicked(void *data);
36+
void clicked(void* data);
3737

38-
button * okbutton = create_button("ok");
38+
button* okbutton = create_button("ok");
3939
static char somedata[] = "This is some data I want the clicked() function to have";
4040

4141
register_click_handler(okbutton, clicked, somedata);
4242
</programlisting>
4343

4444
<para>When clicked, the toolkit will call <literal remap="tt">clicked()</literal> with the data pointer passed
45-
to the <literal remap="tt">register_click_handler</literal> function.</para>
45+
to the <literal remap="tt">register_click_handler()</literal> function.</para>
4646

4747
<para>This works in C, but is not typesafe. There is no compile-time way of
4848
ensuring that <literal remap="tt">clicked()</literal> isn't expecting a struct of some sort instead of a
49-
<literal remap="tt">char *</literal>.</para>
49+
<literal remap="tt">char*</literal>.</para>
5050

5151
<para>As C++ programmers, we want type safety. We also want to be able to use
5252
things other than free-standing functions as callbacks.</para>
@@ -55,7 +55,8 @@ register_click_handler(okbutton, clicked, somedata);
5555
the things that can be used as a callback:
5656
<itemizedlist>
5757
<listitem><para>A free-standing function as in the example</para></listitem>
58-
<listitem><para>A functor objects that defines operator()</para></listitem>
58+
<listitem><para>A functor object that defines operator() (a lambda expression
59+
is such an object)</para></listitem>
5960
<listitem><para>A pointer-to-a-member-function and an instance of an object on which to invoke it (the
6061
object should inherit from <literal remap="tt">sigc::trackable</literal>)</para></listitem>
6162
</itemizedlist></para>
@@ -96,7 +97,7 @@ public:
9697

9798
void run();
9899

99-
sigc::signal&lt;void&gt; signal_detected;
100+
sigc::signal&lt;void()&gt; signal_detected;
100101
};
101102
</programlisting>
102103

@@ -107,7 +108,7 @@ public:
107108
<programlisting>
108109
void warn_people()
109110
{
110-
cout &lt;&lt; "There are aliens in the carpark!" &lt;&lt; endl;
111+
std::cout &lt;&lt; "There are aliens in the carpark!" &lt;&lt; std::endl;
111112
}
112113

113114
int main()
@@ -121,6 +122,11 @@ int main()
121122
}
122123
</programlisting>
123124

125+
<para>You can use a lambda expression instead of sigc::ptr_fun().</para>
126+
<programlisting>
127+
mydetector.signal_detected.connect( [](){ warn_people(); } );
128+
</programlisting>
129+
124130
<para>Pretty simple really - you call the <literal remap="tt">connect()</literal> method on the signal to
125131
connect your function. <literal remap="tt">connect()</literal> takes a <literal remap="tt">slot</literal> parameter (remember slots
126132
are capable of holding any type of callback), so you convert your
@@ -175,6 +181,12 @@ int main()
175181

176182
<para>This code is in example2.cc, which can be compiled in the same way as
177183
example1.cc</para>
184+
185+
<para>It's possible to use a lambda expression instead of sigc::mem_fun(),
186+
but it's not recommended, if the class derives from <literal remap="tt">sigc::trackable</literal>.
187+
With a lambda expression you would lose the automatic disconnection that the
188+
combination of <literal remap="tt">sigc::trackable</literal> and sigc::mem_fun()
189+
offers.</para>
178190
</sect1>
179191

180192
<sect1>
@@ -198,22 +210,25 @@ public:
198210

199211
void run();
200212

201-
sigc::signal&lt;void, std::string&gt; signal_detected; // changed
213+
sigc::signal&lt;void(std::string)&gt; signal_detected; // changed
202214
};
203215
</programlisting>
204216

205217
<para>The only line I had to change was the signal line (in <literal remap="tt">run()</literal> I need to change
206218
my code to supply the argument when I emit the signal too, but that's not shown
207219
here).</para>
208220

209-
<para>The name of the type is '<literal remap="tt">sigc::signal</literal>'. The template parameters are the return type, then the argument types.</para>
221+
<para>The name of the type is '<literal remap="tt">sigc::signal</literal>'.
222+
The template parameters are the return type, then the argument types in parentheses.
223+
(libsigc++2 also accepts a different syntax, with a comma between the return type
224+
and the parameter types. That syntax is deprecated, though.)</para>
210225

211226
<para>The types in the function signature are in the same order as the template
212227
parameters, eg:</para>
213228

214229
<programlisting>
215-
sigc::signal&lt;void, std::string&gt;
216-
void function(std::string foo);
230+
sigc::signal&lt;void(std::string)&gt;
231+
void function(std::string foo);
217232
</programlisting>
218233

219234
<para>So now you can update your alerter (for simplicity, lets go back to the
@@ -222,7 +237,7 @@ sigc::signal&lt;void, std::string&gt;
222237
<programlisting>
223238
void warn_people(std::string where)
224239
{
225-
cout &lt;&lt; "There are aliens in " &lt;&lt; where &lt;&lt; "!" &lt;&lt; endl;
240+
std::cout &lt;&lt; "There are aliens in " &lt;&lt; where &lt;&lt; "!" &lt;&lt; std::endl;
226241
}
227242

228243
int main()
@@ -269,7 +284,7 @@ int main()
269284
<para>A signal is an instance of a template, named <literal remap="tt">sigc::signal</literal>.
270285
The template arguments are the types,
271286
in the order they appear in the function signature that can be connected to that
272-
signal; that is the return type, then the argument types.</para>
287+
signal; that is the return type, then the argument types in parentheses.</para>
273288

274289
<para>To provide a signal for people to connect to, you must make available an
275290
instance of that <literal remap="tt">sigc::signal</literal>. In <literal remap="tt">AlienDetector</literal> this was done
@@ -297,7 +312,7 @@ void AlienDetector::run()
297312
{
298313
sleep(3); // wait for aliens
299314
signal_detected("the carpark"); // this is the std::string version, looks like
300-
// they landed in the carpark afterall.
315+
// they landed in the carpark after all.
301316
}
302317
</programlisting>
303318
</sect1>
@@ -308,7 +323,7 @@ void AlienDetector::run()
308323
about the return value of the last registered one, it's quite straightforward:</para>
309324

310325
<programlisting>
311-
sigc::signal&lt;int&gt; somesignal;
326+
sigc::signal&lt;int()&gt; somesignal;
312327
int a_return_value;
313328

314329
a_return_value = somesignal.emit();
@@ -390,23 +405,21 @@ myaliendetector.signal_detected.connect( sigc::hide&lt;std::string&gt;( sigc::pt
390405
<para>A similar topic is retyping. Perhaps you have a signal that takes an <literal remap="tt">int</literal>, but
391406
you want to connect a function that takes a <literal remap="tt">double</literal>.</para>
392407

393-
<para>This can be achieved with the <literal remap="tt">sigc::retype</literal> template. <literal remap="tt">retype</literal> has template arguments
394-
just like <literal remap="tt">sigc::signal</literal> - return value, signal types.</para>
395-
396-
<para>It's a function template that takes a <literal remap="tt">sigc::slot</literal>, and returns a <literal remap="tt">sigc::slot</literal>. eg.</para>
408+
<para>This can be achieved with the <literal remap="tt">sigc::retype()</literal> template.
409+
It takes a <literal remap="tt">sigc::slot</literal>, and returns a <literal remap="tt">sigc::slot</literal>. eg.</para>
397410

398411
<programlisting>
399412
void dostuff(double foo)
400413
{
401414
}
402415

403-
sigc::signal&lt;void,int&gt; asignal;
416+
sigc::signal&lt;void(int)&gt; asignal;
404417

405-
asignal.connect( sigc::retype&lt;void, int&gt;( slot(&amp;dostuff) ) );
418+
asignal.connect( sigc::retype( sigc::ptr_fun(&amp;dostuff) ) );
406419
</programlisting>
407420

408-
<para>If you only want to change the return type, you can use <literal remap="tt">sigc::retype_return</literal>.
409-
<literal remap="tt">retype_return</literal> needs only one template argument.</para>
421+
<para>If you only want to change the return type, you can use <literal remap="tt">sigc::retype_return()</literal>.
422+
<literal remap="tt">retype_return()</literal> needs one template argument, the new return type.</para>
410423
</sect1>
411424
</chapter>
412425

0 commit comments

Comments
 (0)