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
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
// This file was generated by gir (https://github.com/gtk-rs/gir)
// from gir-files (https://github.com/gtk-rs/gir-files)
// DO NOT EDIT

use glib::{
    prelude::*,
    signal::{connect_raw, SignalHandlerId},
    translate::*,
};
use std::{boxed::Box as Box_, fmt, mem, mem::transmute};

glib::wrapper! {
    /// [`SectionModel`][crate::SectionModel] is an interface that adds support for sections to list models.
    ///
    /// A [`SectionModel`][crate::SectionModel] groups successive items into so-called sections. List widgets
    /// like [`ListView`][crate::ListView] and [`GridView`][crate::GridView] then allow displaying section headers for
    /// these sections by installing a header factory.
    ///
    /// Many GTK list models support sections inherently, or they pass through the sections
    /// of a model they are wrapping.
    ///
    /// When the section groupings of a model change, the model will emit the
    /// [`sections-changed`][struct@crate::SectionModel#sections-changed] signal by calling the
    /// [`SectionModelExt::sections_changed()`][crate::prelude::SectionModelExt::sections_changed()] function. All sections in the given range
    /// then need to be queried again.
    /// The [`items-changed`][struct@crate::gio::ListModel#items-changed] signal has the same effect, all sections in
    /// that range are invalidated, too.
    ///
    /// ## Signals
    ///
    ///
    /// #### `sections-changed`
    ///  Emitted when the start-of-section state of some of the items in @model changes.
    ///
    /// Note that this signal does not specify the new section state of the
    /// items, they need to be queried manually. It is also not necessary for
    /// a model to change the section state of any of the items in the section
    /// model, though it would be rather useless to emit such a signal.
    ///
    /// The [`items-changed`][struct@crate::gio::ListModel#items-changed] implies the effect of the
    /// [`sections-changed`][struct@crate::SectionModel#sections-changed] signal for all the items
    /// it covers.
    ///
    ///
    /// <details><summary><h4>ListModel</h4></summary>
    ///
    ///
    /// #### `items-changed`
    ///  This signal is emitted whenever items were added to or removed
    /// from @list. At @position, @removed items were removed and @added
    /// items were added in their place.
    ///
    /// Note: If `removed != added`, the positions of all later items
    /// in the model change.
    ///
    ///
    /// </details>
    ///
    /// # Implements
    ///
    /// [`SectionModelExt`][trait@crate::prelude::SectionModelExt], [`trait@gio::prelude::ListModelExt`]
    #[doc(alias = "GtkSectionModel")]
    pub struct SectionModel(Interface<ffi::GtkSectionModel, ffi::GtkSectionModelInterface>) @requires gio::ListModel;

    match fn {
        type_ => || ffi::gtk_section_model_get_type(),
    }
}

impl SectionModel {
    pub const NONE: Option<&'static SectionModel> = None;
}

mod sealed {
    pub trait Sealed {}
    impl<T: super::IsA<super::SectionModel>> Sealed for T {}
}

/// Trait containing all [`struct@SectionModel`] methods.
///
/// # Implementors
///
/// [`FilterListModel`][struct@crate::FilterListModel], [`FlattenListModel`][struct@crate::FlattenListModel], [`MapListModel`][struct@crate::MapListModel], [`MultiSelection`][struct@crate::MultiSelection], [`NoSelection`][struct@crate::NoSelection], [`SectionModel`][struct@crate::SectionModel], [`SingleSelection`][struct@crate::SingleSelection], [`SliceListModel`][struct@crate::SliceListModel], [`SortListModel`][struct@crate::SortListModel]
pub trait SectionModelExt: IsA<SectionModel> + sealed::Sealed + 'static {
    /// Query the section that covers the given position. The number of
    /// items in the section can be computed by `out_end - out_start`.
    ///
    /// If the position is larger than the number of items, a single
    /// range from n_items to G_MAXUINT will be returned.
    /// ## `position`
    /// the position of the item to query
    ///
    /// # Returns
    ///
    ///
    /// ## `out_start`
    /// the position of the first item in the section
    ///
    /// ## `out_end`
    /// the position of the first item not part of the section
    ///   anymore.
    #[doc(alias = "gtk_section_model_get_section")]
    #[doc(alias = "get_section")]
    fn section(&self, position: u32) -> (u32, u32) {
        unsafe {
            let mut out_start = mem::MaybeUninit::uninit();
            let mut out_end = mem::MaybeUninit::uninit();
            ffi::gtk_section_model_get_section(
                self.as_ref().to_glib_none().0,
                position,
                out_start.as_mut_ptr(),
                out_end.as_mut_ptr(),
            );
            (out_start.assume_init(), out_end.assume_init())
        }
    }

    #[doc(alias = "gtk_section_model_sections_changed")]
    fn sections_changed(&self, position: u32, n_items: u32) {
        unsafe {
            ffi::gtk_section_model_sections_changed(
                self.as_ref().to_glib_none().0,
                position,
                n_items,
            );
        }
    }

    /// Emitted when the start-of-section state of some of the items in @model changes.
    ///
    /// Note that this signal does not specify the new section state of the
    /// items, they need to be queried manually. It is also not necessary for
    /// a model to change the section state of any of the items in the section
    /// model, though it would be rather useless to emit such a signal.
    ///
    /// The [`items-changed`][struct@crate::gio::ListModel#items-changed] implies the effect of the
    /// [`sections-changed`][struct@crate::SectionModel#sections-changed] signal for all the items
    /// it covers.
    /// ## `position`
    /// The first item that may have changed
    /// ## `n_items`
    /// number of items with changes
    #[cfg(feature = "v4_12")]
    #[cfg_attr(docsrs, doc(cfg(feature = "v4_12")))]
    #[doc(alias = "sections-changed")]
    fn connect_sections_changed<F: Fn(&Self, u32, u32) + 'static>(&self, f: F) -> SignalHandlerId {
        unsafe extern "C" fn sections_changed_trampoline<
            P: IsA<SectionModel>,
            F: Fn(&P, u32, u32) + 'static,
        >(
            this: *mut ffi::GtkSectionModel,
            position: libc::c_uint,
            n_items: libc::c_uint,
            f: glib::ffi::gpointer,
        ) {
            let f: &F = &*(f as *const F);
            f(
                SectionModel::from_glib_borrow(this).unsafe_cast_ref(),
                position,
                n_items,
            )
        }
        unsafe {
            let f: Box_<F> = Box_::new(f);
            connect_raw(
                self.as_ptr() as *mut _,
                b"sections-changed\0".as_ptr() as *const _,
                Some(transmute::<_, unsafe extern "C" fn()>(
                    sections_changed_trampoline::<Self, F> as *const (),
                )),
                Box_::into_raw(f),
            )
        }
    }
}

impl<O: IsA<SectionModel>> SectionModelExt for O {}

impl fmt::Display for SectionModel {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        f.write_str("SectionModel")
    }
}