1use crate::{ffi, Window};
6use glib::{
7 prelude::*,
8 signal::{connect_raw, SignalHandlerId},
9 translate::*,
10};
11use std::{boxed::Box as Box_, pin::Pin};
12
13glib::wrapper! {
14 #[doc(alias = "GtkAlertDialog")]
15 pub struct AlertDialog(Object<ffi::GtkAlertDialog, ffi::GtkAlertDialogClass>);
16
17 match fn {
18 type_ => || ffi::gtk_alert_dialog_get_type(),
19 }
20}
21
22impl AlertDialog {
23 pub fn builder() -> AlertDialogBuilder {
33 AlertDialogBuilder::new()
34 }
35
36 #[doc(alias = "gtk_alert_dialog_choose")]
37 pub fn choose<P: FnOnce(Result<i32, glib::Error>) + 'static>(
38 &self,
39 parent: Option<&impl IsA<Window>>,
40 cancellable: Option<&impl IsA<gio::Cancellable>>,
41 callback: P,
42 ) {
43 let main_context = glib::MainContext::ref_thread_default();
44 let is_main_context_owner = main_context.is_owner();
45 let has_acquired_main_context = (!is_main_context_owner)
46 .then(|| main_context.acquire().ok())
47 .flatten();
48 assert!(
49 is_main_context_owner || has_acquired_main_context.is_some(),
50 "Async operations only allowed if the thread is owning the MainContext"
51 );
52
53 let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
54 Box_::new(glib::thread_guard::ThreadGuard::new(callback));
55 unsafe extern "C" fn choose_trampoline<P: FnOnce(Result<i32, glib::Error>) + 'static>(
56 _source_object: *mut glib::gobject_ffi::GObject,
57 res: *mut gio::ffi::GAsyncResult,
58 user_data: glib::ffi::gpointer,
59 ) {
60 let mut error = std::ptr::null_mut();
61 let ret =
62 ffi::gtk_alert_dialog_choose_finish(_source_object as *mut _, res, &mut error);
63 let result = if error.is_null() {
64 Ok(ret)
65 } else {
66 Err(from_glib_full(error))
67 };
68 let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
69 Box_::from_raw(user_data as *mut _);
70 let callback: P = callback.into_inner();
71 callback(result);
72 }
73 let callback = choose_trampoline::<P>;
74 unsafe {
75 ffi::gtk_alert_dialog_choose(
76 self.to_glib_none().0,
77 parent.map(|p| p.as_ref()).to_glib_none().0,
78 cancellable.map(|p| p.as_ref()).to_glib_none().0,
79 Some(callback),
80 Box_::into_raw(user_data) as *mut _,
81 );
82 }
83 }
84
85 pub fn choose_future(
86 &self,
87 parent: Option<&(impl IsA<Window> + Clone + 'static)>,
88 ) -> Pin<Box_<dyn std::future::Future<Output = Result<i32, glib::Error>> + 'static>> {
89 let parent = parent.map(ToOwned::to_owned);
90 Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
91 obj.choose(
92 parent.as_ref().map(::std::borrow::Borrow::borrow),
93 Some(cancellable),
94 move |res| {
95 send.resolve(res);
96 },
97 );
98 }))
99 }
100
101 #[doc(alias = "gtk_alert_dialog_get_buttons")]
102 #[doc(alias = "get_buttons")]
103 pub fn buttons(&self) -> Vec<glib::GString> {
104 unsafe {
105 FromGlibPtrContainer::from_glib_none(ffi::gtk_alert_dialog_get_buttons(
106 self.to_glib_none().0,
107 ))
108 }
109 }
110
111 #[doc(alias = "gtk_alert_dialog_get_cancel_button")]
112 #[doc(alias = "get_cancel_button")]
113 #[doc(alias = "cancel-button")]
114 pub fn cancel_button(&self) -> i32 {
115 unsafe { ffi::gtk_alert_dialog_get_cancel_button(self.to_glib_none().0) }
116 }
117
118 #[doc(alias = "gtk_alert_dialog_get_default_button")]
119 #[doc(alias = "get_default_button")]
120 #[doc(alias = "default-button")]
121 pub fn default_button(&self) -> i32 {
122 unsafe { ffi::gtk_alert_dialog_get_default_button(self.to_glib_none().0) }
123 }
124
125 #[doc(alias = "gtk_alert_dialog_get_detail")]
126 #[doc(alias = "get_detail")]
127 pub fn detail(&self) -> glib::GString {
128 unsafe { from_glib_none(ffi::gtk_alert_dialog_get_detail(self.to_glib_none().0)) }
129 }
130
131 #[doc(alias = "gtk_alert_dialog_get_message")]
132 #[doc(alias = "get_message")]
133 pub fn message(&self) -> glib::GString {
134 unsafe { from_glib_none(ffi::gtk_alert_dialog_get_message(self.to_glib_none().0)) }
135 }
136
137 #[doc(alias = "gtk_alert_dialog_get_modal")]
138 #[doc(alias = "get_modal")]
139 #[doc(alias = "modal")]
140 pub fn is_modal(&self) -> bool {
141 unsafe { from_glib(ffi::gtk_alert_dialog_get_modal(self.to_glib_none().0)) }
142 }
143
144 #[doc(alias = "gtk_alert_dialog_set_buttons")]
145 #[doc(alias = "buttons")]
146 pub fn set_buttons(&self, labels: &[&str]) {
147 unsafe {
148 ffi::gtk_alert_dialog_set_buttons(self.to_glib_none().0, labels.to_glib_none().0);
149 }
150 }
151
152 #[doc(alias = "gtk_alert_dialog_set_cancel_button")]
153 #[doc(alias = "cancel-button")]
154 pub fn set_cancel_button(&self, button: i32) {
155 unsafe {
156 ffi::gtk_alert_dialog_set_cancel_button(self.to_glib_none().0, button);
157 }
158 }
159
160 #[doc(alias = "gtk_alert_dialog_set_default_button")]
161 #[doc(alias = "default-button")]
162 pub fn set_default_button(&self, button: i32) {
163 unsafe {
164 ffi::gtk_alert_dialog_set_default_button(self.to_glib_none().0, button);
165 }
166 }
167
168 #[doc(alias = "gtk_alert_dialog_set_detail")]
169 #[doc(alias = "detail")]
170 pub fn set_detail(&self, detail: &str) {
171 unsafe {
172 ffi::gtk_alert_dialog_set_detail(self.to_glib_none().0, detail.to_glib_none().0);
173 }
174 }
175
176 #[doc(alias = "gtk_alert_dialog_set_message")]
177 #[doc(alias = "message")]
178 pub fn set_message(&self, message: &str) {
179 unsafe {
180 ffi::gtk_alert_dialog_set_message(self.to_glib_none().0, message.to_glib_none().0);
181 }
182 }
183
184 #[doc(alias = "gtk_alert_dialog_set_modal")]
185 #[doc(alias = "modal")]
186 pub fn set_modal(&self, modal: bool) {
187 unsafe {
188 ffi::gtk_alert_dialog_set_modal(self.to_glib_none().0, modal.into_glib());
189 }
190 }
191
192 #[doc(alias = "gtk_alert_dialog_show")]
193 pub fn show(&self, parent: Option<&impl IsA<Window>>) {
194 unsafe {
195 ffi::gtk_alert_dialog_show(
196 self.to_glib_none().0,
197 parent.map(|p| p.as_ref()).to_glib_none().0,
198 );
199 }
200 }
201
202 #[cfg(feature = "v4_10")]
203 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
204 #[doc(alias = "buttons")]
205 pub fn connect_buttons_notify<F: Fn(&Self) + 'static>(&self, f: F) -> SignalHandlerId {
206 unsafe extern "C" fn notify_buttons_trampoline<F: Fn(&AlertDialog) + 'static>(
207 this: *mut ffi::GtkAlertDialog,
208 _param_spec: glib::ffi::gpointer,
209 f: glib::ffi::gpointer,
210 ) {
211 let f: &F = &*(f as *const F);
212 f(&from_glib_borrow(this))
213 }
214 unsafe {
215 let f: Box_<F> = Box_::new(f);
216 connect_raw(
217 self.as_ptr() as *mut _,
218 c"notify::buttons".as_ptr() as *const _,
219 Some(std::mem::transmute::<*const (), unsafe extern "C" fn()>(
220 notify_buttons_trampoline::<F> as *const (),
221 )),
222 Box_::into_raw(f),
223 )
224 }
225 }
226
227 #[cfg(feature = "v4_10")]
228 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
229 #[doc(alias = "cancel-button")]
230 pub fn connect_cancel_button_notify<F: Fn(&Self) + 'static>(&self, f: F) -> SignalHandlerId {
231 unsafe extern "C" fn notify_cancel_button_trampoline<F: Fn(&AlertDialog) + 'static>(
232 this: *mut ffi::GtkAlertDialog,
233 _param_spec: glib::ffi::gpointer,
234 f: glib::ffi::gpointer,
235 ) {
236 let f: &F = &*(f as *const F);
237 f(&from_glib_borrow(this))
238 }
239 unsafe {
240 let f: Box_<F> = Box_::new(f);
241 connect_raw(
242 self.as_ptr() as *mut _,
243 c"notify::cancel-button".as_ptr() as *const _,
244 Some(std::mem::transmute::<*const (), unsafe extern "C" fn()>(
245 notify_cancel_button_trampoline::<F> as *const (),
246 )),
247 Box_::into_raw(f),
248 )
249 }
250 }
251
252 #[cfg(feature = "v4_10")]
253 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
254 #[doc(alias = "default-button")]
255 pub fn connect_default_button_notify<F: Fn(&Self) + 'static>(&self, f: F) -> SignalHandlerId {
256 unsafe extern "C" fn notify_default_button_trampoline<F: Fn(&AlertDialog) + 'static>(
257 this: *mut ffi::GtkAlertDialog,
258 _param_spec: glib::ffi::gpointer,
259 f: glib::ffi::gpointer,
260 ) {
261 let f: &F = &*(f as *const F);
262 f(&from_glib_borrow(this))
263 }
264 unsafe {
265 let f: Box_<F> = Box_::new(f);
266 connect_raw(
267 self.as_ptr() as *mut _,
268 c"notify::default-button".as_ptr() as *const _,
269 Some(std::mem::transmute::<*const (), unsafe extern "C" fn()>(
270 notify_default_button_trampoline::<F> as *const (),
271 )),
272 Box_::into_raw(f),
273 )
274 }
275 }
276
277 #[cfg(feature = "v4_10")]
278 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
279 #[doc(alias = "detail")]
280 pub fn connect_detail_notify<F: Fn(&Self) + 'static>(&self, f: F) -> SignalHandlerId {
281 unsafe extern "C" fn notify_detail_trampoline<F: Fn(&AlertDialog) + 'static>(
282 this: *mut ffi::GtkAlertDialog,
283 _param_spec: glib::ffi::gpointer,
284 f: glib::ffi::gpointer,
285 ) {
286 let f: &F = &*(f as *const F);
287 f(&from_glib_borrow(this))
288 }
289 unsafe {
290 let f: Box_<F> = Box_::new(f);
291 connect_raw(
292 self.as_ptr() as *mut _,
293 c"notify::detail".as_ptr() as *const _,
294 Some(std::mem::transmute::<*const (), unsafe extern "C" fn()>(
295 notify_detail_trampoline::<F> as *const (),
296 )),
297 Box_::into_raw(f),
298 )
299 }
300 }
301
302 #[cfg(feature = "v4_10")]
303 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
304 #[doc(alias = "message")]
305 pub fn connect_message_notify<F: Fn(&Self) + 'static>(&self, f: F) -> SignalHandlerId {
306 unsafe extern "C" fn notify_message_trampoline<F: Fn(&AlertDialog) + 'static>(
307 this: *mut ffi::GtkAlertDialog,
308 _param_spec: glib::ffi::gpointer,
309 f: glib::ffi::gpointer,
310 ) {
311 let f: &F = &*(f as *const F);
312 f(&from_glib_borrow(this))
313 }
314 unsafe {
315 let f: Box_<F> = Box_::new(f);
316 connect_raw(
317 self.as_ptr() as *mut _,
318 c"notify::message".as_ptr() as *const _,
319 Some(std::mem::transmute::<*const (), unsafe extern "C" fn()>(
320 notify_message_trampoline::<F> as *const (),
321 )),
322 Box_::into_raw(f),
323 )
324 }
325 }
326
327 #[cfg(feature = "v4_10")]
328 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
329 #[doc(alias = "modal")]
330 pub fn connect_modal_notify<F: Fn(&Self) + 'static>(&self, f: F) -> SignalHandlerId {
331 unsafe extern "C" fn notify_modal_trampoline<F: Fn(&AlertDialog) + 'static>(
332 this: *mut ffi::GtkAlertDialog,
333 _param_spec: glib::ffi::gpointer,
334 f: glib::ffi::gpointer,
335 ) {
336 let f: &F = &*(f as *const F);
337 f(&from_glib_borrow(this))
338 }
339 unsafe {
340 let f: Box_<F> = Box_::new(f);
341 connect_raw(
342 self.as_ptr() as *mut _,
343 c"notify::modal".as_ptr() as *const _,
344 Some(std::mem::transmute::<*const (), unsafe extern "C" fn()>(
345 notify_modal_trampoline::<F> as *const (),
346 )),
347 Box_::into_raw(f),
348 )
349 }
350 }
351}
352
353#[cfg(feature = "v4_10")]
354#[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
355impl Default for AlertDialog {
356 fn default() -> Self {
357 glib::object::Object::new::<Self>()
358 }
359}
360
361#[must_use = "The builder must be built to be used"]
366pub struct AlertDialogBuilder {
367 builder: glib::object::ObjectBuilder<'static, AlertDialog>,
368}
369
370impl AlertDialogBuilder {
371 fn new() -> Self {
372 Self {
373 builder: glib::object::Object::builder(),
374 }
375 }
376
377 #[cfg(feature = "v4_10")]
378 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
379 pub fn buttons(self, buttons: impl Into<glib::StrV>) -> Self {
380 Self {
381 builder: self.builder.property("buttons", buttons.into()),
382 }
383 }
384
385 #[cfg(feature = "v4_10")]
386 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
387 pub fn cancel_button(self, cancel_button: i32) -> Self {
388 Self {
389 builder: self.builder.property("cancel-button", cancel_button),
390 }
391 }
392
393 #[cfg(feature = "v4_10")]
394 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
395 pub fn default_button(self, default_button: i32) -> Self {
396 Self {
397 builder: self.builder.property("default-button", default_button),
398 }
399 }
400
401 #[cfg(feature = "v4_10")]
402 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
403 pub fn detail(self, detail: impl Into<glib::GString>) -> Self {
404 Self {
405 builder: self.builder.property("detail", detail.into()),
406 }
407 }
408
409 #[cfg(feature = "v4_10")]
410 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
411 pub fn message(self, message: impl Into<glib::GString>) -> Self {
412 Self {
413 builder: self.builder.property("message", message.into()),
414 }
415 }
416
417 #[cfg(feature = "v4_10")]
418 #[cfg_attr(docsrs, doc(cfg(feature = "v4_10")))]
419 pub fn modal(self, modal: bool) -> Self {
420 Self {
421 builder: self.builder.property("modal", modal),
422 }
423 }
424
425 #[must_use = "Building the object from the builder is usually expensive and is not expected to have side effects"]
428 pub fn build(self) -> AlertDialog {
429 assert_initialized_main_thread!();
430 self.builder.build()
431 }
432}