breadx_image/
ext.rs

1//               Copyright John Nunley, 2022.
2// Distributed under the Boost Software License, Version 1.0.
3//       (See accompanying file LICENSE or copy at
4//         https://www.boost.org/LICENSE_1_0.txt)
5
6#![allow(clippy::too_many_arguments)]
7
8use super::Image;
9use alloc::vec::Vec;
10use breadx::{
11    display::Cookie,
12    display::{Display, DisplayExt as _, DisplayFunctionsExt as _},
13    protocol::xproto::{Drawable, Gcontext, ImageFormat},
14};
15
16#[cfg(feature = "async")]
17use breadx::{
18    display::{AsyncDisplay, AsyncDisplayExt as _},
19    futures,
20};
21
22pub trait DisplayExt: Display {
23    /// Send an [`Image`] to the display.
24    fn put_ximage(
25        &mut self,
26        image: &Image<impl AsRef<[u8]>>,
27        drawable: impl Into<Drawable>,
28        gc: impl Into<Gcontext>,
29        dst_x: i16,
30        dst_y: i16,
31    ) -> breadx::Result<Cookie<()>> {
32        let req = image.put_image_request(drawable, gc, dst_x, dst_y);
33        self.send_void_request(req, true)
34    }
35
36    fn put_ximage_checked(
37        &mut self,
38        image: &Image<impl AsRef<[u8]>>,
39        drawable: impl Into<Drawable>,
40        gc: impl Into<Gcontext>,
41        dst_x: i16,
42        dst_y: i16,
43    ) -> breadx::Result<()> {
44        let cookie = self.put_ximage(image, drawable, gc, dst_x, dst_y)?;
45        self.wait_for_reply(cookie)
46    }
47
48    /// Send a subimage of an [`Image`] to the display.
49    fn put_subimage(
50        &mut self,
51        image: &Image<impl AsRef<[u8]>>,
52        drawable: impl Into<Drawable>,
53        gc: impl Into<Gcontext>,
54        src_x: usize,
55        src_y: usize,
56        width: usize,
57        height: usize,
58        dst_x: i16,
59        dst_y: i16,
60    ) -> breadx::Result<Cookie<()>> {
61        image.put_subimage_request(
62            drawable,
63            gc,
64            src_x,
65            src_y,
66            width,
67            height,
68            dst_x,
69            dst_y,
70            true,
71            |req| self.send_request_raw(req).map(Cookie::from_sequence),
72        )
73    }
74
75    fn put_subimage_checked(
76        &mut self,
77        image: &Image<impl AsRef<[u8]>>,
78        drawable: impl Into<Drawable>,
79        gc: impl Into<Gcontext>,
80        src_x: usize,
81        src_y: usize,
82        width: usize,
83        height: usize,
84        dst_x: i16,
85        dst_y: i16,
86    ) -> breadx::Result<()> {
87        let cookie = self.put_subimage(
88            image, drawable, gc, src_x, src_y, width, height, dst_x, dst_y,
89        )?;
90        self.wait_for_reply(cookie)
91    }
92
93    fn get_ximage(
94        &mut self,
95        drawable: impl Into<Drawable>,
96        format: ImageFormat,
97        x: i16,
98        y: i16,
99        width: u16,
100        height: u16,
101        plane_mask: u32,
102    ) -> breadx::Result<Image<Vec<u8>>> {
103        let repl =
104            self.get_image_immediate(format, drawable.into(), x, y, width, height, plane_mask)?;
105        Image::from_get_image_reply(repl, width, height, format, self.setup())
106    }
107}
108
109impl<D: Display + ?Sized> DisplayExt for D {}
110
111#[cfg(feature = "async")]
112pub trait AsyncDisplayExt: AsyncDisplay {
113    /// Send an [`Image`] to the display.
114    fn put_ximage(
115        &mut self,
116        image: &Image<impl AsRef<[u8]>>,
117        drawable: impl Into<Drawable>,
118        gc: impl Into<Gcontext>,
119        dst_x: i16,
120        dst_y: i16,
121    ) -> futures::SendRequest<'_, Self, ()> {
122        let req = image.put_image_request(drawable, gc, dst_x, dst_y);
123        self.send_void_request(req, true)
124    }
125
126    fn put_ximage_checked(
127        &mut self,
128        image: &Image<impl AsRef<[u8]>>,
129        drawable: impl Into<Drawable>,
130        gc: impl Into<Gcontext>,
131        dst_x: i16,
132        dst_y: i16,
133    ) -> futures::CheckedSendRequest<'_, Self, ()> {
134        let cookie = self.put_ximage(image, drawable, gc, dst_x, dst_y);
135        cookie.into()
136    }
137
138    /// Send a subimage of an [`Image`] to the display.
139    fn put_subimage(
140        &mut self,
141        image: &Image<impl AsRef<[u8]>>,
142        drawable: impl Into<Drawable>,
143        gc: impl Into<Gcontext>,
144        src_x: usize,
145        src_y: usize,
146        width: usize,
147        height: usize,
148        dst_x: i16,
149        dst_y: i16,
150    ) -> futures::SendRequestRaw<'_, Self> {
151        image.put_subimage_request(
152            drawable,
153            gc,
154            src_x,
155            src_y,
156            width,
157            height,
158            dst_x,
159            dst_y,
160            true,
161            move |req| self.send_request_raw(req),
162        )
163    }
164}
165
166#[cfg(feature = "async")]
167impl<D: AsyncDisplay + ?Sized> AsyncDisplayExt for D {}