Skip to content

Commit f08f445

Browse files
authored
Merge pull request #37 from lambda-sh/vmarcella/rendering-improvements
Rendering improvements
2 parents b5fa56e + 0ac1aaf commit f08f445

13 files changed

Lines changed: 196 additions & 159 deletions

File tree

README.md

Lines changed: 24 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -24,27 +24,28 @@ Lambda :
2424
* Desktop applications
2525
* Productivity tools
2626
* Data visualizations
27-
* Physical simulations
27+
* Physical system simulations
2828
* Games
2929

30-
While lambda is still in beta, we're making sure to create a solid
31-
foundation other projects to build upon. Over the last couple of years, the
32-
prominence of the web has replaced traditional desktop applications. While
33-
this has lead to a golden age for developing UI/UX for applications across all
34-
platforms, it has come at the cost of degraded performance & resource consumption.
30+
Over the last couple of years, the prominence of the web has replaced
31+
traditional desktop applications. While this has lead to a golden age for
32+
developing UI/UX for applications across all platforms, it has come at the
33+
cost of degraded performance & resource consumption.
3534

36-
Lambda's goal isn't to replace electron, webview, or other similar web based desktop
37-
frameworks, however; it is to instead create a cross platform ecosystem for
38-
desktop applications with performance and resource consumption at the forefront
39-
of it's priorities without sacrificing. Lambda will not be HTML/CSS based and will instead provide
35+
Lambda's goal isn't to replace electron, webview, or other similar web based
36+
desktop frameworks, however; it is to instead create a cross platform ecosystem
37+
for desktop applications with performance and resource consumption at the
38+
forefront of it's priorities without sacrificing good UI/UX. Lambda may offer
39+
lightweight HTML/CSS based rendering in the future but we're primarily focused
40+
on implementing a Rust native UI framework built on top of our rendering engine.
4041

4142
## Documentation <a name="documentation"></a>
4243
Documentation to be added soon.
4344

4445
## Building <a name="building"></a>
4546

4647
### From source <a name="source"></a>
47-
Currently, building from source is the only method to obtain a copy of Lambda.
48+
Currently, building from source is the only method to obtain a copy of Lambda.
4849

4950
#### Required external dependencies <a name="ext_deps"></a>
5051
* All platforms
@@ -56,12 +57,14 @@ Currently, building from source is the only method to obtain a copy of Lambda.
5657
* `pre-commit` is used for development git commit hooks and any changes that do not pass the pre-commit checks will not be accepted.
5758

5859
#### Rendering API support
59-
These are the Rendering APIs that are supported on each platform and must be installed manually. More information on how to choose which backend lambda uses on each platform is provided further below.
60+
These are the Rendering APIs that are supported on each platform and must be
61+
installed manually. More information on how to choose which backend lambda
62+
uses on each platform is provided further below.
6063
* Windows
6164
* `OpenGL`
6265
* `Vulkan`
6366
* `DirectX11`
64-
* `DirectX12`
67+
* `DirectX12`
6568
* Linux
6669
* `OpenGL`
6770
* `Vulkan`
@@ -74,7 +77,7 @@ If planning to develop for lambda, you must run the setup script provided by rep
7477
```bash
7578
./scripts/setup.sh
7679
```
77-
This will initialize pre commit checks for development use and setup git-lfs for asset management.
80+
This will initialize pre commit checks for development use and setup git-lfs for asset management.
7881

7982
In order to validate that lambda successfully compiles, you can build the library by performing a build with cargo.
8083
```bash
@@ -87,9 +90,9 @@ Coming soon.
8790

8891

8992
## Plans <a name="plans"></a>
90-
- [ ] Architecture support
93+
- [x] Architecture support
9194
- [x] x86
92-
- [ ] arm64
95+
- [x] arm64
9396
- [ ] Operating system support
9497
- [x] MacOS
9598
- [x] Linux
@@ -105,12 +108,12 @@ Coming soon.
105108
- [x] DirectX12
106109
- [ ] Crates
107110
- [ ] lambda-arch -- Architecture support
108-
- [ ] (WIP) lambda-platform -- Platform support
111+
- [x] (WIP) lambda-platform -- Platform support
109112
- [ ] (WIP) lambda-core -- Core library implementations
110113
- [ ] lambda-cloud -- Cloud integrations
111-
- [ ] (WIP) lambda -- Stable Lambda API
114+
- [ ] (WIP) lambda -- The public Lambda API
112115
- [ ] Tools
113-
- [ ] lambda-rs-demo -- 2D rendering demo
116+
- [x] lambda-rs-demo -- 2D rendering demo
114117
- [ ] lambda-rs-cube -- 3D rendering demo
115118
- [ ] lambda-checker -- Checks system specifications against lambda requirements
116119
- [ ] CI/CD
@@ -128,7 +131,7 @@ This process may take anywhere from 3-7 days depending on the scope of the
128131
changes made, my schedule, and any other variable factors. They must also pass
129132
all of the build pipelines are configured to run at merge.
130133

131-
## Resources I used for creating this project. <a name="resources"></a>
134+
## Resources <a name="resources"></a>
132135
[The Cherno's playlist for making a game engine](https://www.youtube.com/playlist?list=PLlrATfBNZ98dC-V-N3m0Go4deliWHPFwT)
133136

134-
[Creator of the repository logo.](https://github.com/RinniSwift)
137+
[Creator of Logo](https://github.com/RinniSwift)

crates/lambda-platform/src/winit/mod.rs

Lines changed: 17 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -35,19 +35,19 @@ pub mod winit_exports {
3535
}
3636

3737
/// Loop wrapping for the winit event loop.
38-
pub struct Loop<E: 'static> {
38+
pub struct Loop<E: 'static + std::fmt::Debug> {
3939
event_loop: EventLoop<E>,
4040
}
4141

42-
pub fn create_event_loop<Events: 'static>() -> Loop<Events> {
42+
pub fn create_event_loop<Events: 'static + std::fmt::Debug>() -> Loop<Events> {
4343
let event_loop = EventLoop::<Events>::with_user_event();
4444
return Loop { event_loop };
4545
}
4646

4747
/// Structure that contains properties needed for building a window.
4848
pub struct WindowProperties {
4949
pub name: String,
50-
pub dimensions: [u32; 2],
50+
pub dimensions: (u32, u32),
5151
pub monitor_handle: MonitorHandle,
5252
}
5353

@@ -70,25 +70,27 @@ pub struct WindowHandle {
7070
/// the monitor being rendered to.
7171
#[inline]
7272
fn construct_window_size(
73-
window_size: [u32; 2],
73+
window_size: (u32, u32),
7474
scale_factor: f64,
7575
) -> WindowSize {
7676
let logical: LogicalSize<u32> = window_size.into();
7777
let physical: PhysicalSize<u32> = logical.to_physical(scale_factor);
7878

79+
let (width, height) = window_size;
7980
return WindowSize {
80-
width: window_size[0],
81-
height: window_size[1],
81+
width,
82+
height,
8283
logical,
8384
physical,
8485
};
8586
}
8687

87-
pub struct EventLoopPublisher<E: 'static> {
88+
#[derive(Clone, Debug)]
89+
pub struct EventLoopPublisher<E: 'static + std::fmt::Debug> {
8890
winit_proxy: EventLoopProxy<E>,
8991
}
9092

91-
impl<E: 'static> EventLoopPublisher<E> {
93+
impl<E: 'static + std::fmt::Debug> EventLoopPublisher<E> {
9294
/// Instantiate a new EventLoopPublisher from an event loop proxy.
9395
#[inline]
9496
pub fn new(winit_proxy: EventLoopProxy<E>) -> Self {
@@ -97,12 +99,15 @@ impl<E: 'static> EventLoopPublisher<E> {
9799

98100
/// Send an event
99101
#[inline]
100-
pub fn send_event(&self, event: E) {
101-
self.winit_proxy.send_event(event);
102+
pub fn publish_event(&self, event: E) {
103+
self
104+
.winit_proxy
105+
.send_event(event)
106+
.expect("Failed to send event");
102107
}
103108
}
104109

105-
impl<E: 'static> Loop<E> {
110+
impl<E: 'static + std::fmt::Debug> Loop<E> {
106111
pub fn create_publisher(&mut self) -> EventLoopPublisher<E> {
107112
let proxy = self.event_loop.create_proxy();
108113
return EventLoopPublisher::new(proxy);
@@ -119,6 +124,7 @@ impl<E: 'static> Loop<E> {
119124
}
120125

121126
pub fn get_any_available_monitors(&self) -> MonitorHandle {
127+
// TODO(vmarcella): Remove the panic from this in favor of returning a result or an error.
122128
match self.event_loop.available_monitors().next() {
123129
Some(monitor) => monitor,
124130
None => panic!("No available monitors found."),

lambda/src/core/events.rs

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,31 @@
11
use std::time::Instant;
22

3+
/// events generated by kernel interactions with the component.
4+
#[derive(Debug)]
35
pub enum ComponentEvent {
46
Attached { name: String },
57
Detached { name: String },
8+
Update { delta: Instant },
69
}
710

11+
/// Window events are generated in response to window events coming from
12+
/// the windowing system.
13+
#[derive(Debug)]
814
pub enum WindowEvent {
915
Close,
1016
Resize { width: u32, height: u32 },
1117
}
1218

13-
pub enum KernelEvent {
19+
/// Kernel events are generated by the kernel itself
20+
#[derive(Debug)]
21+
pub enum RuntimeEvent {
1422
Initialized,
1523
Shutdown,
1624
}
1725

18-
/// Generic Event Enum which encapsulates all possible events that will be emitted
19-
/// by the LambdaKernel
26+
/// Generic Event Enum which encapsulates all possible events that will be
27+
/// emitted by the LambdaKernel
28+
#[derive(Debug)]
2029
pub enum Events {
2130
Component {
2231
event: ComponentEvent,
@@ -26,8 +35,8 @@ pub enum Events {
2635
event: WindowEvent,
2736
issued_at: Instant,
2837
},
29-
Kernel {
30-
event: KernelEvent,
38+
Runtime {
39+
event: RuntimeEvent,
3140
issued_at: Instant,
3241
},
3342
}

lambda/src/core/kernel.rs

Lines changed: 0 additions & 19 deletions
This file was deleted.

lambda/src/core/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
pub mod component;
22
pub mod events;
3-
pub mod kernel;
43
pub mod render;
4+
pub mod runtime;
55
pub mod window;

lambda/src/core/render/command.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ use super::{
1010
PlatformRenderCommand,
1111
RenderContext,
1212
};
13+
1314
/// Commands that are used to render a frame within the RenderContext.
1415
pub enum RenderCommand {
1516
/// sets the viewports for the render context.

lambda/src/core/render/mod.rs

Lines changed: 37 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -126,11 +126,11 @@ impl RenderContextBuilder {
126126
internal::SurfaceBuilder::new().build(&instance, window.window_handle()),
127127
);
128128

129-
// Build a GPU with a 3D Render queue that can render to our surface.
129+
// Build a GPU with a Graphical Render queue that can render to our surface.
130130
let mut gpu = internal::GpuBuilder::new()
131131
.with_render_queue_type(internal::RenderQueueType::Graphical)
132132
.build(&mut instance, Some(&surface))
133-
.expect("Failed to build a GPU.");
133+
.expect("Failed to build a GPU with a graphical render queue.");
134134

135135
// Build command pool and allocate a single buffer named Primary
136136
let command_pool = internal::CommandPoolBuilder::new().build(&gpu);
@@ -145,9 +145,9 @@ impl RenderContextBuilder {
145145

146146
// Create the image extent and initial frame buffer attachment description
147147
// for rendering.
148-
let dimensions = window.dimensions();
148+
let (width, height) = window.dimensions();
149149
let swapchain = SwapchainBuilder::new()
150-
.with_size(dimensions[0], dimensions[1])
150+
.with_size(width, height)
151151
.build(&gpu, &surface);
152152

153153
Rc::get_mut(&mut surface)
@@ -194,27 +194,49 @@ impl RenderContext {
194194
println!("{} will now start destroying resources.", self.name);
195195

196196
// Destroy the submission fence and rendering semaphore.
197-
self.submission_fence.take().unwrap().destroy(&self.gpu);
198-
self.render_semaphore.take().unwrap().destroy(&self.gpu);
197+
self
198+
.submission_fence
199+
.take()
200+
.expect(
201+
"Couldn't take the submission fence from the context and destroy it.",
202+
)
203+
.destroy(&self.gpu);
204+
self
205+
.render_semaphore
206+
.take()
207+
.expect("Couldn't take the rendering semaphore from the context and destroy it.")
208+
.destroy(&self.gpu);
199209

200210
// Destroy render passes.
201211
let mut render_passes = vec![];
202212
swap(&mut self.render_passes, &mut render_passes);
203213

204214
for render_pass in &mut render_passes {
205-
render_pass.take().unwrap().destroy(&self);
215+
render_pass
216+
.take()
217+
.expect(
218+
"Couldn't take the render pass from the context and destroy it.",
219+
)
220+
.destroy(&self);
206221
}
207222

208223
// Destroy render pipelines.
209224
let mut render_pipelines = vec![];
210225
swap(&mut self.render_pipelines, &mut render_pipelines);
211226

212227
for render_pipeline in &mut render_pipelines {
213-
render_pipeline.take().unwrap().destroy(&self);
228+
render_pipeline
229+
.take()
230+
.expect(
231+
"Couldn't take the render pipeline from the context and destroy it.",
232+
)
233+
.destroy(&self);
214234
}
215235

216236
// Takes the inner surface and destroys it.
217-
let mut surface = Rc::try_unwrap(self.surface).ok().unwrap();
237+
let mut surface = Rc::try_unwrap(self.surface)
238+
.expect("Couldn't obtain the surface from the context.");
239+
218240
surface.remove_swapchain(&self.gpu);
219241
surface.destroy(&self.instance);
220242
}
@@ -273,13 +295,17 @@ impl RenderContext {
273295
self.gpu.submit_command_buffer(
274296
&mut command_buffer,
275297
vec![],
276-
self.submission_fence.as_mut().unwrap(),
298+
self
299+
.submission_fence
300+
.as_mut()
301+
.expect("Failed to get mutable reference to submission fence."),
277302
);
278303

279304
self
280305
.gpu
281306
.render_to_surface(
282-
Rc::get_mut(&mut self.surface).expect(""),
307+
Rc::get_mut(&mut self.surface)
308+
.expect("Failed to obtain a surface to render on."),
283309
self.render_semaphore.as_mut().unwrap(),
284310
)
285311
.expect("Failed to render to the surface");

0 commit comments

Comments
 (0)