use bevy::{ pbr::wireframe::{Wireframe, WireframeConfig, WireframePlugin}, prelude::*, render::{ mesh::{Indices, VertexAttributeValues}, options::WgpuOptions, render_resource::WgpuFeatures, }, }; use bevy_polyline::{Polyline, PolylineBundle, PolylineMaterial, PolylinePlugin}; use rand::{thread_rng, Rng}; use crate::{lights::AnimateCyberLightWireframe, planet::CyberPlanet}; pub const BISEXY_COLOR: Color = Color::hsla(292.0, 0.9, 0.60, 1.1); fn wireframe_planet( mut commands: Commands, mut meshes: ResMut>, mut polylines: ResMut>, mut polymats: ResMut>, query: Query<&Handle, With>, ) { let handle = query.single(); let mesh = meshes.get_mut(handle).unwrap(); let vertices = mesh.attribute(Mesh::ATTRIBUTE_POSITION).unwrap(); let mut pts = Vec::with_capacity(vertices.len()); if let VertexAttributeValues::Float32x3(verts) = vertices { let indices = mesh.indices().unwrap(); if let Indices::U32(indices) = indices { for i in indices.iter() { let v = verts[*i as usize]; let v = Vec3::from_slice(&v); pts.push(v); } } } let mut verts = Vec::with_capacity((pts.len() as f32 * 1.4) as usize); for pts in pts.chunks(3) { if pts.len() > 1 { verts.extend_from_slice(pts); verts.push(Vec3::NAN); } } // don't need the indices anymore mesh.duplicate_vertices(); mesh.compute_flat_normals(); commands.spawn_bundle(PolylineBundle { polyline: polylines.add(Polyline { vertices: verts }), material: polymats.add(PolylineMaterial { width: 101.0, color: BISEXY_COLOR, perspective: true, }), ..Default::default() }); } fn wireframify_lights( mut commands: Commands, no_wires: Query, Without)>, wires: Query, With)>, ) { let chance = 0.005; let rng = &mut thread_rng(); for e in no_wires.iter() { if rng.gen::() < chance { commands.entity(e).insert(Wireframe); } } for e in wires.iter() { if rng.gen::() < chance { commands.entity(e).remove::(); } } } // public plugin pub struct CyberGlamorPlugin; impl Plugin for CyberGlamorPlugin { fn build(&self, app: &mut App) { app.insert_resource(WgpuOptions { features: WgpuFeatures::POLYGON_MODE_LINE, ..Default::default() }) .insert_resource(WireframeConfig { global: false }) .add_startup_system_to_stage( StartupStage::PostStartup, wireframe_planet.after("colliders"), ) .add_system(wireframify_lights) .add_plugin(PolylinePlugin) .add_plugin(WireframePlugin); } }