@@ -102,6 +102,59 @@ impl CurveFitApp {
102102 }
103103 }
104104
105+ fn toggle_switch ( ui : & mut egui:: Ui , on : & mut bool ) -> egui:: Response {
106+ let desired_size = ui. spacing ( ) . interact_size . y * egui:: vec2 ( 1.50 , 0.8 ) ;
107+ let ( rect, mut response) = ui. allocate_exact_size ( desired_size, egui:: Sense :: click ( ) ) ;
108+
109+ if response. clicked ( ) {
110+ * on = !* on;
111+ response. mark_changed ( ) ;
112+ }
113+
114+ response. widget_info ( || {
115+ egui:: WidgetInfo :: selected ( egui:: WidgetType :: Checkbox , ui. is_enabled ( ) , * on, "" )
116+ } ) ;
117+
118+ if ui. is_rect_visible ( rect) {
119+ let how_on = ui. ctx ( ) . animate_bool_responsive ( response. id , * on) ;
120+ let visuals = ui. style ( ) . interact_selectable ( & response, * on) ;
121+ let rect = rect. expand ( visuals. expansion ) ;
122+ let radius = 0.5 * rect. height ( ) ;
123+
124+ ui. painter ( ) . rect (
125+ rect,
126+ radius,
127+ visuals. bg_fill ,
128+ visuals. bg_stroke ,
129+ egui:: StrokeKind :: Inside ,
130+ ) ;
131+
132+ let circle_x = egui:: lerp ( ( rect. left ( ) + radius) ..=( rect. right ( ) - radius) , how_on) ;
133+ let center = egui:: pos2 ( circle_x, rect. center ( ) . y ) ;
134+ ui. painter ( )
135+ . circle ( center, 0.75 * radius, visuals. bg_fill , visuals. fg_stroke ) ;
136+ }
137+
138+ response
139+ }
140+
141+ fn toggle_switch_labeled (
142+ ui : & mut egui:: Ui ,
143+ on : & mut bool ,
144+ label : impl Into < egui:: WidgetText > ,
145+ ) -> egui:: Response {
146+ ui. horizontal ( |ui| {
147+ let switch_response = Self :: toggle_switch ( ui, on) ;
148+ let mut label_response = ui. add ( egui:: Label :: new ( label) . sense ( egui:: Sense :: click ( ) ) ) ;
149+ if label_response. clicked ( ) {
150+ * on = !* on;
151+ label_response. mark_changed ( ) ;
152+ }
153+ switch_response | label_response
154+ } )
155+ . inner
156+ }
157+
105158 pub ( super ) fn next_unit_random ( & mut self ) -> f64 {
106159 self . spray_seed = self
107160 . spray_seed
@@ -332,15 +385,18 @@ impl CurveFitApp {
332385 panels_icon_image ( icon_tint) ,
333386 tr ( language, "Panels" , "Панели" ) ,
334387 |ui| {
335- ui. checkbox (
388+ Self :: toggle_switch_labeled (
389+ ui,
336390 & mut self . show_left_panel ,
337391 tr ( language, "Left panel" , "Левая панель" ) ,
338392 ) ;
339- ui. checkbox (
393+ Self :: toggle_switch_labeled (
394+ ui,
340395 & mut self . show_right_panel ,
341396 tr ( language, "Right panel" , "Правая панель" ) ,
342397 ) ;
343- ui. checkbox (
398+ Self :: toggle_switch_labeled (
399+ ui,
344400 & mut self . show_diagnostics_panel ,
345401 tr ( language, "Diagnostics" , "Диагностика" ) ,
346402 ) ;
@@ -363,7 +419,8 @@ impl CurveFitApp {
363419 self . pause_replay ( ) ;
364420 self . select_nearest_replay_iteration ( selected_iteration) ;
365421 }
366- ui. checkbox (
422+ Self :: toggle_switch_labeled (
423+ ui,
367424 & mut self . replay_autoplay_on_fit ,
368425 tr ( language, "Auto-play" , "Автопромотка" ) ,
369426 ) ;
0 commit comments