Skip to content

Commit 4748916

Browse files
ids1024Drakulix
authored andcommitted
Make RenderElement implementations generic to reduce duplication
It would make sense to have a bound like `for<'frame> R::Frame<'frame>: AsGlowFrame<'frame>`. But that appears to not behave properly due to current limitations of the borrow checker: https://blog.rust-lang.org/2022/10/28/gats-stabilization.html#implied-static-requirement-from-higher-ranked-trait-bounds Instead, this makes `glow_frame` and `glow_frame_mut` associated functions of the `AsGlowRenderer` trait. Then it is pretty straightforward to make the `RenderElement` implementations generic using that and `FromGlesError`. It would make sense to make `Self::Error: FromGlessError` a requirement of the `AsGlowRenderer` trait, but due to the lack of implied bounds support, that produces a bunch of errors about missing bounds. If Rustc improves that eventually, some bounds could be cleaned up a bit: rust-lang/rust#44491
1 parent 3dd3460 commit 4748916

File tree

3 files changed

+63
-222
lines changed

3 files changed

+63
-222
lines changed

src/backend/render/element.rs

Lines changed: 29 additions & 81 deletions
Original file line numberDiff line numberDiff line change
@@ -11,12 +11,12 @@ use smithay::{
1111
gles::{GlesError, GlesTexture},
1212
glow::{GlowFrame, GlowRenderer},
1313
utils::{CommitCounter, DamageSet, OpaqueRegions},
14-
Frame, ImportAll, ImportMem, Renderer,
14+
ImportAll, ImportMem, Renderer,
1515
},
1616
utils::{Buffer as BufferCoords, Logical, Physical, Point, Rectangle, Scale},
1717
};
1818

19-
use super::{cursor::CursorRenderElement, GlMultiError, GlMultiFrame, GlMultiRenderer};
19+
use super::{cursor::CursorRenderElement, GlMultiRenderer};
2020

2121
pub enum CosmicElement<R>
2222
where
@@ -179,72 +179,32 @@ where
179179
}
180180
}
181181

182-
impl RenderElement<GlowRenderer> for CosmicElement<GlowRenderer> {
182+
impl<R> RenderElement<R> for CosmicElement<R>
183+
where
184+
R: AsGlowRenderer + Renderer + ImportAll + ImportMem,
185+
<R as Renderer>::TextureId: 'static,
186+
<R as Renderer>::Error: FromGlesError,
187+
CosmicMappedRenderElement<R>: RenderElement<R>,
188+
{
183189
fn draw<'frame>(
184190
&self,
185-
frame: &mut <GlowRenderer as Renderer>::Frame<'frame>,
191+
frame: &mut R::Frame<'frame>,
186192
src: Rectangle<f64, BufferCoords>,
187193
dst: Rectangle<i32, Physical>,
188194
damage: &[Rectangle<i32, Physical>],
189195
opaque_regions: &[Rectangle<i32, Physical>],
190-
) -> Result<(), <GlowRenderer as Renderer>::Error> {
196+
) -> Result<(), R::Error> {
191197
match self {
192198
CosmicElement::Workspace(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
193199
CosmicElement::Cursor(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
194200
CosmicElement::Dnd(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
195201
CosmicElement::MoveGrab(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
196202
CosmicElement::AdditionalDamage(elem) => {
197-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
203+
RenderElement::<R>::draw(elem, frame, src, dst, damage, opaque_regions)
198204
}
199-
CosmicElement::Mirror(elem) => {
200-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
201-
}
202-
#[cfg(feature = "debug")]
203-
CosmicElement::Egui(elem) => {
204-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
205-
}
206-
}
207-
}
208-
209-
fn underlying_storage(&self, renderer: &mut GlowRenderer) -> Option<UnderlyingStorage> {
210-
match self {
211-
CosmicElement::Workspace(elem) => elem.underlying_storage(renderer),
212-
CosmicElement::Cursor(elem) => elem.underlying_storage(renderer),
213-
CosmicElement::Dnd(elem) => elem.underlying_storage(renderer),
214-
CosmicElement::MoveGrab(elem) => elem.underlying_storage(renderer),
215-
CosmicElement::AdditionalDamage(elem) => elem.underlying_storage(renderer),
216-
CosmicElement::Mirror(elem) => elem.underlying_storage(renderer),
217-
#[cfg(feature = "debug")]
218-
CosmicElement::Egui(elem) => elem.underlying_storage(renderer),
219-
}
220-
}
221-
}
222-
223-
impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicElement<GlMultiRenderer<'a>> {
224-
fn draw<'frame>(
225-
&self,
226-
frame: &mut GlMultiFrame<'a, 'frame>,
227-
src: Rectangle<f64, BufferCoords>,
228-
dst: Rectangle<i32, Physical>,
229-
damage: &[Rectangle<i32, Physical>],
230-
opaque_regions: &[Rectangle<i32, Physical>],
231-
) -> Result<(), GlMultiError> {
232-
match self {
233-
CosmicElement::Workspace(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
234-
CosmicElement::Cursor(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
235-
CosmicElement::Dnd(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
236-
CosmicElement::MoveGrab(elem) => elem.draw(frame, src, dst, damage, opaque_regions),
237-
CosmicElement::AdditionalDamage(elem) => RenderElement::<GlMultiRenderer<'a>>::draw(
238-
elem,
239-
frame,
240-
src,
241-
dst,
242-
damage,
243-
opaque_regions,
244-
),
245205
CosmicElement::Mirror(elem) => {
246206
let elem = {
247-
let glow_frame = frame.glow_frame_mut();
207+
let glow_frame = R::glow_frame_mut(frame);
248208
RenderElement::<GlowRenderer>::draw(
249209
elem,
250210
glow_frame,
@@ -253,14 +213,14 @@ impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicElement<GlMultiRenderer<'a
253213
damage,
254214
opaque_regions,
255215
)
256-
.map_err(|err| GlMultiError::Render(err))
216+
.map_err(FromGlesError::from_gles_error)
257217
};
258218
elem
259219
}
260220
#[cfg(feature = "debug")]
261221
CosmicElement::Egui(elem) => {
262222
let elem = {
263-
let glow_frame = frame.glow_frame_mut();
223+
let glow_frame = R::glow_frame_mut(frame);
264224
RenderElement::<GlowRenderer>::draw(
265225
elem,
266226
glow_frame,
@@ -269,14 +229,14 @@ impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicElement<GlMultiRenderer<'a
269229
damage,
270230
opaque_regions,
271231
)
272-
.map_err(|err| GlMultiError::Render(err))
232+
.map_err(FromGlesError::from_gles_error)
273233
};
274234
elem
275235
}
276236
}
277237
}
278238

279-
fn underlying_storage(&self, renderer: &mut GlMultiRenderer<'a>) -> Option<UnderlyingStorage> {
239+
fn underlying_storage(&self, renderer: &mut R) -> Option<UnderlyingStorage> {
280240
match self {
281241
CosmicElement::Workspace(elem) => elem.underlying_storage(renderer),
282242
CosmicElement::Cursor(elem) => elem.underlying_storage(renderer),
@@ -361,6 +321,8 @@ where
361321
{
362322
fn glow_renderer(&self) -> &GlowRenderer;
363323
fn glow_renderer_mut(&mut self) -> &mut GlowRenderer;
324+
fn glow_frame<'a, 'frame>(frame: &'a Self::Frame<'frame>) -> &'a GlowFrame<'frame>;
325+
fn glow_frame_mut<'a, 'frame>(frame: &'a mut Self::Frame<'frame>) -> &'a mut GlowFrame<'frame>;
364326
}
365327

366328
impl AsGlowRenderer for GlowRenderer {
@@ -370,6 +332,12 @@ impl AsGlowRenderer for GlowRenderer {
370332
fn glow_renderer_mut(&mut self) -> &mut GlowRenderer {
371333
self
372334
}
335+
fn glow_frame<'a, 'frame>(frame: &'a Self::Frame<'frame>) -> &'a GlowFrame<'frame> {
336+
frame
337+
}
338+
fn glow_frame_mut<'a, 'frame>(frame: &'a mut Self::Frame<'frame>) -> &'a mut GlowFrame<'frame> {
339+
frame
340+
}
373341
}
374342

375343
impl<'a> AsGlowRenderer for GlMultiRenderer<'a> {
@@ -379,31 +347,11 @@ impl<'a> AsGlowRenderer for GlMultiRenderer<'a> {
379347
fn glow_renderer_mut(&mut self) -> &mut GlowRenderer {
380348
self.as_mut()
381349
}
382-
}
383-
384-
pub trait AsGlowFrame<'a>
385-
where
386-
Self: Frame,
387-
{
388-
fn glow_frame(&self) -> &GlowFrame<'a>;
389-
fn glow_frame_mut(&mut self) -> &mut GlowFrame<'a>;
390-
}
391-
392-
impl<'frame> AsGlowFrame<'frame> for GlowFrame<'frame> {
393-
fn glow_frame(&self) -> &GlowFrame<'frame> {
394-
self
395-
}
396-
fn glow_frame_mut(&mut self) -> &mut GlowFrame<'frame> {
397-
self
398-
}
399-
}
400-
401-
impl<'renderer, 'frame> AsGlowFrame<'frame> for GlMultiFrame<'renderer, 'frame> {
402-
fn glow_frame(&self) -> &GlowFrame<'frame> {
403-
self.as_ref()
350+
fn glow_frame<'b, 'frame>(frame: &'b Self::Frame<'frame>) -> &'b GlowFrame<'frame> {
351+
frame.as_ref()
404352
}
405-
fn glow_frame_mut(&mut self) -> &mut GlowFrame<'frame> {
406-
self.as_mut()
353+
fn glow_frame_mut<'b, 'frame>(frame: &'b mut Self::Frame<'frame>) -> &'b mut GlowFrame<'frame> {
354+
frame.as_mut()
407355
}
408356
}
409357

src/shell/element/mod.rs

Lines changed: 19 additions & 89 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use crate::{
22
backend::render::{
3-
element::{AsGlowFrame, AsGlowRenderer},
4-
GlMultiError, GlMultiFrame, GlMultiRenderer, SplitRenderElements,
3+
element::{AsGlowRenderer, FromGlesError},
4+
SplitRenderElements,
55
},
66
state::State,
77
utils::{iced::IcedElementInternal, prelude::*},
@@ -1270,90 +1270,20 @@ where
12701270
}
12711271
}
12721272

1273-
impl RenderElement<GlowRenderer> for CosmicMappedRenderElement<GlowRenderer> {
1274-
fn draw<'frame>(
1275-
&self,
1276-
frame: &mut <GlowRenderer as Renderer>::Frame<'frame>,
1277-
src: Rectangle<f64, BufferCoords>,
1278-
dst: Rectangle<i32, Physical>,
1279-
damage: &[Rectangle<i32, Physical>],
1280-
opaque_regions: &[Rectangle<i32, Physical>],
1281-
) -> Result<(), <GlowRenderer as Renderer>::Error> {
1282-
match self {
1283-
CosmicMappedRenderElement::Stack(elem) => {
1284-
elem.draw(frame, src, dst, damage, opaque_regions)
1285-
}
1286-
CosmicMappedRenderElement::Window(elem) => {
1287-
elem.draw(frame, src, dst, damage, opaque_regions)
1288-
}
1289-
CosmicMappedRenderElement::TiledStack(elem) => {
1290-
elem.draw(frame, src, dst, damage, opaque_regions)
1291-
}
1292-
CosmicMappedRenderElement::TiledWindow(elem) => {
1293-
elem.draw(frame, src, dst, damage, opaque_regions)
1294-
}
1295-
CosmicMappedRenderElement::TiledOverlay(elem) => {
1296-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
1297-
}
1298-
CosmicMappedRenderElement::MovingStack(elem) => {
1299-
elem.draw(frame, src, dst, damage, opaque_regions)
1300-
}
1301-
CosmicMappedRenderElement::MovingWindow(elem) => {
1302-
elem.draw(frame, src, dst, damage, opaque_regions)
1303-
}
1304-
CosmicMappedRenderElement::GrabbedStack(elem) => {
1305-
elem.draw(frame, src, dst, damage, opaque_regions)
1306-
}
1307-
CosmicMappedRenderElement::GrabbedWindow(elem) => {
1308-
elem.draw(frame, src, dst, damage, opaque_regions)
1309-
}
1310-
CosmicMappedRenderElement::FocusIndicator(elem) => {
1311-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
1312-
}
1313-
CosmicMappedRenderElement::Overlay(elem) => {
1314-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
1315-
}
1316-
CosmicMappedRenderElement::StackHoverIndicator(elem) => {
1317-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
1318-
}
1319-
#[cfg(feature = "debug")]
1320-
CosmicMappedRenderElement::Egui(elem) => {
1321-
RenderElement::<GlowRenderer>::draw(elem, frame, src, dst, damage, opaque_regions)
1322-
}
1323-
}
1324-
}
1325-
1326-
fn underlying_storage(&self, renderer: &mut GlowRenderer) -> Option<UnderlyingStorage> {
1327-
match self {
1328-
CosmicMappedRenderElement::Stack(elem) => elem.underlying_storage(renderer),
1329-
CosmicMappedRenderElement::Window(elem) => elem.underlying_storage(renderer),
1330-
CosmicMappedRenderElement::TiledStack(elem) => elem.underlying_storage(renderer),
1331-
CosmicMappedRenderElement::TiledWindow(elem) => elem.underlying_storage(renderer),
1332-
CosmicMappedRenderElement::TiledOverlay(elem) => elem.underlying_storage(renderer),
1333-
CosmicMappedRenderElement::MovingStack(elem) => elem.underlying_storage(renderer),
1334-
CosmicMappedRenderElement::MovingWindow(elem) => elem.underlying_storage(renderer),
1335-
CosmicMappedRenderElement::GrabbedStack(elem) => elem.underlying_storage(renderer),
1336-
CosmicMappedRenderElement::GrabbedWindow(elem) => elem.underlying_storage(renderer),
1337-
CosmicMappedRenderElement::FocusIndicator(elem) => elem.underlying_storage(renderer),
1338-
CosmicMappedRenderElement::Overlay(elem) => elem.underlying_storage(renderer),
1339-
CosmicMappedRenderElement::StackHoverIndicator(elem) => {
1340-
elem.underlying_storage(renderer)
1341-
}
1342-
#[cfg(feature = "debug")]
1343-
CosmicMappedRenderElement::Egui(elem) => elem.underlying_storage(renderer),
1344-
}
1345-
}
1346-
}
1347-
1348-
impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicMappedRenderElement<GlMultiRenderer<'a>> {
1273+
impl<R> RenderElement<R> for CosmicMappedRenderElement<R>
1274+
where
1275+
R: Renderer + ImportAll + ImportMem + AsGlowRenderer,
1276+
<R as Renderer>::TextureId: 'static,
1277+
<R as Renderer>::Error: FromGlesError,
1278+
{
13491279
fn draw<'frame>(
13501280
&self,
1351-
frame: &mut GlMultiFrame<'a, 'frame>,
1281+
frame: &mut R::Frame<'frame>,
13521282
src: Rectangle<f64, BufferCoords>,
13531283
dst: Rectangle<i32, Physical>,
13541284
damage: &[Rectangle<i32, Physical>],
13551285
opaque_regions: &[Rectangle<i32, Physical>],
1356-
) -> Result<(), GlMultiError> {
1286+
) -> Result<(), R::Error> {
13571287
match self {
13581288
CosmicMappedRenderElement::Stack(elem) => {
13591289
elem.draw(frame, src, dst, damage, opaque_regions)
@@ -1369,13 +1299,13 @@ impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicMappedRenderElement<GlMult
13691299
}
13701300
CosmicMappedRenderElement::TiledOverlay(elem) => RenderElement::<GlowRenderer>::draw(
13711301
elem,
1372-
frame.glow_frame_mut(),
1302+
R::glow_frame_mut(frame),
13731303
src,
13741304
dst,
13751305
damage,
13761306
opaque_regions,
13771307
)
1378-
.map_err(|err| GlMultiError::Render(err)),
1308+
.map_err(FromGlesError::from_gles_error),
13791309
CosmicMappedRenderElement::MovingStack(elem) => {
13801310
elem.draw(frame, src, dst, damage, opaque_regions)
13811311
}
@@ -1390,28 +1320,28 @@ impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicMappedRenderElement<GlMult
13901320
}
13911321
CosmicMappedRenderElement::FocusIndicator(elem) => RenderElement::<GlowRenderer>::draw(
13921322
elem,
1393-
frame.glow_frame_mut(),
1323+
R::glow_frame_mut(frame),
13941324
src,
13951325
dst,
13961326
damage,
13971327
opaque_regions,
13981328
)
1399-
.map_err(|err| GlMultiError::Render(err)),
1329+
.map_err(FromGlesError::from_gles_error),
14001330
CosmicMappedRenderElement::Overlay(elem) => RenderElement::<GlowRenderer>::draw(
14011331
elem,
1402-
frame.glow_frame_mut(),
1332+
R::glow_frame_mut(frame),
14031333
src,
14041334
dst,
14051335
damage,
14061336
opaque_regions,
14071337
)
1408-
.map_err(|err| GlMultiError::Render(err)),
1338+
.map_err(FromGlesError::from_gles_error),
14091339
CosmicMappedRenderElement::StackHoverIndicator(elem) => {
14101340
elem.draw(frame, src, dst, damage, opaque_regions)
14111341
}
14121342
#[cfg(feature = "debug")]
14131343
CosmicMappedRenderElement::Egui(elem) => {
1414-
let glow_frame = frame.glow_frame_mut();
1344+
let glow_frame = R::glow_frame_mut(frame);
14151345
RenderElement::<GlowRenderer>::draw(
14161346
elem,
14171347
glow_frame,
@@ -1420,12 +1350,12 @@ impl<'a> RenderElement<GlMultiRenderer<'a>> for CosmicMappedRenderElement<GlMult
14201350
damage,
14211351
opaque_regions,
14221352
)
1423-
.map_err(|err| GlMultiError::Render(err))
1353+
.map_err(FromGlesError::from_gles_error)
14241354
}
14251355
}
14261356
}
14271357

1428-
fn underlying_storage(&self, renderer: &mut GlMultiRenderer<'a>) -> Option<UnderlyingStorage> {
1358+
fn underlying_storage(&self, renderer: &mut R) -> Option<UnderlyingStorage> {
14291359
match self {
14301360
CosmicMappedRenderElement::Stack(elem) => elem.underlying_storage(renderer),
14311361
CosmicMappedRenderElement::Window(elem) => elem.underlying_storage(renderer),

0 commit comments

Comments
 (0)