Skip to content

Commit

Permalink
Update to new renderer (#10)
Browse files Browse the repository at this point in the history
* Rework to use new bevy rendering pipeline

Regressions:
* Does not work in 2d anymore
* The depth check option is now always on
* Removed user Lines (not sure what their purpose was tbh)

Improvements:
* Does work with the new renerer
* Uses wgsl

I wrote TODOs laying out improvement paths. There are a few performance
low-hanging fruits available.

The depth check is kind of a monster. I wanted to have something out
before trying it, because I'm strongly considering a uniform for this,
so that the depth test can be modified at run time and is probably going
to tank performance.

Uploading uniforms to GPU under the new renderer requires an awful lot
of additional code, due to the nature of wgpu, but it seems completely
possible, just check the `shader_material` example in the bevy
repository.

* Separate retained and immediate lines

The persisting lines now are treated and stored separately from the
temporary ones. This simplifies the logic for the temporary ones, and
since it's the general case, it should improve performance.

* Remove indices of immediate mod line meshes

With bevyengine/bevy#3415 it is now possible to upload meshes to GPU
without `indices` set. Before, it would panic. Removing `indices`
enables us to simply remove the `ImmLinesStorage::fill_indices` code,
since the ordering is exactly as the GPU would interpret the mesh
otherwise.

* follow bevy main HEAD

* Add back depth check configuration

It is configured through the plugin constructor now. It makes more sense
than through the `DebugLines` resource, since it's configured at the
beginning and won't change in the middle of running the plugin.

This was already true before, the difference is that it is now made
explicit to the user.

* Refactor LineStorage to use line over vertex index

At the cost of making the `RetLineStorage::fill_indices` and
`mark_expired` methods a bit more complex, it is possible to only store
the line index rather than two point indices of expired lines.

This should encapsulate neatly the complex underlying storage that
mirrors the mesh attribute buffers. Other side benefit is that
`timestamp` and `expired` vectors have their size divided by two.

I also added the `Line<T>` struct to make the arguments to mutating
methods of LineStorage more understandable.

* Remove references to thickness in examples

* Refactor and document

Various name changes and extra doc string. Also fixes a likely issue
with `mark_expired`, which would add duplicates to the `expired` stack.

* Add back 2d renderning

This however, requires adding a feature flag :/

* Update bevy dependency to 0.6

* Revert to exposing DebugLines as a bevy Resource

* Fix minor spelling errors

* Do not bump already-bumped version
  • Loading branch information
nicopap authored Jan 11, 2022
1 parent 811d4a6 commit bc49414
Show file tree
Hide file tree
Showing 15 changed files with 776 additions and 402 deletions.
23 changes: 10 additions & 13 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
authors = ["Michael Palmos <[email protected]>"]
categories = ["game-engines", "rendering", "game-development"]
description = "A prototype plugin providing a simple line drawing API for bevy."
edition = "2018"
edition = "2021"
homepage = "https://github.com/Toqozz/bevy_debug_lines"
keywords = ["debug", "line", "graphics", "bevy", "drawing"]
license = "MIT"
Expand All @@ -13,37 +13,34 @@ version = "0.4.0"
exclude = ["demo.gif", "demo_2.png", "demo_2.webm"]

[dependencies]
bevy = "0.5"

[patch.crates-io]
bevy = { git = "https://github.com/bevyengine/bevy", default-features = false, features = [
"render",
] }
bevy = { version = "0.6", default-features = false, features = [ "render" ] }

[features]
example_deps_2d = [
"bevy/bevy_winit",
"bevy/bevy_gltf",
"bevy/x11",
]
example_deps = [
"bevy/bevy_wgpu",
"bevy/bevy_winit",
"bevy/bevy_gltf",
"bevy/x11",
"3d",
]
3d = []

[[example]]
name = "3d"
required-features = ["example_deps"]

[[example]]
name = "2d"
required-features = ["example_deps"]
required-features = ["example_deps_2d"]

[[example]]
name = "bench"
required-features = ["example_deps"]

[[example]]
name = "user_lines"
required-features = ["example_deps"]

[[example]]
name = "depth_test"
required-features = ["example_deps"]
Expand Down
71 changes: 59 additions & 12 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,28 +17,36 @@ This plugin uses a shader and sends individual points to the GPU, which then mov
Add `bevy_prototype_debug_lines` to your `Cargo.toml`:
```toml
[dependencies]
bevy_prototype_debug_lines = "0.3.2"
bevy_prototype_debug_lines = "0.4.0"
```

Add the plugin in your `App::build()` phase:
If you are using bevy_debug_lines for 3d rendering, you must add the `3d`
feature like so:
```toml
[dependencies]
bevy_prototype_debug_lines = { version = "0.4.0", features = ["3d"] }
```


Add the plugin in your `App::new()` phase:
```rust
use bevy::prelude::*;
use bevy_prototype_debug_lines::*;

fn main() {
App::build()
App::new()
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
...
.add_plugin(DebugLinesPlugin::default())
// ...
.run();
}
```

Draw a line in whatever system you have using the `DebugLines` resource:
```rust
fn some_system(
...
mut lines: ResMut<DebugLines>
// ...
mut lines: ResMut<DebugLines>,
) {
let start = Vec3::splat(-1.0);
let end = Vec3::splat(1.0);
Expand All @@ -47,24 +55,46 @@ fn some_system(
}
```

Some options, such as depth testing, can be changed by inserting the `DebugLines` resource yourself:
Some options, such as depth testing, can be changed by using the
`DebugLinesPlugin::always_in_front()` method:

```rust
use bevy::prelude::*;
use bevy_prototype_debug_lines::*;

fn main() {
App::build()
App::new()
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
.insert_resource(DebugLines { depth_test: true, ..Default::default() })
...
.add_plugin(DebugLinesPlugin::always_in_front())
// ...
.run();
}
```

See [the examples](https://github.com/Toqozz/bevy_debug_lines/tree/master/examples) for more complete usage examples.

## Troubleshooting

### Lines do not show up

**Problem**: Lines do not show up on screen, even if I added the `DebugLinesPlugin` and
used `DebugLines::lines`

**Solution**: Check the dimension feature of `bevy_debug_lines`, when running your game,
there should be a log message looking like:
```
INFO bevy_prototype_debug_lines: Loaded 2d debug lines plugin.
```
Pay attention to **`Loaded 2d debug`** this should match what you are using in
your game. Is it a 3d game? If so, you should add the
`bevy_prototype_debug_lines/3d` feature flag to your `Cargo.toml`. It should
look like this:

```toml
bevy_prototype_debug_lines = { version = "0.4.0", features = ["3d"] }
```


## Running Examples
You can run the examples like so:
```shell
Expand All @@ -79,10 +109,27 @@ However, if you feel differently, let me know in [this](https://github.com/Toqoz

This is technically a non-breaking change (i.e. your code will still compile) because `duration` was added which takes the same spot, but beware that your code still needs to be updated (probably just set old `thickness` values to `0`, if you don't care about duration stuff.).

## Changes in `0.4.0`

* Complete rewrite
* Support bevy 0.6
* Use a wgsl shader, which should improve web compatibility
* The depth check is not supported through the `DebugLines.depth_check` field
anymore. You need to set it when initializing the plugin. By default depth
test is enabled but can be disabled with:
`.add_plugin(DebugLinesPlugin::always_in_front())`
* `DebugLinesPlugin` now has a constructor, you should replace `.add_plugin(DebugLinesPlugin)`
in your code by `.add_plugin(DebugLinesPlugin::default())`.
* Added the `3d` feature. Due to the changes in the way the plugin works, it is
now necessary to separate the 2d and 3d plugins. If you are using
`bevy_debug_lines` in a 3d game, please add the `features = ["3d"] ` line to
your `bevy_prototype_debug_lines` dependency.

## Bevy Version Support

| bevy | bevy_prototype_debug_lines |
| --- | --- |
| 0.6 | 0.4 |
| 0.5 | 0.3 |
| 0.4 | 0.2.1 |

Expand Down
24 changes: 19 additions & 5 deletions examples/2d.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,9 @@ fn main() {
App::new()
.insert_resource(Msaa { samples: 4 })
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
.add_startup_system(setup.system())
.add_system(demo.system())
.add_plugin(DebugLinesPlugin::always_in_front())
.add_startup_system(setup)
.add_system(demo)
.run();
}

Expand All @@ -24,11 +24,11 @@ fn demo(mut lines: ResMut<DebugLines>) {
Vec3::new(-400.0, 200.0, 0.0),
Vec3::new(400.0, 200.0, 0.0),
0.0,
); // Units are generally "smaller" for 2d, so thickness should be higher.
);
lines.line_colored(
Vec3::new(-400.0, 0.0, 0.0),
Vec3::new(400.0, 0.0, 0.0),
0.0,
0.9,
Color::GREEN,
);
lines.line_gradient(
Expand All @@ -38,4 +38,18 @@ fn demo(mut lines: ResMut<DebugLines>) {
Color::WHITE,
Color::PINK,
);
lines.line_gradient(
Vec3::new(-100.0, 100.0, 0.0),
Vec3::new(100.0, -100.0, 0.0),
0.8,
Color::WHITE,
Color::PINK,
);
lines.line_gradient(
Vec3::new(-100.0, -100.0, 0.0),
Vec3::new(100.0, 100.0, 0.0),
0.3,
Color::MIDNIGHT_BLUE,
Color::YELLOW_GREEN,
);
}
16 changes: 12 additions & 4 deletions examples/3d.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,17 +6,25 @@ fn main() {
App::new()
.insert_resource(Msaa { samples: 4 })
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
.add_startup_system(setup.system())
.add_system(demo.system())
.add_plugin(DebugLinesPlugin::default())
.add_startup_system(setup)
.add_system(demo)
.run();
}

fn setup(mut commands: Commands) {
fn setup(mut commands: Commands, mut lines: ResMut<DebugLines>) {
commands.spawn_bundle(PerspectiveCameraBundle {
transform: Transform::from_translation(Vec3::new(0.0, 0.0, 5.0)),
..Default::default()
});
// A line that stays on screen 9 seconds
lines.line_gradient(
Vec3::new(1.0, -1.0, -1.0),
Vec3::new(-1.0, 1.0, 1.0),
9.0,
Color::CYAN,
Color::MIDNIGHT_BLUE,
);
}

fn demo(time: Res<Time>, mut lines: ResMut<DebugLines>) {
Expand Down
20 changes: 9 additions & 11 deletions examples/bench.rs
Original file line number Diff line number Diff line change
@@ -1,23 +1,21 @@
use bevy::diagnostic::FrameTimeDiagnosticsPlugin;
use bevy::diagnostic::LogDiagnosticsPlugin;
use bevy::prelude::*;
use bevy::wgpu::diagnostic::WgpuResourceDiagnosticsPlugin;

use bevy_prototype_debug_lines::{DebugLines, DebugLinesPlugin};

fn main() {
App::new()
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
.add_plugin(DebugLinesPlugin::default())
.add_plugin(FrameTimeDiagnosticsPlugin::default())
.add_plugin(WgpuResourceDiagnosticsPlugin::default())
.add_plugin(LogDiagnosticsPlugin {
wait_duration: bevy::utils::Duration::new(5, 0),
..Default::default()
})
.add_startup_system(setup.system())
.add_system(demo_circle.system())
//.add_system(demo_block.system())
.add_startup_system(setup)
.add_system(demo_circle)
//.add_system(demo_block)
.run();
}

Expand All @@ -33,7 +31,7 @@ fn demo_circle(time: Res<Time>, mut lines: ResMut<DebugLines>) {
use std::f32::consts::PI;

const RADIUS: f32 = 1.5;
const THICKNESS: f32 = 0.001;
const DURATION: f32 = 0.0;

let seconds = 0.5 * time.seconds_since_startup() as f32;

Expand Down Expand Up @@ -61,14 +59,14 @@ fn demo_circle(time: Res<Time>, mut lines: ResMut<DebugLines>) {
let start_color = Color::rgba(start.x, start.y, 0.5, start.z.max(0.5));
let end_color = Color::rgba(end.x, end.y, 0.5, end.z.max(0.5));

lines.line_gradient(start, end, THICKNESS, start_color, end_color);
lines.line_gradient(start, end, DURATION, start_color, end_color);
}
}

fn _demo_block(mut lines: ResMut<DebugLines>) {
fn _demo_block(mut lines: DebugLines) {
use bevy_prototype_debug_lines::MAX_LINES;

const THICKNESS: f32 = 0.01;
const DURATION: f32 = 10.0;
const X: f32 = 2.0;
const Y: f32 = 1.0;

Expand All @@ -81,6 +79,6 @@ fn _demo_block(mut lines: ResMut<DebugLines>) {
let start_color = Color::rgba(start.x, start.y, 0.5, 1.0);
let end_color = Color::rgba(end.x, end.y, 0.5, 1.0);

lines.line_gradient(start, end, THICKNESS, start_color, end_color);
lines.line_gradient(start, end, DURATION, start_color, end_color);
}
}
6 changes: 1 addition & 5 deletions examples/depth_test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,7 @@ fn main() {
App::new()
.insert_resource(Msaa { samples: 4 })
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
.insert_resource(DebugLines {
depth_test: true,
..Default::default()
})
.add_plugin(DebugLinesPlugin::always_in_front())
.add_startup_system(setup.system())
.add_system(demo.system())
.run();
Expand Down
36 changes: 23 additions & 13 deletions examples/movement.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
use bevy::{input::mouse::MouseMotion, prelude::*};

use bevy_prototype_debug_lines::{ DebugLinesPlugin, DebugLines };
use bevy_prototype_debug_lines::{DebugLines, DebugLinesPlugin};

fn main() {
App::build()
App::new()
.insert_resource(Msaa { samples: 4 })
.add_plugins(DefaultPlugins)
.add_plugin(DebugLinesPlugin)
.add_plugin(DebugLinesPlugin::default())
.add_startup_system(setup.system())
.add_system_to_stage(CoreStage::Last, move_with_mouse.system().before("draw_lines"))
.add_system_to_stage(CoreStage::Last, move_with_mouse.before("draw_lines"))
.run();
}

Expand All @@ -22,15 +22,20 @@ fn setup(
..Default::default()
});

commands.spawn_bundle(PbrBundle {
mesh: meshes.add(Mesh::from(shape::Cube { size: 0.1 })),
material: materials.add(StandardMaterial { base_color: Color::RED, ..Default::default() }),
transform: Transform::from_xyz(0.0, 0.0, -0.5),
..Default::default()
})
.insert(MoveWithMouse);
commands
.spawn_bundle(PbrBundle {
mesh: meshes.add(Mesh::from(shape::Cube { size: 0.1 })),
material: materials.add(StandardMaterial {
base_color: Color::RED,
..Default::default()
}),
transform: Transform::from_xyz(0.0, 0.0, -0.5),
..Default::default()
})
.insert(MoveWithMouse);
}

#[derive(Component)]
struct MoveWithMouse;
fn move_with_mouse(
mut mouse_motion: EventReader<MouseMotion>,
Expand All @@ -46,6 +51,11 @@ fn move_with_mouse(
let movement = Vec3::new(delta.x, -delta.y, 0.0) * 0.01;
transform.translation += movement;
let forward = transform.local_z();
lines.line_colored(transform.translation, transform.translation + forward, 0.0, Color::GREEN);
lines.line_colored(
transform.translation,
transform.translation + forward,
0.0,
Color::GREEN,
);
}
}
}
Loading

0 comments on commit bc49414

Please sign in to comment.