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