1 /*
2  * This file is part of gtkD.
3  *
4  * gtkD is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU Lesser General Public License
6  * as published by the Free Software Foundation; either version 3
7  * of the License, or (at your option) any later version, with
8  * some exceptions, please read the COPYING file.
9  *
10  * gtkD is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public License
16  * along with gtkD; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110, USA
18  */
19 
20 // generated automatically - do not change
21 // find conversion definition on APILookup.txt
22 // implement new conversion functionalities on the wrap.utils pakage
23 
24 
25 module gsv.SourceView;
26 
27 private import gdk.Event;
28 private import glib.ConstructionException;
29 private import glib.Str;
30 private import gobject.ObjectG;
31 private import gobject.Signals;
32 private import gsv.SourceBuffer;
33 private import gsv.SourceCompletion;
34 private import gsv.SourceGutter;
35 private import gsv.SourceMarkAttributes;
36 private import gsv.SpaceDrawer;
37 private import gsv.c.functions;
38 public  import gsv.c.types;
39 public  import gsvc.gsvtypes;
40 private import gtk.BuildableIF;
41 private import gtk.BuildableT;
42 private import gtk.ScrollableIF;
43 private import gtk.ScrollableT;
44 private import gtk.TextIter;
45 private import gtk.TextView;
46 private import gtk.Widget;
47 private import std.algorithm;
48 
49 
50 /** */
51 public class SourceView : TextView
52 {
53 	/** the main Gtk struct */
54 	protected GtkSourceView* gtkSourceView;
55 
56 	/** Get the main Gtk struct */
57 	public GtkSourceView* getSourceViewStruct(bool transferOwnership = false)
58 	{
59 		if (transferOwnership)
60 			ownedRef = false;
61 		return gtkSourceView;
62 	}
63 
64 	/** the main Gtk struct as a void* */
65 	protected override void* getStruct()
66 	{
67 		return cast(void*)gtkSourceView;
68 	}
69 
70 	/**
71 	 * Sets our main struct and passes it to the parent class.
72 	 */
73 	public this (GtkSourceView* gtkSourceView, bool ownedRef = false)
74 	{
75 		this.gtkSourceView = gtkSourceView;
76 		super(cast(GtkTextView*)gtkSourceView, ownedRef);
77 	}
78 
79 	/**
80 	 * Returns the GtkSourceBuffer being displayed by this source view.
81 	 * The reference count on the buffer is not incremented; the caller
82 	 * of this function won't own a new reference.
83 	 *
84 	 * Returns:
85 	 *  a GtkSourceBuffer
86 	 */
87 	public override SourceBuffer getBuffer()
88 	{
89 		auto p = gtk_text_view_get_buffer(cast(GtkTextView*)gtkSourceView);
90 
91 		return ObjectG.getDObject!(SourceBuffer)(cast(GtkSourceBuffer*) p);
92 	}
93 
94 	/**
95 	 */
96 
97 	/** */
98 	public static GType getType()
99 	{
100 		return gtk_source_view_get_type();
101 	}
102 
103 	/**
104 	 * Creates a new #GtkSourceView.
105 	 *
106 	 * By default, an empty #GtkSourceBuffer will be lazily created and can be
107 	 * retrieved with gtk_text_view_get_buffer().
108 	 *
109 	 * If you want to specify your own buffer, either override the
110 	 * #GtkTextViewClass create_buffer factory method, or use
111 	 * gtk_source_view_new_with_buffer().
112 	 *
113 	 * Returns: a new #GtkSourceView.
114 	 *
115 	 * Throws: ConstructionException GTK+ fails to create the object.
116 	 */
117 	public this()
118 	{
119 		auto p = gtk_source_view_new();
120 
121 		if(p is null)
122 		{
123 			throw new ConstructionException("null returned by new");
124 		}
125 
126 		this(cast(GtkSourceView*) p);
127 	}
128 
129 	/**
130 	 * Creates a new #GtkSourceView widget displaying the buffer
131 	 * @buffer. One buffer can be shared among many widgets.
132 	 *
133 	 * Params:
134 	 *     buffer = a #GtkSourceBuffer.
135 	 *
136 	 * Returns: a new #GtkSourceView.
137 	 *
138 	 * Throws: ConstructionException GTK+ fails to create the object.
139 	 */
140 	public this(SourceBuffer buffer)
141 	{
142 		auto p = gtk_source_view_new_with_buffer((buffer is null) ? null : buffer.getSourceBufferStruct());
143 
144 		if(p is null)
145 		{
146 			throw new ConstructionException("null returned by new_with_buffer");
147 		}
148 
149 		this(cast(GtkSourceView*) p);
150 	}
151 
152 	/**
153 	 * Returns whether auto-indentation of text is enabled.
154 	 *
155 	 * Returns: %TRUE if auto indentation is enabled.
156 	 */
157 	public bool getAutoIndent()
158 	{
159 		return gtk_source_view_get_auto_indent(gtkSourceView) != 0;
160 	}
161 
162 	/**
163 	 * Returns the #GtkSourceBackgroundPatternType specifying if and how
164 	 * the background pattern should be displayed for this @view.
165 	 *
166 	 * Returns: the #GtkSourceBackgroundPatternType.
167 	 *
168 	 * Since: 3.16
169 	 */
170 	public GtkSourceBackgroundPatternType getBackgroundPattern()
171 	{
172 		return gtk_source_view_get_background_pattern(gtkSourceView);
173 	}
174 
175 	/**
176 	 * Gets the #GtkSourceCompletion associated with @view. The returned object is
177 	 * guaranteed to be the same for the lifetime of @view. Each #GtkSourceView
178 	 * object has a different #GtkSourceCompletion.
179 	 *
180 	 * Returns: the #GtkSourceCompletion associated with @view.
181 	 */
182 	public SourceCompletion getCompletion()
183 	{
184 		auto p = gtk_source_view_get_completion(gtkSourceView);
185 
186 		if(p is null)
187 		{
188 			return null;
189 		}
190 
191 		return ObjectG.getDObject!(SourceCompletion)(cast(GtkSourceCompletion*) p);
192 	}
193 
194 	/**
195 	 * Returns the #GtkSourceDrawSpacesFlags specifying if and how spaces
196 	 * should be displayed for this @view.
197 	 *
198 	 * Deprecated: Use gtk_source_space_drawer_get_types_for_locations()
199 	 * instead.
200 	 *
201 	 * Returns: the #GtkSourceDrawSpacesFlags, 0 if no spaces should be drawn.
202 	 */
203 	public GtkSourceDrawSpacesFlags getDrawSpaces()
204 	{
205 		return gtk_source_view_get_draw_spaces(gtkSourceView);
206 	}
207 
208 	/**
209 	 * Returns the #GtkSourceGutter object associated with @window_type for @view.
210 	 * Only GTK_TEXT_WINDOW_LEFT and GTK_TEXT_WINDOW_RIGHT are supported,
211 	 * respectively corresponding to the left and right gutter. The line numbers
212 	 * and mark category icons are rendered in the left gutter.
213 	 *
214 	 * Params:
215 	 *     windowType = the gutter window type.
216 	 *
217 	 * Returns: the #GtkSourceGutter.
218 	 *
219 	 * Since: 2.8
220 	 */
221 	public SourceGutter getGutter(GtkTextWindowType windowType)
222 	{
223 		auto p = gtk_source_view_get_gutter(gtkSourceView, windowType);
224 
225 		if(p is null)
226 		{
227 			return null;
228 		}
229 
230 		return ObjectG.getDObject!(SourceGutter)(cast(GtkSourceGutter*) p);
231 	}
232 
233 	/**
234 	 * Returns whether the current line is highlighted.
235 	 *
236 	 * Returns: %TRUE if the current line is highlighted.
237 	 */
238 	public bool getHighlightCurrentLine()
239 	{
240 		return gtk_source_view_get_highlight_current_line(gtkSourceView) != 0;
241 	}
242 
243 	/**
244 	 * Returns whether when the tab key is pressed the current selection
245 	 * should get indented instead of replaced with the \t character.
246 	 *
247 	 * Returns: %TRUE if the selection is indented when tab is pressed.
248 	 */
249 	public bool getIndentOnTab()
250 	{
251 		return gtk_source_view_get_indent_on_tab(gtkSourceView) != 0;
252 	}
253 
254 	/**
255 	 * Returns the number of spaces to use for each step of indent.
256 	 * See gtk_source_view_set_indent_width() for details.
257 	 *
258 	 * Returns: indent width.
259 	 */
260 	public int getIndentWidth()
261 	{
262 		return gtk_source_view_get_indent_width(gtkSourceView);
263 	}
264 
265 	/**
266 	 * Returns whether when inserting a tabulator character it should
267 	 * be replaced by a group of space characters.
268 	 *
269 	 * Returns: %TRUE if spaces are inserted instead of tabs.
270 	 */
271 	public bool getInsertSpacesInsteadOfTabs()
272 	{
273 		return gtk_source_view_get_insert_spaces_instead_of_tabs(gtkSourceView) != 0;
274 	}
275 
276 	/**
277 	 * Gets attributes and priority for the @category.
278 	 *
279 	 * Params:
280 	 *     category = the category.
281 	 *     priority = place where priority of the category will be stored.
282 	 *
283 	 * Returns: #GtkSourceMarkAttributes for the @category.
284 	 *     The object belongs to @view, so it must not be unreffed.
285 	 */
286 	public SourceMarkAttributes getMarkAttributes(string category, int* priority)
287 	{
288 		auto p = gtk_source_view_get_mark_attributes(gtkSourceView, Str.toStringz(category), priority);
289 
290 		if(p is null)
291 		{
292 			return null;
293 		}
294 
295 		return ObjectG.getDObject!(SourceMarkAttributes)(cast(GtkSourceMarkAttributes*) p);
296 	}
297 
298 	/**
299 	 * Gets the position of the right margin in the given @view.
300 	 *
301 	 * Returns: the position of the right margin.
302 	 */
303 	public uint getRightMarginPosition()
304 	{
305 		return gtk_source_view_get_right_margin_position(gtkSourceView);
306 	}
307 
308 	/**
309 	 * Returns whether line marks are displayed beside the text.
310 	 *
311 	 * Returns: %TRUE if the line marks are displayed.
312 	 *
313 	 * Since: 2.2
314 	 */
315 	public bool getShowLineMarks()
316 	{
317 		return gtk_source_view_get_show_line_marks(gtkSourceView) != 0;
318 	}
319 
320 	/**
321 	 * Returns whether line numbers are displayed beside the text.
322 	 *
323 	 * Returns: %TRUE if the line numbers are displayed.
324 	 */
325 	public bool getShowLineNumbers()
326 	{
327 		return gtk_source_view_get_show_line_numbers(gtkSourceView) != 0;
328 	}
329 
330 	/**
331 	 * Returns whether a right margin is displayed.
332 	 *
333 	 * Returns: %TRUE if the right margin is shown.
334 	 */
335 	public bool getShowRightMargin()
336 	{
337 		return gtk_source_view_get_show_right_margin(gtkSourceView) != 0;
338 	}
339 
340 	/**
341 	 * Returns %TRUE if pressing the Backspace key will try to delete spaces
342 	 * up to the previous tab stop.
343 	 *
344 	 * Returns: %TRUE if smart Backspace handling is enabled.
345 	 *
346 	 * Since: 3.18
347 	 */
348 	public bool getSmartBackspace()
349 	{
350 		return gtk_source_view_get_smart_backspace(gtkSourceView) != 0;
351 	}
352 
353 	/**
354 	 * Returns a #GtkSourceSmartHomeEndType end value specifying
355 	 * how the cursor will move when HOME and END keys are pressed.
356 	 *
357 	 * Returns: a #GtkSourceSmartHomeEndType value.
358 	 */
359 	public GtkSourceSmartHomeEndType getSmartHomeEnd()
360 	{
361 		return gtk_source_view_get_smart_home_end(gtkSourceView);
362 	}
363 
364 	/**
365 	 * Gets the #GtkSourceSpaceDrawer associated with @view. The returned object is
366 	 * guaranteed to be the same for the lifetime of @view. Each #GtkSourceView
367 	 * object has a different #GtkSourceSpaceDrawer.
368 	 *
369 	 * Returns: the #GtkSourceSpaceDrawer associated with @view.
370 	 *
371 	 * Since: 3.24
372 	 */
373 	public SpaceDrawer getSpaceDrawer()
374 	{
375 		auto p = gtk_source_view_get_space_drawer(gtkSourceView);
376 
377 		if(p is null)
378 		{
379 			return null;
380 		}
381 
382 		return ObjectG.getDObject!(SpaceDrawer)(cast(GtkSourceSpaceDrawer*) p);
383 	}
384 
385 	/**
386 	 * Returns the width of tabulation in characters.
387 	 *
388 	 * Returns: width of tab.
389 	 */
390 	public uint getTabWidth()
391 	{
392 		return gtk_source_view_get_tab_width(gtkSourceView);
393 	}
394 
395 	/**
396 	 * Determines the visual column at @iter taking into consideration the
397 	 * #GtkSourceView:tab-width of @view.
398 	 *
399 	 * Params:
400 	 *     iter = a position in @view.
401 	 *
402 	 * Returns: the visual column at @iter.
403 	 */
404 	public uint getVisualColumn(TextIter iter)
405 	{
406 		return gtk_source_view_get_visual_column(gtkSourceView, (iter is null) ? null : iter.getTextIterStruct());
407 	}
408 
409 	/**
410 	 * Inserts one indentation level at the beginning of the specified lines. The
411 	 * empty lines are not indented.
412 	 *
413 	 * Params:
414 	 *     start = #GtkTextIter of the first line to indent
415 	 *     end = #GtkTextIter of the last line to indent
416 	 *
417 	 * Since: 3.16
418 	 */
419 	public void indentLines(TextIter start, TextIter end)
420 	{
421 		gtk_source_view_indent_lines(gtkSourceView, (start is null) ? null : start.getTextIterStruct(), (end is null) ? null : end.getTextIterStruct());
422 	}
423 
424 	/**
425 	 * If %TRUE auto-indentation of text is enabled.
426 	 *
427 	 * When Enter is pressed to create a new line, the auto-indentation inserts the
428 	 * same indentation as the previous line. This is <emphasis>not</emphasis> a
429 	 * "smart indentation" where an indentation level is added or removed depending
430 	 * on the context.
431 	 *
432 	 * Params:
433 	 *     enable = whether to enable auto indentation.
434 	 */
435 	public void setAutoIndent(bool enable)
436 	{
437 		gtk_source_view_set_auto_indent(gtkSourceView, enable);
438 	}
439 
440 	/**
441 	 * Set if and how the background pattern should be displayed.
442 	 *
443 	 * Params:
444 	 *     backgroundPattern = the #GtkSourceBackgroundPatternType.
445 	 *
446 	 * Since: 3.16
447 	 */
448 	public void setBackgroundPattern(GtkSourceBackgroundPatternType backgroundPattern)
449 	{
450 		gtk_source_view_set_background_pattern(gtkSourceView, backgroundPattern);
451 	}
452 
453 	/**
454 	 * Set if and how the spaces should be visualized. Specifying @flags as 0 will
455 	 * disable display of spaces.
456 	 *
457 	 * For a finer-grained method, there is also the GtkSourceTag's
458 	 * #GtkSourceTag:draw-spaces property.
459 	 *
460 	 * Deprecated: Use gtk_source_space_drawer_set_types_for_locations()
461 	 * instead.
462 	 *
463 	 * Params:
464 	 *     flags = #GtkSourceDrawSpacesFlags specifing how white spaces should
465 	 *         be displayed
466 	 */
467 	public void setDrawSpaces(GtkSourceDrawSpacesFlags flags)
468 	{
469 		gtk_source_view_set_draw_spaces(gtkSourceView, flags);
470 	}
471 
472 	/**
473 	 * If @highlight is %TRUE the current line will be highlighted.
474 	 *
475 	 * Params:
476 	 *     highlight = whether to highlight the current line.
477 	 */
478 	public void setHighlightCurrentLine(bool highlight)
479 	{
480 		gtk_source_view_set_highlight_current_line(gtkSourceView, highlight);
481 	}
482 
483 	/**
484 	 * If %TRUE, when the tab key is pressed when several lines are selected, the
485 	 * selected lines are indented of one level instead of being replaced with a \t
486 	 * character. Shift+Tab unindents the selection.
487 	 *
488 	 * If the first or last line is not selected completely, it is also indented or
489 	 * unindented.
490 	 *
491 	 * When the selection doesn't span several lines, the tab key always replaces
492 	 * the selection with a normal \t character.
493 	 *
494 	 * Params:
495 	 *     enable = whether to indent a block when tab is pressed.
496 	 */
497 	public void setIndentOnTab(bool enable)
498 	{
499 		gtk_source_view_set_indent_on_tab(gtkSourceView, enable);
500 	}
501 
502 	/**
503 	 * Sets the number of spaces to use for each step of indent when the tab key is
504 	 * pressed. If @width is -1, the value of the #GtkSourceView:tab-width property
505 	 * will be used.
506 	 *
507 	 * The #GtkSourceView:indent-width interacts with the
508 	 * #GtkSourceView:insert-spaces-instead-of-tabs property and
509 	 * #GtkSourceView:tab-width. An example will be clearer: if the
510 	 * #GtkSourceView:indent-width is 4 and
511 	 * #GtkSourceView:tab-width is 8 and
512 	 * #GtkSourceView:insert-spaces-instead-of-tabs is %FALSE, then pressing the tab
513 	 * key at the beginning of a line will insert 4 spaces. So far so good. Pressing
514 	 * the tab key a second time will remove the 4 spaces and insert a \t character
515 	 * instead (since #GtkSourceView:tab-width is 8). On the other hand, if
516 	 * #GtkSourceView:insert-spaces-instead-of-tabs is %TRUE, the second tab key
517 	 * pressed will insert 4 more spaces for a total of 8 spaces in the
518 	 * #GtkTextBuffer.
519 	 *
520 	 * The test-widget program (available in the GtkSourceView repository) may be
521 	 * useful to better understand the indentation settings (enable the space
522 	 * drawing!).
523 	 *
524 	 * Params:
525 	 *     width = indent width in characters.
526 	 */
527 	public void setIndentWidth(int width)
528 	{
529 		gtk_source_view_set_indent_width(gtkSourceView, width);
530 	}
531 
532 	/**
533 	 * If %TRUE a tab key pressed is replaced by a group of space characters. Of
534 	 * course it is still possible to insert a real \t programmatically with the
535 	 * #GtkTextBuffer API.
536 	 *
537 	 * Params:
538 	 *     enable = whether to insert spaces instead of tabs.
539 	 */
540 	public void setInsertSpacesInsteadOfTabs(bool enable)
541 	{
542 		gtk_source_view_set_insert_spaces_instead_of_tabs(gtkSourceView, enable);
543 	}
544 
545 	/**
546 	 * Sets attributes and priority for the @category.
547 	 *
548 	 * Params:
549 	 *     category = the category.
550 	 *     attributes = mark attributes.
551 	 *     priority = priority of the category.
552 	 */
553 	public void setMarkAttributes(string category, SourceMarkAttributes attributes, int priority)
554 	{
555 		gtk_source_view_set_mark_attributes(gtkSourceView, Str.toStringz(category), (attributes is null) ? null : attributes.getSourceMarkAttributesStruct(), priority);
556 	}
557 
558 	/**
559 	 * Sets the position of the right margin in the given @view.
560 	 *
561 	 * Params:
562 	 *     pos = the width in characters where to position the right margin.
563 	 */
564 	public void setRightMarginPosition(uint pos)
565 	{
566 		gtk_source_view_set_right_margin_position(gtkSourceView, pos);
567 	}
568 
569 	/**
570 	 * If %TRUE line marks will be displayed beside the text.
571 	 *
572 	 * Params:
573 	 *     show = whether line marks should be displayed.
574 	 *
575 	 * Since: 2.2
576 	 */
577 	public void setShowLineMarks(bool show)
578 	{
579 		gtk_source_view_set_show_line_marks(gtkSourceView, show);
580 	}
581 
582 	/**
583 	 * If %TRUE line numbers will be displayed beside the text.
584 	 *
585 	 * Params:
586 	 *     show = whether line numbers should be displayed.
587 	 */
588 	public void setShowLineNumbers(bool show)
589 	{
590 		gtk_source_view_set_show_line_numbers(gtkSourceView, show);
591 	}
592 
593 	/**
594 	 * If %TRUE a right margin is displayed.
595 	 *
596 	 * Params:
597 	 *     show = whether to show a right margin.
598 	 */
599 	public void setShowRightMargin(bool show)
600 	{
601 		gtk_source_view_set_show_right_margin(gtkSourceView, show);
602 	}
603 
604 	/**
605 	 * When set to %TRUE, pressing the Backspace key will try to delete spaces
606 	 * up to the previous tab stop.
607 	 *
608 	 * Params:
609 	 *     smartBackspace = whether to enable smart Backspace handling.
610 	 *
611 	 * Since: 3.18
612 	 */
613 	public void setSmartBackspace(bool smartBackspace)
614 	{
615 		gtk_source_view_set_smart_backspace(gtkSourceView, smartBackspace);
616 	}
617 
618 	/**
619 	 * Set the desired movement of the cursor when HOME and END keys
620 	 * are pressed.
621 	 *
622 	 * Params:
623 	 *     smartHomeEnd = the desired behavior among #GtkSourceSmartHomeEndType.
624 	 */
625 	public void setSmartHomeEnd(GtkSourceSmartHomeEndType smartHomeEnd)
626 	{
627 		gtk_source_view_set_smart_home_end(gtkSourceView, smartHomeEnd);
628 	}
629 
630 	/**
631 	 * Sets the width of tabulation in characters. The #GtkTextBuffer still contains
632 	 * \t characters, but they can take a different visual width in a #GtkSourceView
633 	 * widget.
634 	 *
635 	 * Params:
636 	 *     width = width of tab in characters.
637 	 */
638 	public void setTabWidth(uint width)
639 	{
640 		gtk_source_view_set_tab_width(gtkSourceView, width);
641 	}
642 
643 	/**
644 	 * Removes one indentation level at the beginning of the
645 	 * specified lines.
646 	 *
647 	 * Params:
648 	 *     start = #GtkTextIter of the first line to indent
649 	 *     end = #GtkTextIter of the last line to indent
650 	 *
651 	 * Since: 3.16
652 	 */
653 	public void unindentLines(TextIter start, TextIter end)
654 	{
655 		gtk_source_view_unindent_lines(gtkSourceView, (start is null) ? null : start.getTextIterStruct(), (end is null) ? null : end.getTextIterStruct());
656 	}
657 
658 	protected class OnChangeCaseDelegateWrapper
659 	{
660 		void delegate(GtkSourceChangeCaseType, SourceView) dlg;
661 		gulong handlerId;
662 
663 		this(void delegate(GtkSourceChangeCaseType, SourceView) dlg)
664 		{
665 			this.dlg = dlg;
666 			onChangeCaseListeners ~= this;
667 		}
668 
669 		void remove(OnChangeCaseDelegateWrapper source)
670 		{
671 			foreach(index, wrapper; onChangeCaseListeners)
672 			{
673 				if (wrapper.handlerId == source.handlerId)
674 				{
675 					onChangeCaseListeners[index] = null;
676 					onChangeCaseListeners = std.algorithm.remove(onChangeCaseListeners, index);
677 					break;
678 				}
679 			}
680 		}
681 	}
682 	OnChangeCaseDelegateWrapper[] onChangeCaseListeners;
683 
684 	/**
685 	 * Keybinding signal to change case of the text at the current cursor position.
686 	 *
687 	 * Params:
688 	 *     caseType = the case to use
689 	 *
690 	 * Since: 3.16
691 	 */
692 	gulong addOnChangeCase(void delegate(GtkSourceChangeCaseType, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
693 	{
694 		auto wrapper = new OnChangeCaseDelegateWrapper(dlg);
695 		wrapper.handlerId = Signals.connectData(
696 			this,
697 			"change-case",
698 			cast(GCallback)&callBackChangeCase,
699 			cast(void*)wrapper,
700 			cast(GClosureNotify)&callBackChangeCaseDestroy,
701 			connectFlags);
702 		return wrapper.handlerId;
703 	}
704 
705 	extern(C) static void callBackChangeCase(GtkSourceView* sourceviewStruct, GtkSourceChangeCaseType caseType, OnChangeCaseDelegateWrapper wrapper)
706 	{
707 		wrapper.dlg(caseType, wrapper.outer);
708 	}
709 
710 	extern(C) static void callBackChangeCaseDestroy(OnChangeCaseDelegateWrapper wrapper, GClosure* closure)
711 	{
712 		wrapper.remove(wrapper);
713 	}
714 
715 	protected class OnChangeNumberDelegateWrapper
716 	{
717 		void delegate(int, SourceView) dlg;
718 		gulong handlerId;
719 
720 		this(void delegate(int, SourceView) dlg)
721 		{
722 			this.dlg = dlg;
723 			onChangeNumberListeners ~= this;
724 		}
725 
726 		void remove(OnChangeNumberDelegateWrapper source)
727 		{
728 			foreach(index, wrapper; onChangeNumberListeners)
729 			{
730 				if (wrapper.handlerId == source.handlerId)
731 				{
732 					onChangeNumberListeners[index] = null;
733 					onChangeNumberListeners = std.algorithm.remove(onChangeNumberListeners, index);
734 					break;
735 				}
736 			}
737 		}
738 	}
739 	OnChangeNumberDelegateWrapper[] onChangeNumberListeners;
740 
741 	/**
742 	 * Keybinding signal to edit a number at the current cursor position.
743 	 *
744 	 * Params:
745 	 *     count = the number to add to the number at the current position
746 	 *
747 	 * Since: 3.16
748 	 */
749 	gulong addOnChangeNumber(void delegate(int, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
750 	{
751 		auto wrapper = new OnChangeNumberDelegateWrapper(dlg);
752 		wrapper.handlerId = Signals.connectData(
753 			this,
754 			"change-number",
755 			cast(GCallback)&callBackChangeNumber,
756 			cast(void*)wrapper,
757 			cast(GClosureNotify)&callBackChangeNumberDestroy,
758 			connectFlags);
759 		return wrapper.handlerId;
760 	}
761 
762 	extern(C) static void callBackChangeNumber(GtkSourceView* sourceviewStruct, int count, OnChangeNumberDelegateWrapper wrapper)
763 	{
764 		wrapper.dlg(count, wrapper.outer);
765 	}
766 
767 	extern(C) static void callBackChangeNumberDestroy(OnChangeNumberDelegateWrapper wrapper, GClosure* closure)
768 	{
769 		wrapper.remove(wrapper);
770 	}
771 
772 	protected class OnJoinLinesDelegateWrapper
773 	{
774 		void delegate(SourceView) dlg;
775 		gulong handlerId;
776 
777 		this(void delegate(SourceView) dlg)
778 		{
779 			this.dlg = dlg;
780 			onJoinLinesListeners ~= this;
781 		}
782 
783 		void remove(OnJoinLinesDelegateWrapper source)
784 		{
785 			foreach(index, wrapper; onJoinLinesListeners)
786 			{
787 				if (wrapper.handlerId == source.handlerId)
788 				{
789 					onJoinLinesListeners[index] = null;
790 					onJoinLinesListeners = std.algorithm.remove(onJoinLinesListeners, index);
791 					break;
792 				}
793 			}
794 		}
795 	}
796 	OnJoinLinesDelegateWrapper[] onJoinLinesListeners;
797 
798 	/**
799 	 * Keybinding signal to join the lines currently selected.
800 	 *
801 	 * Since: 3.16
802 	 */
803 	gulong addOnJoinLines(void delegate(SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
804 	{
805 		auto wrapper = new OnJoinLinesDelegateWrapper(dlg);
806 		wrapper.handlerId = Signals.connectData(
807 			this,
808 			"join-lines",
809 			cast(GCallback)&callBackJoinLines,
810 			cast(void*)wrapper,
811 			cast(GClosureNotify)&callBackJoinLinesDestroy,
812 			connectFlags);
813 		return wrapper.handlerId;
814 	}
815 
816 	extern(C) static void callBackJoinLines(GtkSourceView* sourceviewStruct, OnJoinLinesDelegateWrapper wrapper)
817 	{
818 		wrapper.dlg(wrapper.outer);
819 	}
820 
821 	extern(C) static void callBackJoinLinesDestroy(OnJoinLinesDelegateWrapper wrapper, GClosure* closure)
822 	{
823 		wrapper.remove(wrapper);
824 	}
825 
826 	protected class OnLineMarkActivatedDelegateWrapper
827 	{
828 		void delegate(TextIter, Event, SourceView) dlg;
829 		gulong handlerId;
830 
831 		this(void delegate(TextIter, Event, SourceView) dlg)
832 		{
833 			this.dlg = dlg;
834 			onLineMarkActivatedListeners ~= this;
835 		}
836 
837 		void remove(OnLineMarkActivatedDelegateWrapper source)
838 		{
839 			foreach(index, wrapper; onLineMarkActivatedListeners)
840 			{
841 				if (wrapper.handlerId == source.handlerId)
842 				{
843 					onLineMarkActivatedListeners[index] = null;
844 					onLineMarkActivatedListeners = std.algorithm.remove(onLineMarkActivatedListeners, index);
845 					break;
846 				}
847 			}
848 		}
849 	}
850 	OnLineMarkActivatedDelegateWrapper[] onLineMarkActivatedListeners;
851 
852 	/**
853 	 * Emitted when a line mark has been activated (for instance when there
854 	 * was a button press in the line marks gutter). You can use @iter to
855 	 * determine on which line the activation took place.
856 	 *
857 	 * Params:
858 	 *     iter = a #GtkTextIter
859 	 *     event = the #GdkEvent that activated the event
860 	 */
861 	gulong addOnLineMarkActivated(void delegate(TextIter, Event, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
862 	{
863 		auto wrapper = new OnLineMarkActivatedDelegateWrapper(dlg);
864 		wrapper.handlerId = Signals.connectData(
865 			this,
866 			"line-mark-activated",
867 			cast(GCallback)&callBackLineMarkActivated,
868 			cast(void*)wrapper,
869 			cast(GClosureNotify)&callBackLineMarkActivatedDestroy,
870 			connectFlags);
871 		return wrapper.handlerId;
872 	}
873 
874 	extern(C) static void callBackLineMarkActivated(GtkSourceView* sourceviewStruct, GtkTextIter* iter, GdkEvent* event, OnLineMarkActivatedDelegateWrapper wrapper)
875 	{
876 		wrapper.dlg(ObjectG.getDObject!(TextIter)(iter), ObjectG.getDObject!(Event)(event), wrapper.outer);
877 	}
878 
879 	extern(C) static void callBackLineMarkActivatedDestroy(OnLineMarkActivatedDelegateWrapper wrapper, GClosure* closure)
880 	{
881 		wrapper.remove(wrapper);
882 	}
883 
884 	protected class OnMoveLinesDelegateWrapper
885 	{
886 		void delegate(bool, int, SourceView) dlg;
887 		gulong handlerId;
888 
889 		this(void delegate(bool, int, SourceView) dlg)
890 		{
891 			this.dlg = dlg;
892 			onMoveLinesListeners ~= this;
893 		}
894 
895 		void remove(OnMoveLinesDelegateWrapper source)
896 		{
897 			foreach(index, wrapper; onMoveLinesListeners)
898 			{
899 				if (wrapper.handlerId == source.handlerId)
900 				{
901 					onMoveLinesListeners[index] = null;
902 					onMoveLinesListeners = std.algorithm.remove(onMoveLinesListeners, index);
903 					break;
904 				}
905 			}
906 		}
907 	}
908 	OnMoveLinesDelegateWrapper[] onMoveLinesListeners;
909 
910 	/**
911 	 * The ::move-lines signal is a keybinding which gets emitted
912 	 * when the user initiates moving a line. The default binding key
913 	 * is Alt+Up/Down arrow. And moves the currently selected lines,
914 	 * or the current line by @count. For the moment, only
915 	 * @count of -1 or 1 is valid.
916 	 *
917 	 * The @copy parameter is deprecated, it has never been used by
918 	 * GtkSourceView (the value is always %FALSE) and was buggy.
919 	 *
920 	 * Params:
921 	 *     copy = %TRUE if the line should be copied, %FALSE if it should be
922 	 *         moved. This parameter is deprecated and will be removed in a later
923 	 *         version, it should be always %FALSE.
924 	 *     count = the number of lines to move over. Only 1 and -1 are
925 	 *         supported.
926 	 *
927 	 * Since: 2.10
928 	 */
929 	gulong addOnMoveLines(void delegate(bool, int, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
930 	{
931 		auto wrapper = new OnMoveLinesDelegateWrapper(dlg);
932 		wrapper.handlerId = Signals.connectData(
933 			this,
934 			"move-lines",
935 			cast(GCallback)&callBackMoveLines,
936 			cast(void*)wrapper,
937 			cast(GClosureNotify)&callBackMoveLinesDestroy,
938 			connectFlags);
939 		return wrapper.handlerId;
940 	}
941 
942 	extern(C) static void callBackMoveLines(GtkSourceView* sourceviewStruct, bool copy, int count, OnMoveLinesDelegateWrapper wrapper)
943 	{
944 		wrapper.dlg(copy, count, wrapper.outer);
945 	}
946 
947 	extern(C) static void callBackMoveLinesDestroy(OnMoveLinesDelegateWrapper wrapper, GClosure* closure)
948 	{
949 		wrapper.remove(wrapper);
950 	}
951 
952 	protected class OnMoveToMatchingBracketDelegateWrapper
953 	{
954 		void delegate(bool, SourceView) dlg;
955 		gulong handlerId;
956 
957 		this(void delegate(bool, SourceView) dlg)
958 		{
959 			this.dlg = dlg;
960 			onMoveToMatchingBracketListeners ~= this;
961 		}
962 
963 		void remove(OnMoveToMatchingBracketDelegateWrapper source)
964 		{
965 			foreach(index, wrapper; onMoveToMatchingBracketListeners)
966 			{
967 				if (wrapper.handlerId == source.handlerId)
968 				{
969 					onMoveToMatchingBracketListeners[index] = null;
970 					onMoveToMatchingBracketListeners = std.algorithm.remove(onMoveToMatchingBracketListeners, index);
971 					break;
972 				}
973 			}
974 		}
975 	}
976 	OnMoveToMatchingBracketDelegateWrapper[] onMoveToMatchingBracketListeners;
977 
978 	/**
979 	 * Keybinding signal to move the cursor to the matching bracket.
980 	 *
981 	 * Params:
982 	 *     extendSelection = %TRUE if the move should extend the selection
983 	 *
984 	 * Since: 3.16
985 	 */
986 	gulong addOnMoveToMatchingBracket(void delegate(bool, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
987 	{
988 		auto wrapper = new OnMoveToMatchingBracketDelegateWrapper(dlg);
989 		wrapper.handlerId = Signals.connectData(
990 			this,
991 			"move-to-matching-bracket",
992 			cast(GCallback)&callBackMoveToMatchingBracket,
993 			cast(void*)wrapper,
994 			cast(GClosureNotify)&callBackMoveToMatchingBracketDestroy,
995 			connectFlags);
996 		return wrapper.handlerId;
997 	}
998 
999 	extern(C) static void callBackMoveToMatchingBracket(GtkSourceView* sourceviewStruct, bool extendSelection, OnMoveToMatchingBracketDelegateWrapper wrapper)
1000 	{
1001 		wrapper.dlg(extendSelection, wrapper.outer);
1002 	}
1003 
1004 	extern(C) static void callBackMoveToMatchingBracketDestroy(OnMoveToMatchingBracketDelegateWrapper wrapper, GClosure* closure)
1005 	{
1006 		wrapper.remove(wrapper);
1007 	}
1008 
1009 	protected class OnMoveWordsDelegateWrapper
1010 	{
1011 		void delegate(int, SourceView) dlg;
1012 		gulong handlerId;
1013 
1014 		this(void delegate(int, SourceView) dlg)
1015 		{
1016 			this.dlg = dlg;
1017 			onMoveWordsListeners ~= this;
1018 		}
1019 
1020 		void remove(OnMoveWordsDelegateWrapper source)
1021 		{
1022 			foreach(index, wrapper; onMoveWordsListeners)
1023 			{
1024 				if (wrapper.handlerId == source.handlerId)
1025 				{
1026 					onMoveWordsListeners[index] = null;
1027 					onMoveWordsListeners = std.algorithm.remove(onMoveWordsListeners, index);
1028 					break;
1029 				}
1030 			}
1031 		}
1032 	}
1033 	OnMoveWordsDelegateWrapper[] onMoveWordsListeners;
1034 
1035 	/**
1036 	 * The ::move-words signal is a keybinding which gets emitted
1037 	 * when the user initiates moving a word. The default binding key
1038 	 * is Alt+Left/Right Arrow and moves the current selection, or the current
1039 	 * word by one word.
1040 	 *
1041 	 * Params:
1042 	 *     count = the number of words to move over
1043 	 *
1044 	 * Since: 3.0
1045 	 */
1046 	gulong addOnMoveWords(void delegate(int, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
1047 	{
1048 		auto wrapper = new OnMoveWordsDelegateWrapper(dlg);
1049 		wrapper.handlerId = Signals.connectData(
1050 			this,
1051 			"move-words",
1052 			cast(GCallback)&callBackMoveWords,
1053 			cast(void*)wrapper,
1054 			cast(GClosureNotify)&callBackMoveWordsDestroy,
1055 			connectFlags);
1056 		return wrapper.handlerId;
1057 	}
1058 
1059 	extern(C) static void callBackMoveWords(GtkSourceView* sourceviewStruct, int count, OnMoveWordsDelegateWrapper wrapper)
1060 	{
1061 		wrapper.dlg(count, wrapper.outer);
1062 	}
1063 
1064 	extern(C) static void callBackMoveWordsDestroy(OnMoveWordsDelegateWrapper wrapper, GClosure* closure)
1065 	{
1066 		wrapper.remove(wrapper);
1067 	}
1068 
1069 	protected class OnRedoDelegateWrapper
1070 	{
1071 		void delegate(SourceView) dlg;
1072 		gulong handlerId;
1073 
1074 		this(void delegate(SourceView) dlg)
1075 		{
1076 			this.dlg = dlg;
1077 			onRedoListeners ~= this;
1078 		}
1079 
1080 		void remove(OnRedoDelegateWrapper source)
1081 		{
1082 			foreach(index, wrapper; onRedoListeners)
1083 			{
1084 				if (wrapper.handlerId == source.handlerId)
1085 				{
1086 					onRedoListeners[index] = null;
1087 					onRedoListeners = std.algorithm.remove(onRedoListeners, index);
1088 					break;
1089 				}
1090 			}
1091 		}
1092 	}
1093 	OnRedoDelegateWrapper[] onRedoListeners;
1094 
1095 	/** */
1096 	gulong addOnRedo(void delegate(SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
1097 	{
1098 		auto wrapper = new OnRedoDelegateWrapper(dlg);
1099 		wrapper.handlerId = Signals.connectData(
1100 			this,
1101 			"redo",
1102 			cast(GCallback)&callBackRedo,
1103 			cast(void*)wrapper,
1104 			cast(GClosureNotify)&callBackRedoDestroy,
1105 			connectFlags);
1106 		return wrapper.handlerId;
1107 	}
1108 
1109 	extern(C) static void callBackRedo(GtkSourceView* sourceviewStruct, OnRedoDelegateWrapper wrapper)
1110 	{
1111 		wrapper.dlg(wrapper.outer);
1112 	}
1113 
1114 	extern(C) static void callBackRedoDestroy(OnRedoDelegateWrapper wrapper, GClosure* closure)
1115 	{
1116 		wrapper.remove(wrapper);
1117 	}
1118 
1119 	protected class OnShowCompletionDelegateWrapper
1120 	{
1121 		void delegate(SourceView) dlg;
1122 		gulong handlerId;
1123 
1124 		this(void delegate(SourceView) dlg)
1125 		{
1126 			this.dlg = dlg;
1127 			onShowCompletionListeners ~= this;
1128 		}
1129 
1130 		void remove(OnShowCompletionDelegateWrapper source)
1131 		{
1132 			foreach(index, wrapper; onShowCompletionListeners)
1133 			{
1134 				if (wrapper.handlerId == source.handlerId)
1135 				{
1136 					onShowCompletionListeners[index] = null;
1137 					onShowCompletionListeners = std.algorithm.remove(onShowCompletionListeners, index);
1138 					break;
1139 				}
1140 			}
1141 		}
1142 	}
1143 	OnShowCompletionDelegateWrapper[] onShowCompletionListeners;
1144 
1145 	/**
1146 	 * The ::show-completion signal is a key binding signal which gets
1147 	 * emitted when the user requests a completion, by pressing
1148 	 * <keycombo><keycap>Control</keycap><keycap>space</keycap></keycombo>.
1149 	 *
1150 	 * This will create a #GtkSourceCompletionContext with the activation
1151 	 * type as %GTK_SOURCE_COMPLETION_ACTIVATION_USER_REQUESTED.
1152 	 *
1153 	 * Applications should not connect to it, but may emit it with
1154 	 * g_signal_emit_by_name() if they need to activate the completion by
1155 	 * another means, for example with another key binding or a menu entry.
1156 	 */
1157 	gulong addOnShowCompletion(void delegate(SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
1158 	{
1159 		auto wrapper = new OnShowCompletionDelegateWrapper(dlg);
1160 		wrapper.handlerId = Signals.connectData(
1161 			this,
1162 			"show-completion",
1163 			cast(GCallback)&callBackShowCompletion,
1164 			cast(void*)wrapper,
1165 			cast(GClosureNotify)&callBackShowCompletionDestroy,
1166 			connectFlags);
1167 		return wrapper.handlerId;
1168 	}
1169 
1170 	extern(C) static void callBackShowCompletion(GtkSourceView* sourceviewStruct, OnShowCompletionDelegateWrapper wrapper)
1171 	{
1172 		wrapper.dlg(wrapper.outer);
1173 	}
1174 
1175 	extern(C) static void callBackShowCompletionDestroy(OnShowCompletionDelegateWrapper wrapper, GClosure* closure)
1176 	{
1177 		wrapper.remove(wrapper);
1178 	}
1179 
1180 	protected class OnSmartHomeEndDelegateWrapper
1181 	{
1182 		void delegate(TextIter, int, SourceView) dlg;
1183 		gulong handlerId;
1184 
1185 		this(void delegate(TextIter, int, SourceView) dlg)
1186 		{
1187 			this.dlg = dlg;
1188 			onSmartHomeEndListeners ~= this;
1189 		}
1190 
1191 		void remove(OnSmartHomeEndDelegateWrapper source)
1192 		{
1193 			foreach(index, wrapper; onSmartHomeEndListeners)
1194 			{
1195 				if (wrapper.handlerId == source.handlerId)
1196 				{
1197 					onSmartHomeEndListeners[index] = null;
1198 					onSmartHomeEndListeners = std.algorithm.remove(onSmartHomeEndListeners, index);
1199 					break;
1200 				}
1201 			}
1202 		}
1203 	}
1204 	OnSmartHomeEndDelegateWrapper[] onSmartHomeEndListeners;
1205 
1206 	/**
1207 	 * Emitted when a the cursor was moved according to the smart home
1208 	 * end setting. The signal is emitted after the cursor is moved, but
1209 	 * during the GtkTextView::move-cursor action. This can be used to find
1210 	 * out whether the cursor was moved by a normal home/end or by a smart
1211 	 * home/end.
1212 	 *
1213 	 * Params:
1214 	 *     iter = a #GtkTextIter
1215 	 *     count = the count
1216 	 *
1217 	 * Since: 3.0
1218 	 */
1219 	gulong addOnSmartHomeEnd(void delegate(TextIter, int, SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
1220 	{
1221 		auto wrapper = new OnSmartHomeEndDelegateWrapper(dlg);
1222 		wrapper.handlerId = Signals.connectData(
1223 			this,
1224 			"smart-home-end",
1225 			cast(GCallback)&callBackSmartHomeEnd,
1226 			cast(void*)wrapper,
1227 			cast(GClosureNotify)&callBackSmartHomeEndDestroy,
1228 			connectFlags);
1229 		return wrapper.handlerId;
1230 	}
1231 
1232 	extern(C) static void callBackSmartHomeEnd(GtkSourceView* sourceviewStruct, GtkTextIter* iter, int count, OnSmartHomeEndDelegateWrapper wrapper)
1233 	{
1234 		wrapper.dlg(ObjectG.getDObject!(TextIter)(iter), count, wrapper.outer);
1235 	}
1236 
1237 	extern(C) static void callBackSmartHomeEndDestroy(OnSmartHomeEndDelegateWrapper wrapper, GClosure* closure)
1238 	{
1239 		wrapper.remove(wrapper);
1240 	}
1241 
1242 	protected class OnUndoDelegateWrapper
1243 	{
1244 		void delegate(SourceView) dlg;
1245 		gulong handlerId;
1246 
1247 		this(void delegate(SourceView) dlg)
1248 		{
1249 			this.dlg = dlg;
1250 			onUndoListeners ~= this;
1251 		}
1252 
1253 		void remove(OnUndoDelegateWrapper source)
1254 		{
1255 			foreach(index, wrapper; onUndoListeners)
1256 			{
1257 				if (wrapper.handlerId == source.handlerId)
1258 				{
1259 					onUndoListeners[index] = null;
1260 					onUndoListeners = std.algorithm.remove(onUndoListeners, index);
1261 					break;
1262 				}
1263 			}
1264 		}
1265 	}
1266 	OnUndoDelegateWrapper[] onUndoListeners;
1267 
1268 	/** */
1269 	gulong addOnUndo(void delegate(SourceView) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0)
1270 	{
1271 		auto wrapper = new OnUndoDelegateWrapper(dlg);
1272 		wrapper.handlerId = Signals.connectData(
1273 			this,
1274 			"undo",
1275 			cast(GCallback)&callBackUndo,
1276 			cast(void*)wrapper,
1277 			cast(GClosureNotify)&callBackUndoDestroy,
1278 			connectFlags);
1279 		return wrapper.handlerId;
1280 	}
1281 
1282 	extern(C) static void callBackUndo(GtkSourceView* sourceviewStruct, OnUndoDelegateWrapper wrapper)
1283 	{
1284 		wrapper.dlg(wrapper.outer);
1285 	}
1286 
1287 	extern(C) static void callBackUndoDestroy(OnUndoDelegateWrapper wrapper, GClosure* closure)
1288 	{
1289 		wrapper.remove(wrapper);
1290 	}
1291 }