mirror of
https://github.com/slint-ui/slint.git
synced 2025-10-01 06:11:16 +00:00
Free graphics resources without item tree traversal
This commit is contained in:
parent
ba0ec058ab
commit
7a5113ece1
7 changed files with 54 additions and 40 deletions
|
@ -96,11 +96,9 @@ public:
|
||||||
sixtyfps_component_window_set_scale_factor(&inner, value);
|
sixtyfps_component_window_set_scale_factor(&inner, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename Component>
|
void free_graphics_resources(const sixtyfps::Slice<ItemRef> &items) const
|
||||||
void free_graphics_resources(Component *c) const
|
|
||||||
{
|
{
|
||||||
cbindgen_private::sixtyfps_component_window_free_graphics_resources(
|
cbindgen_private::sixtyfps_component_window_free_graphics_resources(&inner, &items);
|
||||||
&inner, vtable::VRef<ComponentVTable> { &Component::component_type, c });
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void set_focus_item(vtable::VRef<ComponentVTable> c, vtable::VRef<ItemVTable> item)
|
void set_focus_item(vtable::VRef<ComponentVTable> c, vtable::VRef<ItemVTable> item)
|
||||||
|
|
|
@ -894,6 +894,7 @@ fn generate_component(
|
||||||
let mut repeated_input_branch = vec![];
|
let mut repeated_input_branch = vec![];
|
||||||
let mut repeater_layout_code = vec![];
|
let mut repeater_layout_code = vec![];
|
||||||
let mut tree_array = vec![];
|
let mut tree_array = vec![];
|
||||||
|
let mut item_names_and_vt_symbols = vec![];
|
||||||
let mut repeater_count = 0;
|
let mut repeater_count = 0;
|
||||||
super::build_array_helper(component, |item_rc, children_offset, is_flickable_rect| {
|
super::build_array_helper(component, |item_rc, children_offset, is_flickable_rect| {
|
||||||
let item = item_rc.borrow();
|
let item = item_rc.borrow();
|
||||||
|
@ -944,6 +945,8 @@ fn generate_component(
|
||||||
children_offset,
|
children_offset,
|
||||||
));
|
));
|
||||||
handle_item(item_rc, &mut component_struct, &mut init);
|
handle_item(item_rc, &mut component_struct, &mut init);
|
||||||
|
item_names_and_vt_symbols
|
||||||
|
.push((item.id.clone(), item.base_type.as_native().vtable_symbol.clone()));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -979,7 +982,15 @@ fn generate_component(
|
||||||
if component.parent_element.upgrade().is_some() {
|
if component.parent_element.upgrade().is_some() {
|
||||||
destructor.push("if (!parent) return;".to_owned())
|
destructor.push("if (!parent) return;".to_owned())
|
||||||
}
|
}
|
||||||
destructor.push("self->window.free_graphics_resources(this);".into());
|
if !item_names_and_vt_symbols.is_empty() {
|
||||||
|
destructor.push("sixtyfps::private_api::ItemRef items[] = {".into());
|
||||||
|
destructor.push(item_names_and_vt_symbols.iter()
|
||||||
|
.map(|(item_name, vt_symbol)|
|
||||||
|
format!("{{ &sixtyfps::private_api::{vt}, const_cast<decltype(this->{id})*>(&this->{id}) }}", id = item_name, vt = vt_symbol)
|
||||||
|
).join(","));
|
||||||
|
destructor.push("};".into());
|
||||||
|
destructor.push("window.free_graphics_resources(sixtyfps::Slice<sixtyfps::private_api::ItemRef>{items, std::size(items)});".into());
|
||||||
|
}
|
||||||
|
|
||||||
component_struct.members.push((
|
component_struct.members.push((
|
||||||
Access::Public,
|
Access::Public,
|
||||||
|
|
|
@ -611,7 +611,10 @@ fn generate_component(
|
||||||
Some(quote!(impl sixtyfps::re_exports::PinnedDrop for #component_id {
|
Some(quote!(impl sixtyfps::re_exports::PinnedDrop for #component_id {
|
||||||
fn drop(self: core::pin::Pin<&mut #component_id>) {
|
fn drop(self: core::pin::Pin<&mut #component_id>) {
|
||||||
use sixtyfps::re_exports::*;
|
use sixtyfps::re_exports::*;
|
||||||
self.window.free_graphics_resources(VRef::new_pin(self.as_ref()));
|
let items = [
|
||||||
|
#(VRef::new_pin(Self::FIELD_OFFSETS.#item_names.apply_pin(self.as_ref())),)*
|
||||||
|
];
|
||||||
|
self.window.free_graphics_resources(&Slice::from_slice(&items));
|
||||||
}
|
}
|
||||||
})),
|
})),
|
||||||
quote!(#[pin_drop]),
|
quote!(#[pin_drop]),
|
||||||
|
|
|
@ -13,7 +13,11 @@ LICENSE END */
|
||||||
[GenericWindow] trait used by the generated code and the run-time to change
|
[GenericWindow] trait used by the generated code and the run-time to change
|
||||||
aspects of windows on the screen.
|
aspects of windows on the screen.
|
||||||
*/
|
*/
|
||||||
use crate::component::{ComponentRc, ComponentVTable};
|
use crate::{
|
||||||
|
component::{ComponentRc, ComponentVTable},
|
||||||
|
items::ItemRef,
|
||||||
|
slice::Slice,
|
||||||
|
};
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
use std::{
|
use std::{
|
||||||
convert::TryInto,
|
convert::TryInto,
|
||||||
|
@ -91,10 +95,7 @@ pub trait GenericWindow {
|
||||||
|
|
||||||
/// This function is called by the generated code when a component and therefore its tree of items are destroyed. The
|
/// This function is called by the generated code when a component and therefore its tree of items are destroyed. The
|
||||||
/// implementation typically uses this to free the underlying graphics resources cached via [`crate::graphics::RenderingCache`].
|
/// implementation typically uses this to free the underlying graphics resources cached via [`crate::graphics::RenderingCache`].
|
||||||
fn free_graphics_resources(
|
fn free_graphics_resources<'a>(self: Rc<Self>, items: &Slice<'a, Pin<ItemRef<'a>>>);
|
||||||
self: Rc<Self>,
|
|
||||||
component: core::pin::Pin<crate::component::ComponentRef>,
|
|
||||||
);
|
|
||||||
/// Installs a binding on the specified property that's toggled whenever the text cursor is supposed to be visible or not.
|
/// Installs a binding on the specified property that's toggled whenever the text cursor is supposed to be visible or not.
|
||||||
fn set_cursor_blink_binding(&self, prop: &crate::properties::Property<bool>);
|
fn set_cursor_blink_binding(&self, prop: &crate::properties::Property<bool>);
|
||||||
|
|
||||||
|
@ -151,11 +152,8 @@ impl ComponentWindow {
|
||||||
|
|
||||||
/// This function is called by the generated code when a component and therefore its tree of items are destroyed. The
|
/// This function is called by the generated code when a component and therefore its tree of items are destroyed. The
|
||||||
/// implementation typically uses this to free the underlying graphics resources cached via [RenderingCache][`crate::graphics::RenderingCache`].
|
/// implementation typically uses this to free the underlying graphics resources cached via [RenderingCache][`crate::graphics::RenderingCache`].
|
||||||
pub fn free_graphics_resources(
|
pub fn free_graphics_resources<'a>(&self, items: &Slice<'a, Pin<ItemRef<'a>>>) {
|
||||||
&self,
|
self.0.clone().free_graphics_resources(items);
|
||||||
component: core::pin::Pin<crate::component::ComponentRef>,
|
|
||||||
) {
|
|
||||||
self.0.clone().free_graphics_resources(component);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Installs a binding on the specified property that's toggled whenever the text cursor is supposed to be visible or not.
|
/// Installs a binding on the specified property that's toggled whenever the text cursor is supposed to be visible or not.
|
||||||
|
@ -599,12 +597,12 @@ pub mod ffi {
|
||||||
|
|
||||||
/// Sets the window scale factor, merely for testing purposes.
|
/// Sets the window scale factor, merely for testing purposes.
|
||||||
#[no_mangle]
|
#[no_mangle]
|
||||||
pub unsafe extern "C" fn sixtyfps_component_window_free_graphics_resources(
|
pub unsafe extern "C" fn sixtyfps_component_window_free_graphics_resources<'a>(
|
||||||
handle: *const ComponentWindowOpaque,
|
handle: *const ComponentWindowOpaque,
|
||||||
component: Pin<VRef<ComponentVTable>>,
|
items: &Slice<'a, Pin<ItemRef<'a>>>,
|
||||||
) {
|
) {
|
||||||
let window = &*(handle as *const ComponentWindow);
|
let window = &*(handle as *const ComponentWindow);
|
||||||
window.free_graphics_resources(component)
|
window.free_graphics_resources(items)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the focus item.
|
/// Sets the focus item.
|
||||||
|
|
|
@ -20,7 +20,6 @@ LICENSE END */
|
||||||
created by the backend in a type-erased manner.
|
created by the backend in a type-erased manner.
|
||||||
*/
|
*/
|
||||||
extern crate alloc;
|
extern crate alloc;
|
||||||
use crate::component::{ComponentRc, ComponentWeak};
|
|
||||||
use crate::input::{KeyEvent, KeyboardModifiers, MouseEvent, MouseEventType};
|
use crate::input::{KeyEvent, KeyboardModifiers, MouseEvent, MouseEventType};
|
||||||
use crate::items::ItemRef;
|
use crate::items::ItemRef;
|
||||||
use crate::properties::{InterpolatedPropertyValue, Property, PropertyTracker};
|
use crate::properties::{InterpolatedPropertyValue, Property, PropertyTracker};
|
||||||
|
@ -29,6 +28,10 @@ use crate::rtti::{BuiltinItem, FieldInfo, PropertyInfo, ValueType};
|
||||||
use crate::SharedArray;
|
use crate::SharedArray;
|
||||||
#[cfg(feature = "rtti")]
|
#[cfg(feature = "rtti")]
|
||||||
use crate::Signal;
|
use crate::Signal;
|
||||||
|
use crate::{
|
||||||
|
component::{ComponentRc, ComponentWeak},
|
||||||
|
slice::Slice,
|
||||||
|
};
|
||||||
|
|
||||||
use auto_enums::auto_enum;
|
use auto_enums::auto_enum;
|
||||||
use cgmath::Matrix4;
|
use cgmath::Matrix4;
|
||||||
|
@ -820,14 +823,11 @@ impl<Backend: GraphicsBackend> crate::eventloop::GenericWindow for GraphicsWindo
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn free_graphics_resources(
|
fn free_graphics_resources<'a>(self: Rc<Self>, items: &Slice<'a, Pin<ItemRef<'a>>>) {
|
||||||
self: Rc<Self>,
|
|
||||||
component: core::pin::Pin<crate::component::ComponentRef>,
|
|
||||||
) {
|
|
||||||
match &*self.map_state.borrow() {
|
match &*self.map_state.borrow() {
|
||||||
GraphicsWindowBackendState::Unmapped => {}
|
GraphicsWindowBackendState::Unmapped => {}
|
||||||
GraphicsWindowBackendState::Mapped(window) => {
|
GraphicsWindowBackendState::Mapped(window) => {
|
||||||
crate::item_rendering::free_item_rendering_data(component, &window.rendering_cache)
|
crate::item_rendering::free_item_rendering_data(items, &window.rendering_cache)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,8 +14,8 @@ use super::graphics::{
|
||||||
Frame, GraphicsBackend, GraphicsWindow, RenderingCache, RenderingPrimitivesBuilder,
|
Frame, GraphicsBackend, GraphicsWindow, RenderingCache, RenderingPrimitivesBuilder,
|
||||||
};
|
};
|
||||||
use super::items::ItemRef;
|
use super::items::ItemRef;
|
||||||
use crate::eventloop::ComponentWindow;
|
|
||||||
use crate::item_tree::ItemVisitorResult;
|
use crate::item_tree::ItemVisitorResult;
|
||||||
|
use crate::{eventloop::ComponentWindow, slice::Slice};
|
||||||
use cgmath::{Matrix4, SquareMatrix, Vector3};
|
use cgmath::{Matrix4, SquareMatrix, Vector3};
|
||||||
use std::cell::{Cell, RefCell};
|
use std::cell::{Cell, RefCell};
|
||||||
|
|
||||||
|
@ -123,18 +123,12 @@ pub(crate) fn render_component_items<Backend: GraphicsBackend>(
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn free_item_rendering_data<Backend: GraphicsBackend>(
|
pub(crate) fn free_item_rendering_data<'a, Backend: GraphicsBackend>(
|
||||||
component: crate::component::ComponentRefPin,
|
items: &Slice<'a, core::pin::Pin<ItemRef<'a>>>,
|
||||||
rendering_cache: &RefCell<RenderingCache<Backend>>,
|
rendering_cache: &RefCell<RenderingCache<Backend>>,
|
||||||
) {
|
) {
|
||||||
crate::item_tree::visit_items(
|
for item in items.iter() {
|
||||||
component,
|
|
||||||
crate::item_tree::TraversalOrder::FrontToBack,
|
|
||||||
|_, item, _| {
|
|
||||||
let cached_rendering_data = item.cached_rendering_data_offset();
|
let cached_rendering_data = item.cached_rendering_data_offset();
|
||||||
cached_rendering_data.release(rendering_cache);
|
cached_rendering_data.release(rendering_cache);
|
||||||
ItemVisitorResult::Continue(())
|
}
|
||||||
},
|
|
||||||
(),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -77,9 +77,19 @@ impl<'id> ComponentBox<'id> {
|
||||||
|
|
||||||
impl<'id> Drop for ComponentBox<'id> {
|
impl<'id> Drop for ComponentBox<'id> {
|
||||||
fn drop(&mut self) {
|
fn drop(&mut self) {
|
||||||
match eval::window_ref(self.borrow_instance()) {
|
let instance_ref = self.borrow_instance();
|
||||||
|
match eval::window_ref(instance_ref) {
|
||||||
Some(window) => {
|
Some(window) => {
|
||||||
window.free_graphics_resources(self.borrow());
|
let items = self
|
||||||
|
.component_type
|
||||||
|
.items
|
||||||
|
.values()
|
||||||
|
.map(|item_within_component| unsafe {
|
||||||
|
item_within_component.item_from_component(instance_ref.as_ptr())
|
||||||
|
})
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
window.free_graphics_resources(&Slice::from_slice(items.as_slice()));
|
||||||
}
|
}
|
||||||
None => {}
|
None => {}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue