1
0

tui_update.rs 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220
  1. use criterion::{criterion_group, criterion_main, BenchmarkId, Criterion};
  2. use dioxus::prelude::*;
  3. use dioxus_tui::{Config, TuiContext};
  4. criterion_group!(mbenches, tui_update);
  5. criterion_main!(mbenches);
  6. /// This benchmarks the cache performance of the TUI for small edits by changing one box at a time.
  7. fn tui_update(c: &mut Criterion) {
  8. let mut group = c.benchmark_group("Update boxes");
  9. // We can also use loops to define multiple benchmarks, even over multiple dimensions.
  10. for size in 1..=8u32 {
  11. let parameter_string = format!("{}", (3 * size).pow(2));
  12. group.bench_with_input(
  13. BenchmarkId::new("size", parameter_string),
  14. &size,
  15. |b, size| {
  16. b.iter(|| match size {
  17. 1 => dioxus::tui::launch_cfg(app3, Config::default().with_headless()),
  18. 2 => dioxus::tui::launch_cfg(app6, Config::default().with_headless()),
  19. 3 => dioxus::tui::launch_cfg(app9, Config::default().with_headless()),
  20. 4 => dioxus::tui::launch_cfg(app12, Config::default().with_headless()),
  21. 5 => dioxus::tui::launch_cfg(app15, Config::default().with_headless()),
  22. 6 => dioxus::tui::launch_cfg(app18, Config::default().with_headless()),
  23. 7 => dioxus::tui::launch_cfg(app21, Config::default().with_headless()),
  24. 8 => dioxus::tui::launch_cfg(app24, Config::default().with_headless()),
  25. _ => (),
  26. })
  27. },
  28. );
  29. }
  30. }
  31. #[derive(Props, PartialEq)]
  32. struct BoxProps {
  33. x: usize,
  34. y: usize,
  35. hue: f32,
  36. alpha: f32,
  37. }
  38. #[allow(non_snake_case)]
  39. fn Box(cx: Scope<BoxProps>) -> Element {
  40. let count = use_state(&cx, || 0);
  41. let x = cx.props.x * 2;
  42. let y = cx.props.y * 2;
  43. let hue = cx.props.hue;
  44. let display_hue = cx.props.hue as u32 / 10;
  45. let count = count.get();
  46. let alpha = cx.props.alpha + (count % 100) as f32;
  47. cx.render(rsx! {
  48. div {
  49. left: "{x}%",
  50. top: "{y}%",
  51. width: "100%",
  52. height: "100%",
  53. background_color: "hsl({hue}, 100%, 50%, {alpha}%)",
  54. align_items: "center",
  55. p{"{display_hue:03}"}
  56. }
  57. })
  58. }
  59. #[derive(Props, PartialEq)]
  60. struct GridProps {
  61. size: usize,
  62. }
  63. #[allow(non_snake_case)]
  64. fn Grid(cx: Scope<GridProps>) -> Element {
  65. let size = cx.props.size;
  66. let count = use_state(&cx, || 0);
  67. let counts = use_ref(&cx, || vec![0; size * size]);
  68. let ctx: TuiContext = cx.consume_context().unwrap();
  69. if *count.get() + 1 >= (size * size) {
  70. ctx.quit();
  71. } else {
  72. counts.with_mut(|c| {
  73. let i = *count.current();
  74. c[i] += 1;
  75. c[i] = c[i] % 360;
  76. });
  77. count.with_mut(|i| {
  78. *i += 1;
  79. *i = *i % (size * size);
  80. });
  81. }
  82. cx.render(rsx! {
  83. div{
  84. width: "100%",
  85. height: "100%",
  86. flex_direction: "column",
  87. (0..size).map(|x|
  88. {
  89. cx.render(rsx! {
  90. div{
  91. width: "100%",
  92. height: "100%",
  93. flex_direction: "row",
  94. (0..size).map(|y|
  95. {
  96. let alpha = y as f32*100.0/size as f32 + counts.read()[x*size + y] as f32;
  97. let key = format!("{}-{}", x, y);
  98. cx.render(rsx! {
  99. Box{
  100. x: x,
  101. y: y,
  102. alpha: 100.0,
  103. hue: alpha,
  104. key: "{key}",
  105. }
  106. })
  107. }
  108. )
  109. }
  110. })
  111. }
  112. )
  113. }
  114. })
  115. }
  116. fn app3(cx: Scope) -> Element {
  117. cx.render(rsx! {
  118. div{
  119. width: "100%",
  120. height: "100%",
  121. Grid{
  122. size: 3,
  123. }
  124. }
  125. })
  126. }
  127. fn app6(cx: Scope) -> Element {
  128. cx.render(rsx! {
  129. div{
  130. width: "100%",
  131. height: "100%",
  132. Grid{
  133. size: 6,
  134. }
  135. }
  136. })
  137. }
  138. fn app9(cx: Scope) -> Element {
  139. cx.render(rsx! {
  140. div{
  141. width: "100%",
  142. height: "100%",
  143. Grid{
  144. size: 9,
  145. }
  146. }
  147. })
  148. }
  149. fn app12(cx: Scope) -> Element {
  150. cx.render(rsx! {
  151. div{
  152. width: "100%",
  153. height: "100%",
  154. Grid{
  155. size: 12,
  156. }
  157. }
  158. })
  159. }
  160. fn app15(cx: Scope) -> Element {
  161. cx.render(rsx! {
  162. div{
  163. width: "100%",
  164. height: "100%",
  165. Grid{
  166. size: 15,
  167. }
  168. }
  169. })
  170. }
  171. fn app18(cx: Scope) -> Element {
  172. cx.render(rsx! {
  173. div{
  174. width: "100%",
  175. height: "100%",
  176. Grid{
  177. size: 18,
  178. }
  179. }
  180. })
  181. }
  182. fn app21(cx: Scope) -> Element {
  183. cx.render(rsx! {
  184. div{
  185. width: "100%",
  186. height: "100%",
  187. Grid{
  188. size: 21,
  189. }
  190. }
  191. })
  192. }
  193. fn app24(cx: Scope) -> Element {
  194. cx.render(rsx! {
  195. div{
  196. width: "100%",
  197. height: "100%",
  198. Grid{
  199. size: 24,
  200. }
  201. }
  202. })
  203. }