1use super::{RESET_BUTTONS_HEIGHT, RESET_BUTTONS_WIDTH};
2
3use crate::{
4 GlobalState,
5 hud::{TEXT_COLOR, TEXT_COLOR_GREY, img_ids::Imgs},
6 session::settings_change::{Audio as AudioChange, Audio::*},
7 ui::{ImageSlider, ToggleButton, fonts::Fonts},
8};
9use conrod_core::{
10 Colorable, Labelable, Positionable, Sizeable, Widget, WidgetCommon, color,
11 position::{Align, Relative},
12 widget::{self, Button, Rectangle, Scrollbar, Text},
13 widget_ids,
14};
15use i18n::Localization;
16
17widget_ids! {
18 struct Ids {
19 window,
20 window_r,
21 window_scrollbar,
22 master_volume_text,
23 master_volume_slider,
24 master_volume_number,
25 master_volume_muted,
26 inactive_master_volume_text,
27 inactive_master_volume_slider,
28 inactive_master_volume_number,
29 inactive_master_volume_muted,
30 music_volume_text,
31 music_volume_slider,
32 music_volume_number,
33 music_volume_muted,
34 sfx_volume_text,
35 sfx_volume_slider,
36 sfx_volume_number,
37 sfx_volume_muted,
38 ambience_volume_text,
39 ambience_volume_slider,
40 ambience_volume_number,
41 ambience_volume_muted,
42 music_spacing_text,
43 music_spacing_slider,
44 music_spacing_number,
45 reset_sound_button,
48 combat_music_toggle_label,
49 combat_music_toggle_button,
50 }
51}
52
53#[derive(WidgetCommon)]
54pub struct Sound<'a> {
55 global_state: &'a GlobalState,
56 imgs: &'a Imgs,
57 fonts: &'a Fonts,
58 localized_strings: &'a Localization,
59 #[conrod(common_builder)]
60 common: widget::CommonBuilder,
61}
62impl<'a> Sound<'a> {
63 pub fn new(
64 global_state: &'a GlobalState,
65 imgs: &'a Imgs,
66 fonts: &'a Fonts,
67 localized_strings: &'a Localization,
68 ) -> Self {
69 Self {
70 global_state,
71 imgs,
72 fonts,
73 localized_strings,
74 common: widget::CommonBuilder::default(),
75 }
76 }
77}
78
79pub struct State {
80 ids: Ids,
81}
82
83impl Widget for Sound<'_> {
84 type Event = Vec<AudioChange>;
85 type State = State;
86 type Style = ();
87
88 fn init_state(&self, id_gen: widget::id::Generator) -> Self::State {
89 State {
90 ids: Ids::new(id_gen),
91 }
92 }
93
94 fn style(&self) -> Self::Style {}
95
96 fn update(self, args: widget::UpdateArgs<Self>) -> Self::Event {
97 common_base::prof_span!("Sound::update");
98 let widget::UpdateArgs { state, ui, .. } = args;
99
100 let mut events = Vec::new();
101
102 Rectangle::fill_with(args.rect.dim(), color::TRANSPARENT)
103 .xy(args.rect.xy())
104 .graphics_for(args.id)
105 .scroll_kids()
106 .scroll_kids_vertically()
107 .set(state.ids.window, ui);
108 Rectangle::fill_with([args.rect.w() / 2.0, args.rect.h()], color::TRANSPARENT)
109 .top_right()
110 .parent(state.ids.window)
111 .set(state.ids.window_r, ui);
112 Scrollbar::y_axis(state.ids.window)
113 .thickness(5.0)
114 .rgba(0.33, 0.33, 0.33, 1.0)
115 .set(state.ids.window_scrollbar, ui);
116
117 let non_master_volume_text_color =
118 match self.global_state.settings.audio.master_volume.muted {
119 true => TEXT_COLOR_GREY,
120 false => TEXT_COLOR,
121 };
122
123 Text::new(&self.localized_strings.get_msg("hud-settings-master_volume"))
125 .top_left_with_margins_on(state.ids.window, 10.0, 10.0)
126 .font_size(self.fonts.cyri.scale(14))
127 .font_id(self.fonts.cyri.conrod_id)
128 .color(TEXT_COLOR)
129 .set(state.ids.master_volume_text, ui);
130 let master_muted = ToggleButton::new(
132 self.global_state.settings.audio.master_volume.muted,
133 self.imgs.button_mute,
134 self.imgs.button_muted,
135 )
136 .w_h(24.0, 25.0)
137 .down_from(state.ids.master_volume_text, 10.0)
138 .hover_images(self.imgs.button_mute_hover, self.imgs.button_muted_hover)
139 .press_images(self.imgs.button_mute_press, self.imgs.button_muted_press)
140 .set(state.ids.master_volume_muted, ui);
141 if master_muted != self.global_state.settings.audio.master_volume.muted {
142 events.push(MuteMasterVolume(master_muted));
143 }
144 if let Some(new_val) = ImageSlider::continuous(
146 self.global_state.settings.audio.master_volume.volume,
147 0.0,
148 1.0,
149 self.imgs.slider_indicator,
150 self.imgs.slider,
151 )
152 .w_h(104.0, 22.0)
153 .right_from(state.ids.master_volume_muted, 8.0)
154 .track_breadth(12.0)
155 .slider_length(10.0)
156 .pad_track((5.0, 5.0))
157 .set(state.ids.master_volume_slider, ui)
158 {
159 events.push(AdjustMasterVolume(new_val));
160 }
161 Text::new(&format!(
163 "{:2.0}%",
164 self.global_state.settings.audio.master_volume.volume * 100.0
165 ))
166 .right_from(state.ids.master_volume_slider, 8.0)
167 .font_size(self.fonts.cyri.scale(14))
168 .font_id(self.fonts.cyri.conrod_id)
169 .color(TEXT_COLOR)
170 .set(state.ids.master_volume_number, ui);
171
172 Text::new(
174 &self
175 .localized_strings
176 .get_msg("hud-settings-inactive_master_volume_perc"),
177 )
178 .down_from(state.ids.master_volume_muted, 10.0)
179 .font_size(self.fonts.cyri.scale(14))
180 .font_id(self.fonts.cyri.conrod_id)
181 .color(TEXT_COLOR)
182 .set(state.ids.inactive_master_volume_text, ui);
183 let inactive_master_muted = ToggleButton::new(
185 self.global_state
186 .settings
187 .audio
188 .inactive_master_volume_perc
189 .muted,
190 self.imgs.button_mute,
191 self.imgs.button_muted,
192 )
193 .w_h(24.0, 25.0)
194 .down_from(state.ids.inactive_master_volume_text, 10.0)
195 .hover_images(self.imgs.button_mute_hover, self.imgs.button_muted_hover)
196 .press_images(self.imgs.button_mute_press, self.imgs.button_muted_press)
197 .set(state.ids.inactive_master_volume_muted, ui);
198 if inactive_master_muted
199 != self
200 .global_state
201 .settings
202 .audio
203 .inactive_master_volume_perc
204 .muted
205 {
206 events.push(MuteInactiveMasterVolume(inactive_master_muted));
207 }
208 if let Some(new_val) = ImageSlider::continuous(
210 self.global_state
211 .settings
212 .audio
213 .inactive_master_volume_perc
214 .volume,
215 0.0,
216 1.0,
217 self.imgs.slider_indicator,
218 self.imgs.slider,
219 )
220 .w_h(104.0, 22.0)
221 .right_from(state.ids.inactive_master_volume_muted, 8.0)
222 .track_breadth(12.0)
223 .slider_length(10.0)
224 .pad_track((5.0, 5.0))
225 .set(state.ids.inactive_master_volume_slider, ui)
226 {
227 events.push(AdjustInactiveMasterVolume(new_val));
228 }
229 Text::new(&format!(
231 "{:2.0}%",
232 self.global_state
233 .settings
234 .audio
235 .inactive_master_volume_perc
236 .volume
237 * 100.0
238 ))
239 .right_from(state.ids.inactive_master_volume_slider, 8.0)
240 .font_size(self.fonts.cyri.scale(14))
241 .font_id(self.fonts.cyri.conrod_id)
242 .color(non_master_volume_text_color)
243 .set(state.ids.inactive_master_volume_number, ui);
244
245 Text::new(&self.localized_strings.get_msg("hud-settings-music_volume"))
247 .down_from(state.ids.inactive_master_volume_muted, 10.0)
248 .font_size(self.fonts.cyri.scale(14))
249 .font_id(self.fonts.cyri.conrod_id)
250 .color(TEXT_COLOR)
251 .set(state.ids.music_volume_text, ui);
252 let music_muted = ToggleButton::new(
254 self.global_state.settings.audio.music_volume.muted,
255 self.imgs.button_mute,
256 self.imgs.button_muted,
257 )
258 .w_h(24.0, 25.0)
259 .down_from(state.ids.music_volume_text, 10.0)
260 .hover_images(self.imgs.button_mute_hover, self.imgs.button_muted_hover)
261 .press_images(self.imgs.button_mute_press, self.imgs.button_muted_press)
262 .set(state.ids.music_volume_muted, ui);
263 if music_muted != self.global_state.settings.audio.music_volume.muted {
264 events.push(MuteMusicVolume(music_muted));
265 }
266 if let Some(new_val) = ImageSlider::continuous(
268 self.global_state.settings.audio.music_volume.volume,
269 0.0,
270 1.0,
271 self.imgs.slider_indicator,
272 self.imgs.slider,
273 )
274 .w_h(104.0, 22.0)
275 .right_from(state.ids.music_volume_muted, 8.0)
276 .track_breadth(12.0)
277 .slider_length(10.0)
278 .pad_track((5.0, 5.0))
279 .set(state.ids.music_volume_slider, ui)
280 {
281 events.push(AdjustMusicVolume(new_val));
282 }
283 Text::new(&format!(
285 "{:2.0}%",
286 self.global_state.settings.audio.music_volume.volume * 100.0
287 ))
288 .right_from(state.ids.music_volume_slider, 8.0)
289 .font_size(self.fonts.cyri.scale(14))
290 .font_id(self.fonts.cyri.conrod_id)
291 .color(non_master_volume_text_color)
292 .set(state.ids.music_volume_number, ui);
293
294 Text::new(
296 &self
297 .localized_strings
298 .get_msg("hud-settings-sound_effect_volume"),
299 )
300 .down_from(state.ids.music_volume_muted, 10.0)
301 .font_size(self.fonts.cyri.scale(14))
302 .font_id(self.fonts.cyri.conrod_id)
303 .color(TEXT_COLOR)
304 .set(state.ids.sfx_volume_text, ui);
305 let sfx_muted = ToggleButton::new(
307 self.global_state.settings.audio.sfx_volume.muted,
308 self.imgs.button_mute,
309 self.imgs.button_muted,
310 )
311 .w_h(24.0, 25.0)
312 .down_from(state.ids.sfx_volume_text, 10.0)
313 .hover_images(self.imgs.button_mute_hover, self.imgs.button_muted_hover)
314 .press_images(self.imgs.button_mute_press, self.imgs.button_muted_press)
315 .set(state.ids.sfx_volume_muted, ui);
316 if sfx_muted != self.global_state.settings.audio.sfx_volume.muted {
317 events.push(MuteSfxVolume(sfx_muted));
318 }
319 if let Some(new_val) = ImageSlider::continuous(
321 self.global_state.settings.audio.sfx_volume.volume,
322 0.0,
323 1.0,
324 self.imgs.slider_indicator,
325 self.imgs.slider,
326 )
327 .w_h(104.0, 22.0)
328 .right_from(state.ids.sfx_volume_muted, 8.0)
329 .track_breadth(12.0)
330 .slider_length(10.0)
331 .pad_track((5.0, 5.0))
332 .set(state.ids.sfx_volume_slider, ui)
333 {
334 events.push(AdjustSfxVolume(new_val));
335 }
336 Text::new(&format!(
338 "{:2.0}%",
339 self.global_state.settings.audio.sfx_volume.volume * 100.0
340 ))
341 .right_from(state.ids.sfx_volume_slider, 8.0)
342 .font_size(self.fonts.cyri.scale(14))
343 .font_id(self.fonts.cyri.conrod_id)
344 .color(non_master_volume_text_color)
345 .set(state.ids.sfx_volume_number, ui);
346
347 Text::new(
349 &self
350 .localized_strings
351 .get_msg("hud-settings-ambience_volume"),
352 )
353 .down_from(state.ids.sfx_volume_muted, 10.0)
354 .font_size(self.fonts.cyri.scale(14))
355 .font_id(self.fonts.cyri.conrod_id)
356 .color(TEXT_COLOR)
357 .set(state.ids.ambience_volume_text, ui);
358 let ambience_muted = ToggleButton::new(
360 self.global_state.settings.audio.ambience_volume.muted,
361 self.imgs.button_mute,
362 self.imgs.button_muted,
363 )
364 .w_h(24.0, 25.0)
365 .down_from(state.ids.ambience_volume_text, 10.0)
366 .hover_images(self.imgs.button_mute_hover, self.imgs.button_muted_hover)
367 .press_images(self.imgs.button_mute_press, self.imgs.button_muted_press)
368 .set(state.ids.ambience_volume_muted, ui);
369 if ambience_muted != self.global_state.settings.audio.ambience_volume.muted {
370 events.push(MuteAmbienceVolume(ambience_muted));
371 }
372 if let Some(new_val) = ImageSlider::continuous(
374 self.global_state.settings.audio.ambience_volume.volume,
375 0.0,
376 1.0,
377 self.imgs.slider_indicator,
378 self.imgs.slider,
379 )
380 .w_h(104.0, 22.0)
381 .right_from(state.ids.ambience_volume_muted, 8.0)
382 .track_breadth(12.0)
383 .slider_length(10.0)
384 .pad_track((5.0, 5.0))
385 .set(state.ids.ambience_volume_slider, ui)
386 {
387 events.push(AdjustAmbienceVolume(new_val));
388 }
389 Text::new(&format!(
391 "{:2.0}%",
392 self.global_state.settings.audio.ambience_volume.volume * 100.0
393 ))
394 .right_from(state.ids.ambience_volume_slider, 8.0)
395 .font_size(self.fonts.cyri.scale(14))
396 .font_id(self.fonts.cyri.conrod_id)
397 .color(non_master_volume_text_color)
398 .set(state.ids.ambience_volume_number, ui);
399
400 Text::new(&self.localized_strings.get_msg("hud-settings-music_spacing"))
402 .down_from(state.ids.ambience_volume_muted, 10.0)
403 .font_size(self.fonts.cyri.scale(14))
404 .font_id(self.fonts.cyri.conrod_id)
405 .color(TEXT_COLOR)
406 .set(state.ids.music_spacing_text, ui);
407 if let Some(new_val) = ImageSlider::continuous(
409 self.global_state.settings.audio.music_spacing,
410 0.0,
411 2.0,
412 self.imgs.slider_indicator,
413 self.imgs.slider,
414 )
415 .w_h(104.0, 22.0)
416 .down_from(state.ids.music_spacing_text, 10.0)
417 .x_align_to(state.ids.ambience_volume_slider, Align::Start)
418 .track_breadth(12.0)
419 .slider_length(10.0)
420 .pad_track((5.0, 5.0))
421 .set(state.ids.music_spacing_slider, ui)
422 {
423 events.push(AdjustMusicSpacing(new_val));
424 }
425 Text::new(&format!(
427 "{:1.2}x",
428 self.global_state.settings.audio.music_spacing
429 ))
430 .right_from(state.ids.music_spacing_slider, 8.0)
431 .font_size(self.fonts.cyri.scale(14))
432 .font_id(self.fonts.cyri.conrod_id)
433 .color(TEXT_COLOR)
434 .set(state.ids.music_spacing_number, ui);
435
436 if Button::image(self.imgs.button)
489 .w_h(RESET_BUTTONS_WIDTH, RESET_BUTTONS_HEIGHT)
490 .hover_image(self.imgs.button_hover)
491 .press_image(self.imgs.button_press)
492 .down_from(state.ids.combat_music_toggle_button, 12.0)
493 .x_align_to(state.ids.ambience_volume_text, Align::Start)
494 .label(&self.localized_strings.get_msg("hud-settings-reset_sound"))
495 .label_font_size(self.fonts.cyri.scale(14))
496 .label_color(TEXT_COLOR)
497 .label_font_id(self.fonts.cyri.conrod_id)
498 .label_y(Relative::Scalar(2.0))
499 .set(state.ids.reset_sound_button, ui)
500 .was_clicked()
501 {
502 events.push(ResetAudioSettings);
503 }
504
505 events
506 }
507}