dilemma_tactix_lib/models/game_option_builder.rs
1// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
2// * Copyright (c) 2023-2024
3// *
4// * This project is dual-licensed under the MIT and Apache licenses.
5// *
6// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
7// ** APACHE 2.0 LICENSE
8// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
9// *
10// * Licensed under the Apache License, Version 2.0 (the "License");
11// * you may not use this file except in compliance with the License.
12// * You may obtain a copy of the License at
13// *
14// * http://www.apache.org/licenses/LICENSE-2.0
15// *
16// * Unless required by applicable law or agreed to in writing, software
17// * distributed under the License is distributed on an "AS IS" BASIS,
18// * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
19// * See the License for the specific language governing permissions and
20// * limitations under the License.
21// *
22// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
23// * * MIT LICENSE
24// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
25// *
26// * Permission is hereby granted, free of charge, to any person obtaining a copy
27// * of this software and associated documentation files (the "Software"), to deal
28// * in the Software without restriction, including without limitation the rights
29// * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
30// * copies of the Software, and to permit persons to whom the Software is
31// * furnished to do so, subject to the following conditions:
32// *
33// * The above copyright notice and this permission notice shall be included in all
34// * copies or substantial portions of the Software.
35// *
36// * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
37// * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
38// * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
39// * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
40// * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
41// * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
42// * SOFTWARE.
43// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
44
45use crate::{
46 BuilderError,
47 GameOptions,
48 NumberPair,
49};
50
51#[derive(Clone, Copy, Debug, PartialEq, Eq)]
52pub enum GameOptionsBuilderTypes {
53 /// This builder variant allows for full randomization
54 /// of the GameOptions struct that is being built.
55 Randomized,
56 /// This builder variant allows for the GameOptions struct
57 /// that is being built to be randomized, but seeded.
58 Seeded,
59 /// This builder variant allows for the GameOptions struct
60 /// that is being built to be fully customized.
61 Customized,
62}
63
64/// A builder struct to create a [`GameOptions`](crate::GameOptions).
65///
66/// This struct is designed to encapsulate different ways of generating a new
67/// `GameOptions` struct. It is designed to be used in conjunction with the
68/// [`GameOptions`](crate::GameOptions) struct.
69///
70/// The `GameOptionsBuilder::new()` method is used to create a new builder,
71/// which takes a `builder_type` argument. This argument is used to determine
72/// which variant of the builder is used. The `builder_type` argument can be one
73/// of the following:
74///
75/// * "randomized": This creates a builder of type
76/// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized).
77/// * "seeded": This creates a builder of type
78/// [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded)
79/// * "customized": This creates a builder of type
80/// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized)
81///
82/// Each of these variants has different fields that can be set and serve
83/// different purposes. The following table shows which fields should be set for
84/// each variant:
85///
86/// | Field | Randomized | Seeded | Customized | Type | Default |
87/// | ----- | ---------- | ------ | ---------- | ---- | ------- |
88/// | `min_value` | Yes | No | Yes | u32 | 1 |
89/// | `max_value` | Yes | No | Yes | u32 | 10 |
90/// | `choice_atlantis` | Yes | Yes | Yes | &'static str | "cooperate" |
91/// | `choice_olympus` | Yes | Yes | Yes | &'static str | "defect" |
92/// | `atlantis_atlantis` | No | No | Yes | `NumberPair` | `NumberPair::new(4, 4)` |
93/// | `atlantis_olympus` | No | No | Yes | `NumberPair` | `NumberPair::new(0, 5)` |
94/// | `olympus_atlantis` | No | No | Yes | `NumberPair` | `NumberPair::new(5, 0)` |
95/// | `olympus_olympus` | No | No | Yes | `NumberPair` | `NumberPair::new(3, 3)` |
96/// | `seed` | No | Yes | No | `u64` | `None` |
97/// # Example
98///
99/// ## `RandomizedBuilder`
100///
101/// This builder path takes in the lower bound and the upper bound for the
102/// scores that can be assigned to each option. It then generates a random
103/// score for each option within the given bounds.
104///
105/// ```
106/// use dilemma_tactix_lib::{
107/// GameOptionsBuilder as Builder,
108/// GameOptionsBuilderTypes as BuilderTypes,
109/// NumberPair,
110/// # BuilderError,
111/// };
112///
113/// let builder = Builder::new(BuilderTypes::Randomized);
114/// let builder = builder.min_value(1);
115/// # assert!(builder.is_ok());
116/// let builder = builder?.max_value(10);
117/// # assert!(builder.is_ok());
118/// let builder = builder?.choice_atlantis("cooperate");
119/// # assert!(builder.is_ok());
120/// let builder = builder?.choice_olympus("defect");
121/// # assert!(builder.is_ok());
122///
123/// let game_options = builder?.build();
124///
125/// # assert_eq!(game_options.choice_atlantis(), "cooperate");
126/// # assert_eq!(game_options.choice_olympus(), "defect");
127/// # assert!(game_options.atlantis_atlantis().first() >= 1);
128/// # assert!(game_options.atlantis_atlantis().first() <= 10);
129/// # assert!(game_options.atlantis_atlantis().second() >= 1);
130/// # assert!(game_options.atlantis_atlantis().second() <= 10);
131/// # assert!(game_options.atlantis_olympus().first() >= 1);
132/// # assert!(game_options.atlantis_olympus().first() <= 10);
133/// # assert!(game_options.atlantis_olympus().second() >= 1);
134/// # assert!(game_options.atlantis_olympus().second() <= 10);
135/// # assert!(game_options.olympus_atlantis().first() >= 1);
136/// # assert!(game_options.olympus_atlantis().first() <= 10);
137/// # assert!(game_options.olympus_atlantis().second() >= 1);
138/// # assert!(game_options.olympus_atlantis().second() <= 10);
139/// # assert!(game_options.olympus_olympus().first() >= 1);
140/// # assert!(game_options.olympus_olympus().first() <= 10);
141/// # assert!(game_options.olympus_olympus().second() >= 1);
142/// # assert!(game_options.olympus_olympus().second() <= 10);
143///
144/// # Ok::<(), BuilderError>(())
145/// ```
146/// ## `SeededBuilder`
147///
148/// This builder path takes in the lower bound and the upper bound for the
149/// scores that can be assigned to each option. It also takes a `seed` value
150/// It then generates a random score for each option within the given
151/// bounds and the given seed.
152///
153/// ```no_run
154/// use dilemma_tactix_lib::{
155/// GameOptionsBuilder as Builder,
156/// GameOptionsBuilderTypes as BuilderTypes,
157/// };
158///
159/// let builder = Builder::new(BuilderTypes::Seeded);
160/// # assert_eq!(builder.choice_atlantis, None);
161/// # assert_eq!(builder.choice_olympus, None);
162/// # assert_eq!(builder.atlantis_atlantis, None);
163/// # assert_eq!(builder.atlantis_olympus, None);
164/// # assert_eq!(builder.olympus_atlantis, None);
165/// # assert_eq!(builder.olympus_olympus, None);
166/// ```
167///
168/// ## `CustomizedBuilder`
169///
170/// This builder allows you to set all the scores for each possible
171/// outcome individually. This allows for the most customization of the
172/// `GameOptions` struct.
173///
174/// ```
175/// use dilemma_tactix_lib::{
176/// GameOptionsBuilder as Builder,
177/// GameOptionsBuilderTypes as BuilderTypes,
178/// NumberPair,
179/// # BuilderError,
180/// };
181///
182/// let builder = Builder::new(BuilderTypes::Customized);
183/// let builder = builder.choice_atlantis("cooperate");
184/// # assert!(builder.is_ok());
185/// let builder = builder?.choice_olympus("defect");
186/// # assert!(builder.is_ok());
187/// let builder = builder?.atlantis_atlantis(NumberPair::new(4, 4));
188/// # assert!(builder.is_ok());
189/// let builder = builder?.atlantis_olympus(NumberPair::new(0, 5));
190/// # assert!(builder.is_ok());
191/// let builder = builder?.olympus_atlantis(NumberPair::new(5, 0));
192/// # assert!(builder.is_ok());
193/// let builder = builder?.olympus_olympus(NumberPair::new(3, 3));
194/// # assert!(builder.is_ok());
195///
196/// let game_options = builder?.build();
197///
198/// # assert_eq!(game_options.choice_atlantis(), "cooperate");
199/// # assert_eq!(game_options.choice_olympus(), "defect");
200/// # assert_eq!(game_options.atlantis_atlantis(), NumberPair::new(4, 4));
201/// # assert_eq!(game_options.atlantis_olympus(), NumberPair::new(0, 5));
202/// # assert_eq!(game_options.olympus_atlantis(), NumberPair::new(5, 0));
203/// # assert_eq!(game_options.olympus_olympus(), NumberPair::new(3, 3));
204/// # Ok::<(), BuilderError>(())
205/// ```
206///
207/// # Notes
208///
209/// I chose to use the `Builder` pattern here because it allows for easier
210/// manipulation of the `GameOptions` struct. I also used a `State` or `Variant`
211/// pattern here because it had the lowest complexity in terms of understanding
212/// the flow of options that need to be set.
213///
214/// # See Also
215///
216/// * [`GameOptions`](crate::GameOptions)
217#[derive(Debug, Clone, Copy, PartialEq, Eq)]
218pub struct GameOptionsBuilder {
219 builder_type: GameOptionsBuilderTypes,
220 min_value: Option<u32>,
221 max_value: Option<u32>,
222 pub choice_atlantis: Option<&'static str>,
223 pub choice_olympus: Option<&'static str>,
224 pub atlantis_atlantis: Option<NumberPair>,
225 pub atlantis_olympus: Option<NumberPair>,
226 pub olympus_atlantis: Option<NumberPair>,
227 pub olympus_olympus: Option<NumberPair>,
228 seed: Option<u64>,
229}
230
231impl GameOptionsBuilder {
232 /// Creates a new `GameOptionsBuilder` struct.
233 ///
234 /// This associated function creates a new `GameOptionsBuilder` struct with
235 /// the given `builder_type`. The `builder_type` argument can be one of the
236 /// following:
237 ///
238 /// * "randomized": This creates a builder of type
239 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized).
240 /// * "seeded": This creates a builder of type
241 /// [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded)
242 /// * "customized": This creates a builder of type
243 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized)
244 ///
245 /// # Arguments
246 ///
247 /// * `builder_type` - The type of builder to create.
248 ///
249 /// # Example
250 ///
251 /// ## `RandomizedBuilder`
252 ///
253 /// This builder path takes in the lower bound and the upper bound for the
254 /// scores that can be assigned to each option. It then generates a random
255 /// score for each option within the given bounds.
256 ///
257 /// ```
258 /// use dilemma_tactix_lib::{
259 /// GameOptionsBuilder,
260 /// GameOptionsBuilderTypes,
261 /// };
262 ///
263 /// let game_options_builder =
264 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
265 /// # assert_eq!(game_options_builder.choice_atlantis, None);
266 /// # assert_eq!(game_options_builder.choice_olympus, None);
267 /// # assert_eq!(game_options_builder.atlantis_atlantis, None);
268 /// # assert_eq!(game_options_builder.atlantis_olympus, None);
269 /// # assert_eq!(game_options_builder.olympus_atlantis, None);
270 /// # assert_eq!(game_options_builder.olympus_olympus, None);
271 /// ```
272 /// ## `SeededBuilder`
273 ///
274 /// This builder path takes in the lower bound and the upper bound for the
275 /// scores that can be assigned to each option. It also takes a `seed` value
276 /// It then generates a random score for each option within the given
277 /// bounds and the given seed.
278 ///
279 /// ```no_run
280 /// use dilemma_tactix_lib::{
281 /// GameOptionsBuilder,
282 /// GameOptionsBuilderTypes,
283 /// };
284 ///
285 /// let game_options_builder =
286 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
287 /// # assert_eq!(game_options_builder.choice_atlantis, None);
288 /// # assert_eq!(game_options_builder.choice_olympus, None);
289 /// # assert_eq!(game_options_builder.atlantis_atlantis, None);
290 /// # assert_eq!(game_options_builder.atlantis_olympus, None);
291 /// # assert_eq!(game_options_builder.olympus_atlantis, None);
292 /// # assert_eq!(game_options_builder.olympus_olympus, None);
293 /// ```
294 ///
295 /// ## `CustomizedBuilder`
296 ///
297 /// This builder allows you to set all the scores for each possible
298 /// outcome individually. This allows for the most customization of the
299 /// `GameOptions` struct.
300 ///
301 /// ```
302 /// use dilemma_tactix_lib::{
303 /// GameOptionsBuilder,
304 /// GameOptionsBuilderTypes,
305 /// };
306 ///
307 /// let game_options_builder =
308 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized);
309 /// # assert_eq!(game_options_builder.choice_atlantis, None);
310 /// # assert_eq!(game_options_builder.choice_olympus, None);
311 /// # assert_eq!(game_options_builder.atlantis_atlantis, None);
312 /// # assert_eq!(game_options_builder.atlantis_olympus, None);
313 /// # assert_eq!(game_options_builder.olympus_atlantis, None);
314 /// # assert_eq!(game_options_builder.olympus_olympus, None);
315 /// ```
316 ///
317 /// # Returns
318 ///
319 /// A new `GameOptionsBuilder` struct with a given builder type.
320 ///
321 /// # See Also
322 ///
323 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
324 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
325 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
326 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
327 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
328 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
329 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
330 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
331 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
332 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
333 #[must_use]
334 pub const fn new(builder_type: GameOptionsBuilderTypes) -> Self {
335 Self {
336 builder_type,
337 max_value: None,
338 min_value: None,
339 choice_atlantis: None,
340 choice_olympus: None,
341 atlantis_atlantis: None,
342 atlantis_olympus: None,
343 olympus_atlantis: None,
344 olympus_olympus: None,
345 seed: None,
346 }
347 }
348
349 /// Sets the minimum value for the `GameOptions`.
350 ///
351 /// This function sets the minimum value for the `GameOptions` struct that
352 /// is being built. This function is only valid for the
353 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
354 /// and the [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded)
355 /// variants of the `GameOptionsBuilder` struct.
356 ///
357 /// # Arguments
358 ///
359 /// * `min_value` - The minimum value for the `GameOptions`.
360 ///
361 /// # Example
362 ///
363 /// ## `RandomizedBuilder`
364 /// ```
365 /// use dilemma_tactix_lib::{
366 /// GameOptionsBuilder,
367 /// GameOptionsBuilderTypes,
368 /// };
369 ///
370 /// let game_options_builder =
371 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
372 /// .min_value(1);
373 /// assert!(game_options_builder.is_ok());
374 /// ```
375 ///
376 /// ## `SeededBuilder`
377 ///
378 /// ```no_run
379 /// use dilemma_tactix_lib::{
380 /// GameOptionsBuilder,
381 /// GameOptionsBuilderTypes,
382 /// };
383 ///
384 /// let game_options_builder =
385 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).min_value(1);
386 ///
387 /// assert!(game_options_builder.is_ok());
388 /// ```
389 ///
390 /// ## `CustomizedBuilder`
391 ///
392 /// ```
393 /// use dilemma_tactix_lib::{
394 /// GameOptionsBuilder,
395 /// GameOptionsBuilderTypes,
396 /// };
397 ///
398 /// let game_options_builder =
399 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
400 /// .min_value(1);
401 ///
402 /// assert!(game_options_builder.is_err());
403 /// ```
404 ///
405 /// # Errors
406 ///
407 /// This function will return an error if the `builder_type` is
408 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized).
409 ///
410 /// # Returns
411 ///
412 /// The `GameOptionsBuilder` struct with the `min_value` field set.
413 ///
414 /// # See Also
415 ///
416 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
417 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
418 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
419 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
420 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
421 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
422 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
423 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
424 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
425 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
426 pub fn min_value(mut self, min_value: u32) -> Result<Self, BuilderError> {
427 match self.builder_type {
428 GameOptionsBuilderTypes::Randomized | GameOptionsBuilderTypes::Seeded => {
429 self.min_value = Some(min_value);
430 Ok(self)
431 }
432 GameOptionsBuilderTypes::Customized => Err(BuilderError::InvalidOptionSpecified(
433 "min_value must not be set when using CusotmizedBuilder".to_string(),
434 )),
435 }
436 }
437
438 /// Sets the maximum value for the `GameOptions`.
439 ///
440 /// This function sets the maximum value for the `GameOptions` struct that
441 /// is being built. This function is only valid for the
442 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
443 /// and the [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded)
444 /// variants of the `GameOptionsBuilder` struct.
445 ///
446 /// # Arguments
447 ///
448 /// * `max_value` - The maximum value for the `GameOptions`.
449 ///
450 /// # Example
451 ///
452 /// ## `RandomizedBuilder`
453 /// ```
454 /// use dilemma_tactix_lib::{
455 /// GameOptionsBuilder,
456 /// GameOptionsBuilderTypes,
457 /// };
458 ///
459 /// let game_options_builder =
460 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
461 /// .max_value(10);
462 /// assert!(game_options_builder.is_ok());
463 /// ```
464 ///
465 /// ## `SeededBuilder`
466 ///
467 /// ```no_run
468 /// use dilemma_tactix_lib::{
469 /// GameOptionsBuilder,
470 /// GameOptionsBuilderTypes,
471 /// };
472 ///
473 /// let game_options_builder =
474 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).max_value(10);
475 ///
476 /// assert!(game_options_builder.is_ok());
477 /// ```
478 ///
479 /// ## `CustomizedBuilder`
480 ///
481 /// ```
482 /// use dilemma_tactix_lib::{
483 /// GameOptionsBuilder,
484 /// GameOptionsBuilderTypes,
485 /// };
486 ///
487 /// let game_options_builder =
488 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
489 /// .max_value(10);
490 ///
491 /// assert!(game_options_builder.is_err());
492 /// ```
493 ///
494 /// # Errors
495 ///
496 /// This function will return an error if the `builder_type` is
497 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized).
498 ///
499 /// # Returns
500 ///
501 /// The `GameOptionsBuilder` struct with the `max_value` field set.
502 ///
503 /// # See Also
504 ///
505 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
506 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
507 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
508 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
509 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
510 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
511 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
512 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
513 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
514 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
515 pub fn max_value(mut self, max_value: u32) -> Result<Self, BuilderError> {
516 match self.builder_type {
517 GameOptionsBuilderTypes::Randomized | GameOptionsBuilderTypes::Seeded => {
518 self.max_value = Some(max_value);
519 Ok(self)
520 }
521 GameOptionsBuilderTypes::Customized => Err(BuilderError::InvalidOptionSpecified(
522 "max_value must not be set when using CustomizedBuilder".to_string(),
523 )),
524 }
525 }
526
527 /// Sets the first choice available to players in `GameOptions`.
528 ///
529 /// This function sets the first choice available to players in
530 /// `GameOptions`. This function is valid for all variants of the
531 /// `GameOptionsBuilder` struct.
532 ///
533 /// # Arguments
534 ///
535 /// * `choice_atlantis` - The first choice available to players in `GameOptions`.
536 ///
537 /// # Example
538 ///
539 /// ## `RandomizedBuilder`
540 ///
541 /// ```
542 /// use dilemma_tactix_lib::{
543 /// GameOptionsBuilder,
544 /// GameOptionsBuilderTypes,
545 /// };
546 ///
547 /// let game_options_builder =
548 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
549 /// .choice_atlantis("cooperate");
550 /// # assert!(game_options_builder.is_ok());
551 ///
552 /// let game_options = game_options_builder.unwrap().build();
553 ///
554 /// # assert_eq!(game_options.choice_atlantis(), "cooperate");
555 /// ```
556 ///
557 /// ## `SeededBuilder`
558 ///
559 /// ```no_run
560 /// use dilemma_tactix_lib::{
561 /// GameOptionsBuilder,
562 /// GameOptionsBuilderTypes,
563 /// };
564 /// use rand::SeedableRng;
565 ///
566 /// let game_options_builder =
567 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
568 /// .choice_atlantis("cooperate");
569 /// # assert!(game_options_builder.is_ok());
570 ///
571 /// let game_options = game_options_builder.unwrap().build();
572 ///
573 /// # assert_eq!(game_options.choice_atlantis(), "cooperate");
574 /// ```
575 ///
576 /// ## `CustomizedBuilder`
577 ///
578 /// ```
579 /// use dilemma_tactix_lib::{
580 /// GameOptionsBuilder,
581 /// GameOptionsBuilderTypes,
582 /// };
583 ///
584 /// let game_options_builder =
585 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
586 /// .choice_atlantis("cooperate");
587 /// # assert!(game_options_builder.is_ok());
588 ///
589 /// let game_options = game_options_builder.unwrap().build();
590 ///
591 /// # assert_eq!(game_options.choice_atlantis(), "cooperate");
592 /// ```
593 ///
594 /// # Errors
595 ///
596 /// This function will return an error if the `choice_atlantis` argument is
597 /// empty.
598 ///
599 /// # Returns
600 ///
601 /// The `GameOptionsBuilder` struct with the `choice_atlantis` field set.
602 ///
603 /// # See Also
604 ///
605 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
606 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
607 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
608 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
609 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
610 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
611 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
612 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
613 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
614 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
615 pub fn choice_atlantis(mut self, choice_atlantis: &'static str) -> Result<Self, BuilderError> {
616 if choice_atlantis.is_empty() {
617 return Err(BuilderError::InvalidOptionValueSpecified(
618 "choice_atlantis must not be empty".to_string(),
619 ));
620 }
621 self.choice_atlantis = Some(choice_atlantis);
622 Ok(self)
623 }
624
625 /// Sets the second choice available to players in `GameOptions`.
626 ///
627 /// This function sets the second choice available to players in
628 /// `GameOptions`. This function is valid for all variants of the
629 /// `GameOptionsBuilder` struct.
630 ///
631 /// # Arguments
632 ///
633 /// * `choice_olympus` - The second choice available to players in `GameOptions`.
634 ///
635 /// # Example
636 ///
637 /// ## `RandomizedBuilder`
638 ///
639 /// ```
640 /// use dilemma_tactix_lib::{
641 /// GameOptionsBuilder,
642 /// GameOptionsBuilderTypes,
643 /// };
644 ///
645 /// let game_options_builder =
646 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
647 /// .choice_olympus("defect");
648 /// # assert!(game_options_builder.is_ok());
649 ///
650 /// let game_options = game_options_builder.unwrap().build();
651 ///
652 /// # assert_eq!(game_options.choice_olympus(), "defect");
653 /// ```
654 ///
655 /// ## `SeededBuilder`
656 ///
657 /// ```no_run
658 /// use dilemma_tactix_lib::{
659 /// GameOptionsBuilder,
660 /// GameOptionsBuilderTypes,
661 /// };
662 ///
663 /// let game_options_builder =
664 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
665 /// .choice_olympus("defect");
666 /// # assert!(game_options_builder.is_ok());
667 ///
668 /// let game_options = game_options_builder.unwrap().build();
669 ///
670 /// # assert_eq!(game_options.choice_olympus(), "defect");
671 /// ```
672 ///
673 /// ## `CustomizedBuilder`
674 ///
675 /// ```
676 /// use dilemma_tactix_lib::{
677 /// GameOptionsBuilder,
678 /// GameOptionsBuilderTypes,
679 /// };
680 ///
681 /// let game_options_builder =
682 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
683 /// .choice_olympus("defect");
684 /// # assert!(game_options_builder.is_ok());
685 ///
686 /// let game_options = game_options_builder.unwrap().build();
687 ///
688 /// # assert_eq!(game_options.choice_olympus(), "defect");
689 /// ```
690 ///
691 /// # Errors
692 ///
693 /// This function will return an error if the `choice_olympus` argument is
694 /// empty.
695 ///
696 /// # Returns
697 ///
698 /// The `GameOptionsBuilder` struct with the `choice_olympus` field set.
699 ///
700 /// # See Also
701 ///
702 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
703 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
704 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
705 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
706 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
707 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
708 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
709 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
710 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
711 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
712 pub fn choice_olympus(mut self, choice_olympus: &'static str) -> Result<Self, BuilderError> {
713 if choice_olympus.is_empty() {
714 return Err(BuilderError::InvalidOptionValueSpecified(
715 "choice_olympus must not be empty".to_string(),
716 ));
717 }
718 self.choice_olympus = Some(choice_olympus);
719 Ok(self)
720 }
721
722 /// Sets the score for the case when both players (Aleph and Beth) choose
723 /// the first (Atlantis) choice.
724 ///
725 /// This function sets the score for the case when both players choose the
726 /// first (Atlantis) choice. This function is only valid for the
727 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized)
728 /// variant of the `GameOptionsBuilder` struct.
729 ///
730 /// # Arguments
731 ///
732 /// * `atlantis_atlantis` - The score to set.
733 ///
734 /// # Example
735 ///
736 /// ## `RandomizedBuilder`
737 ///
738 /// ```
739 /// use dilemma_tactix_lib::{
740 /// GameOptionsBuilder,
741 /// GameOptionsBuilderTypes,
742 /// NumberPair,
743 /// };
744 ///
745 /// let game_options_builder =
746 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
747 /// .atlantis_atlantis(NumberPair::new(4, 4));
748 /// # assert!(game_options_builder.is_err());
749 /// ```
750 ///
751 /// ## `SeededBuilder`
752 ///
753 /// ```no_run
754 /// use dilemma_tactix_lib::{
755 /// GameOptionsBuilder,
756 /// GameOptionsBuilderTypes,
757 /// NumberPair,
758 /// };
759 ///
760 /// let game_options_builder =
761 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
762 /// .atlantis_atlantis(NumberPair::new(4, 4));
763 /// # assert!(game_options_builder.is_err());
764 /// ```
765 ///
766 /// ## `CustomizedBuilder`
767 ///
768 /// ```
769 /// use dilemma_tactix_lib::{
770 /// GameOptionsBuilder,
771 /// GameOptionsBuilderTypes,
772 /// NumberPair,
773 /// };
774 ///
775 /// let game_options_builder =
776 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
777 /// .atlantis_atlantis(NumberPair::new(4, 4));
778 ///
779 /// # assert!(game_options_builder.is_ok());
780 ///
781 /// let game_options = game_options_builder.unwrap().build();
782 ///
783 /// # assert_eq!(game_options.atlantis_atlantis(), NumberPair::new(4, 4));
784 /// ```
785 ///
786 /// # Errors
787 ///
788 /// This function will return an error if the `builder_type` is
789 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
790 /// or [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded).
791 ///
792 /// # Returns
793 ///
794 /// The `GameOptionsBuilder` struct with the `atlantis_atlantis` field set.
795 ///
796 /// # See Also
797 ///
798 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
799 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
800 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
801 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
802 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
803 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
804 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
805 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
806 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
807 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
808 pub fn atlantis_atlantis(
809 mut self,
810 atlantis_atlantis: NumberPair,
811 ) -> Result<Self, BuilderError> {
812 match self.builder_type {
813 GameOptionsBuilderTypes::Randomized => Err(BuilderError::InvalidOptionSpecified(
814 "Field atlantis_atlantis can not be set when using RandomizedBuilder".to_string(),
815 )),
816 GameOptionsBuilderTypes::Seeded => Err(BuilderError::InvalidOptionSpecified(
817 "Field atlantis_atlantis can not be set when using SeededBuilder".to_string(),
818 )),
819 GameOptionsBuilderTypes::Customized => {
820 self.atlantis_atlantis = Some(atlantis_atlantis);
821 Ok(self)
822 }
823 }
824 }
825
826 /// Sets the score for the case when Player Aleph chooses the first
827 /// (Atlantis) choice and Player Beth chooses the second (Olympus)
828 /// choice.
829 ///
830 /// This function sets the score for the case when Player Aleph chooses the
831 /// first (Atlantis) choice and Player Beth chooses the second (Olympus)
832 /// choice. This function is only valid for the
833 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized)
834 /// variant of the `GameOptionsBuilder` struct.
835 ///
836 /// # Arguments
837 ///
838 /// * `atlantis_olympus` - The score to set.
839 ///
840 /// # Example
841 ///
842 /// ## `RandomizedBuilder`
843 ///
844 /// ```
845 /// use dilemma_tactix_lib::{
846 /// GameOptionsBuilder,
847 /// GameOptionsBuilderTypes,
848 /// NumberPair,
849 /// };
850 ///
851 /// let game_options_builder =
852 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
853 /// .atlantis_olympus(NumberPair::new(0, 5));
854 /// # assert!(game_options_builder.is_err());
855 /// ```
856 ///
857 /// ## `SeededBuilder`
858 ///
859 /// ```
860 /// use dilemma_tactix_lib::{
861 /// GameOptionsBuilder,
862 /// GameOptionsBuilderTypes,
863 /// NumberPair,
864 /// };
865 ///
866 /// let game_options_builder =
867 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
868 /// .atlantis_olympus(NumberPair::new(0, 5));
869 /// # assert!(game_options_builder.is_err());
870 /// ```
871 ///
872 /// ## `CustomizedBuilder`
873 ///
874 /// ```
875 /// use dilemma_tactix_lib::{
876 /// GameOptionsBuilder,
877 /// GameOptionsBuilderTypes,
878 /// NumberPair,
879 /// };
880 ///
881 /// let game_options_builder =
882 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
883 /// .atlantis_olympus(NumberPair::new(0, 5));
884 /// # assert!(game_options_builder.is_ok());
885 ///
886 /// let game_options = game_options_builder.unwrap().build();
887 ///
888 /// # assert_eq!(game_options.atlantis_olympus(), NumberPair::new(0, 5));
889 /// ```
890 ///
891 /// # Errors
892 ///
893 /// This function will return an error if the `builder_type` is
894 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
895 /// or [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded).
896 ///
897 /// # Returns
898 ///
899 /// The `GameOptionsBuilder` struct with the `atlantis_olympus` field set.
900 ///
901 ///
902 /// # See Also
903 ///
904 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
905 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
906 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
907 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
908 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
909 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
910 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
911 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
912 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
913 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
914 pub fn atlantis_olympus(mut self, atlantis_olympus: NumberPair) -> Result<Self, BuilderError> {
915 match self.builder_type {
916 GameOptionsBuilderTypes::Randomized => Err(BuilderError::InvalidOptionSpecified(
917 "Field atlantis_olympus can not be set when using RandomizedBuilder".to_string(),
918 )),
919 GameOptionsBuilderTypes::Seeded => Err(BuilderError::InvalidOptionSpecified(
920 "Field atlantis_olympus can not be set when using SeededBuilder".to_string(),
921 )),
922 GameOptionsBuilderTypes::Customized => {
923 self.atlantis_olympus = Some(atlantis_olympus);
924 Ok(self)
925 }
926 }
927 }
928
929 /// Sets the score for the case when Player Aleph chooses the second
930 /// choice and Player Beth chooses the first choice.
931 ///
932 /// This function sets the score for the case when Player Aleph chooses the
933 /// second (Olympus) choice and Player Beth chooses the first (Atlantis)
934 /// choice. This function is only valid for the
935 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized)
936 /// variant of the `GameOptionsBuilder` struct.
937 ///
938 /// # Arguments
939 ///
940 /// * `olympus_atlantis` - The score to set.
941 ///
942 /// # Example
943 ///
944 /// ## `RandomizedBuilder`
945 ///
946 /// ```
947 /// use dilemma_tactix_lib::{
948 /// GameOptionsBuilder,
949 /// GameOptionsBuilderTypes,
950 /// NumberPair,
951 /// };
952 ///
953 /// let game_options_builder =
954 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
955 /// .olympus_atlantis(NumberPair::new(5, 0));
956 ///
957 /// # assert!(game_options_builder.is_err());
958 /// ```
959 ///
960 /// ## `SeededBuilder`
961 ///
962 /// ```
963 /// use dilemma_tactix_lib::{
964 /// GameOptionsBuilder,
965 /// GameOptionsBuilderTypes,
966 /// NumberPair,
967 /// };
968 ///
969 /// let game_options_builder =
970 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
971 /// .olympus_atlantis(NumberPair::new(5, 0));
972 ///
973 /// # assert!(game_options_builder.is_err());
974 /// ```
975 ///
976 /// ## `CustomizedBuilder`
977 ///
978 /// ```
979 /// use dilemma_tactix_lib::{
980 /// GameOptionsBuilder,
981 /// GameOptionsBuilderTypes,
982 /// NumberPair,
983 /// };
984 ///
985 /// let game_options_builder =
986 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
987 /// .olympus_atlantis(NumberPair::new(5, 0));
988 ///
989 /// # assert!(game_options_builder.is_ok());
990 ///
991 /// let game_options = game_options_builder.unwrap().build();
992 ///
993 /// # assert_eq!(game_options.olympus_atlantis(), NumberPair::new(5, 0));
994 /// ```
995 ///
996 /// # Errors
997 ///
998 /// This function will return an error if the `builder_type` is
999 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
1000 /// or [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded).
1001 ///
1002 /// # Returns
1003 ///
1004 /// The `GameOptionsBuilder` struct with the `olympus_atlantis` field set.
1005 ///
1006 ///
1007 /// # See Also
1008 ///
1009 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
1010 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
1011 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
1012 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
1013 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
1014 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
1015 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
1016 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
1017 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
1018 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
1019 pub fn olympus_atlantis(mut self, olympus_atlantis: NumberPair) -> Result<Self, BuilderError> {
1020 match self.builder_type {
1021 GameOptionsBuilderTypes::Randomized => Err(BuilderError::InvalidOptionSpecified(
1022 "Field olympus_atlantis can not be set when using RandomizedBuilder".to_string(),
1023 )),
1024 GameOptionsBuilderTypes::Seeded => Err(BuilderError::InvalidOptionSpecified(
1025 "Field olympus_atlantis can not be set when using SeededBuilder".to_string(),
1026 )),
1027 GameOptionsBuilderTypes::Customized => {
1028 self.olympus_atlantis = Some(olympus_atlantis);
1029 Ok(self)
1030 }
1031 }
1032 }
1033
1034 /// Sets the score for the case when both players (Aleph and Beth) choose
1035 /// the second (Olympus) choice.
1036 ///
1037 /// This function sets the score for the case when both players choose the
1038 /// second (Olympus) choice. This function is only valid for the
1039 /// [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized)
1040 /// variant of the `GameOptionsBuilder` struct.
1041 ///
1042 /// # Arguments
1043 ///
1044 /// * `olympus_olympus` - The score to set.
1045 ///
1046 /// # Example
1047 ///
1048 /// ## `RandomizedBuilder`
1049 ///
1050 /// ```
1051 /// use dilemma_tactix_lib::{
1052 /// GameOptionsBuilder,
1053 /// GameOptionsBuilderTypes,
1054 /// NumberPair,
1055 /// };
1056 ///
1057 /// let game_options_builder =
1058 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1059 /// .olympus_olympus(NumberPair::new(3, 3));
1060 ///
1061 /// # assert!(game_options_builder.is_err());
1062 /// ```
1063 ///
1064 /// ## `SeededBuilder`
1065 ///
1066 /// ```
1067 /// use dilemma_tactix_lib::{
1068 /// GameOptionsBuilder,
1069 /// GameOptionsBuilderTypes,
1070 /// NumberPair,
1071 /// };
1072 ///
1073 /// let game_options_builder =
1074 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
1075 /// .olympus_olympus(NumberPair::new(3, 3));
1076 ///
1077 /// # assert!(game_options_builder.is_err());
1078 /// ```
1079 ///
1080 /// ## `CustomizedBuilder`
1081 ///
1082 /// ```
1083 /// use dilemma_tactix_lib::{
1084 /// GameOptionsBuilder,
1085 /// GameOptionsBuilderTypes,
1086 /// NumberPair,
1087 /// };
1088 ///
1089 /// let game_options_builder =
1090 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1091 /// .olympus_olympus(NumberPair::new(3, 3));
1092 ///
1093 /// # assert!(game_options_builder.is_ok());
1094 ///
1095 /// let game_options = game_options_builder.unwrap().build();
1096 ///
1097 /// # assert_eq!(game_options.olympus_olympus(), NumberPair::new(3, 3));
1098 /// ```
1099 ///
1100 /// # Errors
1101 ///
1102 /// This function will return an error if the `builder_type` is
1103 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
1104 /// or [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded).
1105 ///
1106 /// # Returns
1107 ///
1108 /// The `GameOptionsBuilder` struct with the `olympus_olympus` field set.
1109 ///
1110 ///
1111 /// # See Also
1112 ///
1113 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
1114 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
1115 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
1116 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
1117 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
1118 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
1119 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
1120 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
1121 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
1122 /// * [`GameOptionsBuilder::seed()`](GameOptionsBuilder::seed())
1123 pub fn olympus_olympus(mut self, olympus_olympus: NumberPair) -> Result<Self, BuilderError> {
1124 match self.builder_type {
1125 GameOptionsBuilderTypes::Randomized => Err(BuilderError::InvalidOptionSpecified(
1126 "Field olympus_olympus can not be set when using RandomizedBuilder".to_string(),
1127 )),
1128 GameOptionsBuilderTypes::Seeded => Err(BuilderError::InvalidOptionSpecified(
1129 "Field olympus_olympus can not be set when using SeededBuilder".to_string(),
1130 )),
1131 GameOptionsBuilderTypes::Customized => {
1132 self.olympus_olympus = Some(olympus_olympus);
1133 Ok(self)
1134 }
1135 }
1136 }
1137
1138 /// Sets the seed for the `GameOptions`.
1139 ///
1140 /// This function sets the seed for the `GameOptions` struct that is being
1141 /// built. This function is only valid for the
1142 /// [`GameOptionsBuilderTypes::Seeded`](GameOptionsBuilderTypes::Seeded)
1143 /// variant of the `GameOptionsBuilder` struct.
1144 ///
1145 /// # Arguments
1146 ///
1147 /// * `seed` - The seed for the `GameOptions`.
1148 ///
1149 /// # Example
1150 ///
1151 /// ## `RandomizedBuilder`
1152 ///
1153 /// ```
1154 /// use dilemma_tactix_lib::{
1155 /// GameOptionsBuilder,
1156 /// GameOptionsBuilderTypes,
1157 /// };
1158 ///
1159 /// let game_options_builder =
1160 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1161 /// .seed(123456789);
1162 ///
1163 /// # assert!(game_options_builder.is_err());
1164 /// ```
1165 ///
1166 /// ## `SeededBuilder`
1167 ///
1168 /// ```no_run
1169 /// use dilemma_tactix_lib::{
1170 /// GameOptionsBuilder,
1171 /// GameOptionsBuilderTypes,
1172 /// };
1173 ///
1174 /// let game_options_builder =
1175 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
1176 /// .seed(123456789);
1177 ///
1178 /// # assert!(game_options_builder.is_ok());
1179 /// ```
1180 ///
1181 /// ## `CustomizedBuilder`
1182 ///
1183 /// ```
1184 /// use dilemma_tactix_lib::{
1185 /// GameOptionsBuilder,
1186 /// GameOptionsBuilderTypes,
1187 /// };
1188 ///
1189 /// let game_options_builder =
1190 /// GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1191 /// .seed(123456789);
1192 ///
1193 /// # assert!(game_options_builder.is_err());
1194 /// ```
1195 ///
1196 /// # Errors
1197 ///
1198 /// This function will return an error if the `builder_type` is
1199 /// [`GameOptionsBuilderTypes::Randomized`](GameOptionsBuilderTypes::Randomized)
1200 /// or [`GameOptionsBuilderTypes::Customized`](GameOptionsBuilderTypes::Customized).
1201 ///
1202 /// # Returns
1203 ///
1204 /// The `GameOptionsBuilder` struct with the `seed` field set.
1205 ///
1206 /// # See Also
1207 ///
1208 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
1209 /// * [`GameOptionsBuilder::build()`](GameOptionsBuilder::build())
1210 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
1211 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
1212 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
1213 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
1214 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
1215 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
1216 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
1217 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
1218 pub fn seed(mut self, seed: u64) -> Result<Self, BuilderError> {
1219 match self.builder_type {
1220 GameOptionsBuilderTypes::Randomized => Err(BuilderError::InvalidOptionSpecified(
1221 "Field seed can not be set when using RandomizedBuilder".to_string(),
1222 )),
1223 GameOptionsBuilderTypes::Seeded => {
1224 self.seed = Some(seed);
1225 Ok(self)
1226 }
1227 GameOptionsBuilderTypes::Customized => Err(BuilderError::InvalidOptionSpecified(
1228 "Field seed can not be set when using CustomizedBuilder".to_string(),
1229 )),
1230 }
1231 }
1232
1233 /// Builds the `GameOptions` struct.
1234 ///
1235 /// # Returns
1236 ///
1237 /// A new `GameOptions` struct.
1238 ///
1239 /// # Panics
1240 ///
1241 /// This function will panic if any of the required fields are not set.
1242 ///
1243 /// # See Also
1244 ///
1245 /// * [`GameOptionsBuilder::new()`](GameOptionsBuilder::new())
1246 /// * [`GameOptionsBuilder::max_value()`](GameOptionsBuilder::max_value())
1247 /// * [`GameOptionsBuilder::min_value()`](GameOptionsBuilder::min_value())
1248 /// * [`GameOptionsBuilder::choice_atlantis()`](GameOptionsBuilder::choice_atlantis())
1249 /// * [`GameOptionsBuilder::choice_olympus()`](GameOptionsBuilder::choice_olympus())
1250 /// * [`GameOptionsBuilder::atlantis_atlantis()`](GameOptionsBuilder::atlantis_atlantis())
1251 /// * [`GameOptionsBuilder::atlantis_olympus()`](GameOptionsBuilder::atlantis_olympus())
1252 /// * [`GameOptionsBuilder::olympus_atlantis()`](GameOptionsBuilder::olympus_atlantis())
1253 /// * [`GameOptionsBuilder::olympus_olympus()`](GameOptionsBuilder::olympus_olympus())
1254 #[must_use]
1255 pub fn build(self) -> GameOptions {
1256 match self.builder_type {
1257 GameOptionsBuilderTypes::Randomized => self.build_randomized(),
1258 GameOptionsBuilderTypes::Seeded => self.build_seeded(),
1259 GameOptionsBuilderTypes::Customized => self.build_customized(),
1260 }
1261 }
1262
1263 fn build_customized(&self) -> GameOptions {
1264 let choice_atlantis = self.choice_atlantis.unwrap_or("cooperate");
1265 let choice_olympus = self.choice_olympus.unwrap_or("defect");
1266 let atlantis_atlantis = self.atlantis_atlantis.unwrap_or(NumberPair::new(4, 4));
1267 let atlantis_olympus = self.atlantis_olympus.unwrap_or(NumberPair::new(5, 0));
1268 let olympus_atlantis = self.olympus_atlantis.unwrap_or(NumberPair::new(0, 5));
1269 let olympus_olympus = self.olympus_olympus.unwrap_or(NumberPair::new(3, 3));
1270
1271 GameOptions {
1272 choice_atlantis,
1273 choice_olympus,
1274 atlantis_atlantis,
1275 atlantis_olympus,
1276 olympus_atlantis,
1277 olympus_olympus,
1278 }
1279 }
1280
1281 fn build_seeded(&self) -> GameOptions {
1282 todo!()
1283 }
1284
1285 fn build_randomized(&self) -> GameOptions {
1286 let min_value = self.min_value.unwrap_or(1);
1287 let max_value = self.max_value.unwrap_or(10);
1288
1289 let choice_atlantis = self.choice_atlantis.unwrap_or("cooperate");
1290 let choice_olympus = self.choice_olympus.unwrap_or("defect");
1291
1292 let atlantis_atlantis = NumberPair::random(min_value, max_value);
1293 let atlantis_olympus = NumberPair::random(min_value, max_value);
1294 let olympus_atlantis = NumberPair::random(min_value, max_value);
1295 let olympus_olympus = NumberPair::random(min_value, max_value);
1296
1297 GameOptions {
1298 choice_atlantis,
1299 choice_olympus,
1300 atlantis_atlantis,
1301 atlantis_olympus,
1302 olympus_atlantis,
1303 olympus_olympus,
1304 }
1305 }
1306}
1307
1308#[cfg(test)]
1309mod tests {
1310 use super::*;
1311
1312 #[test]
1313 fn test_new() {
1314 let game_options_builder_randomized =
1315 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1316 assert_eq!(
1317 game_options_builder_randomized.builder_type,
1318 GameOptionsBuilderTypes::Randomized
1319 );
1320 let game_options_builder_seeded = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1321 assert_eq!(
1322 game_options_builder_seeded.builder_type,
1323 GameOptionsBuilderTypes::Seeded
1324 );
1325 let game_options_builder_customized =
1326 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized);
1327 assert_eq!(
1328 game_options_builder_customized.builder_type,
1329 GameOptionsBuilderTypes::Customized
1330 );
1331 }
1332
1333 #[test]
1334 fn test_min_value() {
1335 let game_options_builder_randomized =
1336 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized).min_value(1);
1337 assert!(game_options_builder_randomized.is_ok());
1338 let game_options_builder_seeded =
1339 GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).min_value(1);
1340 assert!(game_options_builder_seeded.is_ok());
1341 let game_options_builder_customized =
1342 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized).min_value(1);
1343 assert!(game_options_builder_customized.is_err());
1344 }
1345
1346 #[test]
1347 fn test_max_value() {
1348 let game_options_builder_randomized =
1349 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized).max_value(10);
1350 assert!(game_options_builder_randomized.is_ok());
1351 let game_options_builder_seeded =
1352 GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).max_value(10);
1353 assert!(game_options_builder_seeded.is_ok());
1354 let game_options_builder_customized =
1355 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized).max_value(10);
1356 assert!(game_options_builder_customized.is_err());
1357 }
1358
1359 #[test]
1360 fn test_choice_atlantis() {
1361 let game_options_builder_randomized =
1362 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1363 .choice_atlantis("cooperate");
1364 assert!(game_options_builder_randomized.is_ok());
1365 let game_options_builder_seeded =
1366 GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).choice_atlantis("cooperate");
1367 assert!(game_options_builder_seeded.is_ok());
1368 let game_options_builder_customized =
1369 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1370 .choice_atlantis("cooperate");
1371 assert!(game_options_builder_customized.is_ok());
1372 }
1373
1374 #[test]
1375 fn test_choice_olympus() {
1376 let game_options_builder_randomized =
1377 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized).choice_olympus("defect");
1378 assert!(game_options_builder_randomized.is_ok());
1379 let game_options_builder_seeded =
1380 GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).choice_olympus("defect");
1381 assert!(game_options_builder_seeded.is_ok());
1382 let game_options_builder_customized =
1383 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized).choice_olympus("defect");
1384 assert!(game_options_builder_customized.is_ok());
1385 }
1386
1387 #[test]
1388 fn test_atlantis_atlantis() {
1389 let game_options_builder_randomized =
1390 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1391 .atlantis_atlantis(NumberPair::new(1, 1));
1392 assert!(game_options_builder_randomized.is_err());
1393 let game_options_builder_seeded = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
1394 .atlantis_atlantis(NumberPair::new(1, 1));
1395 assert!(game_options_builder_seeded.is_err());
1396 let game_options_builder_customized =
1397 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1398 .atlantis_atlantis(NumberPair::new(1, 1));
1399 assert!(game_options_builder_customized.is_ok());
1400 }
1401
1402 #[test]
1403 fn test_atlantis_olympus() {
1404 let game_options_builder_randomized =
1405 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1406 .atlantis_olympus(NumberPair::new(1, 1));
1407 assert!(game_options_builder_randomized.is_err());
1408 let game_options_builder_seeded = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
1409 .atlantis_olympus(NumberPair::new(1, 1));
1410 assert!(game_options_builder_seeded.is_err());
1411 let game_options_builder_customized =
1412 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1413 .atlantis_olympus(NumberPair::new(1, 1));
1414 assert!(game_options_builder_customized.is_ok());
1415 }
1416
1417 #[test]
1418 fn test_olympus_atlantis() {
1419 let game_options_builder_randomized =
1420 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1421 .olympus_atlantis(NumberPair::new(1, 1));
1422 assert!(game_options_builder_randomized.is_err());
1423 let game_options_builder_seeded = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
1424 .olympus_atlantis(NumberPair::new(1, 1));
1425 assert!(game_options_builder_seeded.is_err());
1426 let game_options_builder_customized =
1427 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1428 .olympus_atlantis(NumberPair::new(1, 1));
1429 assert!(game_options_builder_customized.is_ok());
1430 }
1431
1432 #[test]
1433 fn test_olympus_olympus() {
1434 let game_options_builder_randomized =
1435 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized)
1436 .olympus_olympus(NumberPair::new(1, 1));
1437 assert!(game_options_builder_randomized.is_err());
1438 let game_options_builder_seeded = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded)
1439 .olympus_olympus(NumberPair::new(1, 1));
1440 assert!(game_options_builder_seeded.is_err());
1441 let game_options_builder_customized =
1442 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized)
1443 .olympus_olympus(NumberPair::new(1, 1));
1444 assert!(game_options_builder_customized.is_ok());
1445 }
1446
1447 #[test]
1448 fn test_seed() {
1449 let game_options_builder_randomized =
1450 GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized).seed(123456789);
1451 assert!(game_options_builder_randomized.is_err());
1452 let game_options_builder_seeded =
1453 GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded).seed(123456789);
1454 assert!(game_options_builder_seeded.is_ok());
1455 let game_options_builder_customized =
1456 GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized).seed(123456789);
1457 assert!(game_options_builder_customized.is_err());
1458 }
1459
1460 #[test]
1461 fn test_build_randomized() -> Result<(), BuilderError> {
1462 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1463 let builder = builder.min_value(1);
1464 assert!(builder.is_ok());
1465 let builder = builder?.max_value(10);
1466 assert!(builder.is_ok());
1467 let builder = builder?.choice_atlantis("cooperate");
1468 assert!(builder.is_ok());
1469 let builder = builder?.choice_olympus("defect");
1470 assert!(builder.is_ok());
1471 let game_options = builder?.build();
1472
1473 assert_eq!(game_options.choice_atlantis(), "cooperate");
1474 assert_eq!(game_options.choice_olympus(), "defect");
1475
1476 Ok(())
1477 }
1478
1479 #[test]
1480 #[ignore = "Seeded is not yet implemented"]
1481 fn test_build_seeded() -> Result<(), BuilderError> {
1482 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1483 let builder = builder.min_value(1);
1484 assert!(builder.is_ok());
1485 let builder = builder?.max_value(10);
1486 assert!(builder.is_ok());
1487 let builder = builder?.choice_atlantis("cooperate");
1488 assert!(builder.is_ok());
1489 let builder = builder?.choice_olympus("defect");
1490 assert!(builder.is_ok());
1491 let builder = builder?.seed(123456789);
1492 assert!(builder.is_ok());
1493 let game_options = builder?.build();
1494
1495 assert_eq!(game_options.choice_atlantis(), "cooperate");
1496 assert_eq!(game_options.choice_olympus(), "defect");
1497
1498 Ok(())
1499 }
1500
1501 #[test]
1502 fn test_build_customized() -> Result<(), BuilderError> {
1503 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized);
1504 let builder = builder.choice_atlantis("cooperate");
1505 assert!(builder.is_ok());
1506 let builder = builder?.choice_olympus("defect");
1507 assert!(builder.is_ok());
1508 let builder = builder?.atlantis_atlantis(NumberPair::new(1, 1));
1509 assert!(builder.is_ok());
1510 let builder = builder?.atlantis_olympus(NumberPair::new(1, 1));
1511 assert!(builder.is_ok());
1512 let builder = builder?.olympus_atlantis(NumberPair::new(1, 1));
1513 assert!(builder.is_ok());
1514 let builder = builder?.olympus_olympus(NumberPair::new(1, 1));
1515 assert!(builder.is_ok());
1516 let game_options = builder?.build();
1517
1518 assert_eq!(game_options.choice_atlantis(), "cooperate");
1519 assert_eq!(game_options.choice_olympus(), "defect");
1520
1521 Ok(())
1522 }
1523
1524 #[test]
1525 fn test_build_randomized_missing_min_value() {
1526 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1527 let builder = builder.max_value(10);
1528 assert!(builder.is_ok());
1529 let builder = builder.unwrap().choice_atlantis("cooperate");
1530 assert!(builder.is_ok());
1531 let builder = builder.unwrap().choice_olympus("defect");
1532 assert!(builder.is_ok());
1533 let game_options = builder.unwrap().build();
1534
1535 assert_eq!(game_options.choice_atlantis(), "cooperate");
1536 assert_eq!(game_options.choice_olympus(), "defect");
1537 }
1538
1539 #[test]
1540 fn test_build_randomized_missing_max_value() {
1541 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1542 let builder = builder.min_value(1);
1543 assert!(builder.is_ok());
1544 let builder = builder.unwrap().choice_atlantis("cooperate");
1545 assert!(builder.is_ok());
1546 let builder = builder.unwrap().choice_olympus("defect");
1547 assert!(builder.is_ok());
1548 let game_options = builder.unwrap().build();
1549
1550 assert_eq!(game_options.choice_atlantis(), "cooperate");
1551 assert_eq!(game_options.choice_olympus(), "defect");
1552 }
1553
1554 #[test]
1555 fn test_build_randomized_missing_choice_atlantis() {
1556 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1557 let builder = builder.min_value(1);
1558 assert!(builder.is_ok());
1559 let builder = builder.unwrap().max_value(10);
1560 assert!(builder.is_ok());
1561 let builder = builder.unwrap().choice_olympus("defect");
1562 assert!(builder.is_ok());
1563 let game_options = builder.unwrap().build();
1564
1565 assert_eq!(game_options.choice_atlantis(), "cooperate");
1566 assert_eq!(game_options.choice_olympus(), "defect");
1567 }
1568
1569 #[test]
1570 fn test_build_randomized_missing_choice_olympus() {
1571 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1572 let builder = builder.min_value(1);
1573 assert!(builder.is_ok());
1574 let builder = builder.unwrap().max_value(10);
1575 assert!(builder.is_ok());
1576 let builder = builder.unwrap().choice_atlantis("cooperate");
1577 assert!(builder.is_ok());
1578 let game_options = builder.unwrap().build();
1579
1580 assert_eq!(game_options.choice_atlantis(), "cooperate");
1581 assert_eq!(game_options.choice_olympus(), "defect");
1582 }
1583
1584 #[test]
1585 #[ignore = "Seeded build is not yet implemented"]
1586 fn test_build_seeded_missing_min_value() {
1587 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1588 let builder = builder.max_value(10);
1589 assert!(builder.is_ok());
1590 let builder = builder.unwrap().choice_atlantis("cooperate");
1591 assert!(builder.is_ok());
1592 let builder = builder.unwrap().choice_olympus("defect");
1593 assert!(builder.is_ok());
1594 let builder = builder.unwrap().seed(123456789);
1595 assert!(builder.is_ok());
1596 let game_options = builder.unwrap().build();
1597
1598 assert_eq!(game_options.choice_atlantis(), "cooperate");
1599 assert_eq!(game_options.choice_olympus(), "defect");
1600 }
1601
1602 #[test]
1603 #[ignore = "Seeded is not yet implemented"]
1604 fn test_build_seeded_missing_max_value() {
1605 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1606 let builder = builder.min_value(1);
1607 assert!(builder.is_ok());
1608 let builder = builder.unwrap().choice_atlantis("cooperate");
1609 assert!(builder.is_ok());
1610 let builder = builder.unwrap().choice_olympus("defect");
1611 assert!(builder.is_ok());
1612 let builder = builder.unwrap().seed(123456789);
1613 assert!(builder.is_ok());
1614 let game_options = builder.unwrap().build();
1615
1616 assert_eq!(game_options.choice_atlantis(), "cooperate");
1617 assert_eq!(game_options.choice_olympus(), "defect");
1618 }
1619
1620 #[test]
1621 #[ignore = "Seeded is not yet implemented"]
1622 fn test_build_seeded_missing_choice_atlantis() {
1623 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1624 let builder = builder.min_value(1);
1625 assert!(builder.is_ok());
1626 let builder = builder.unwrap().max_value(10);
1627 assert!(builder.is_ok());
1628 let builder = builder.unwrap().choice_olympus("defect");
1629 assert!(builder.is_ok());
1630 let builder = builder.unwrap().seed(123456789);
1631 assert!(builder.is_ok());
1632 let game_options = builder.unwrap().build();
1633
1634 assert_eq!(game_options.choice_atlantis(), "cooperate");
1635 assert_eq!(game_options.choice_olympus(), "defect");
1636 }
1637
1638 #[test]
1639 #[ignore = "Seeded is not yet implemented"]
1640 fn test_build_seeded_missing_choice_olympus() {
1641 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1642 let builder = builder.min_value(1);
1643 assert!(builder.is_ok());
1644 let builder = builder.unwrap().max_value(10);
1645 assert!(builder.is_ok());
1646 let builder = builder.unwrap().choice_atlantis("cooperate");
1647 assert!(builder.is_ok());
1648 let builder = builder.unwrap().seed(123456789);
1649 assert!(builder.is_ok());
1650 let game_options = builder.unwrap().build();
1651
1652 assert_eq!(game_options.choice_atlantis(), "cooperate");
1653 assert_eq!(game_options.choice_olympus(), "defect");
1654 }
1655
1656 #[test]
1657 #[ignore = "Seeded is not yet implemented"]
1658 fn test_build_seeded_missing_seed() {
1659 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1660 let builder = builder.min_value(1);
1661 assert!(builder.is_ok());
1662 let builder = builder.unwrap().max_value(10);
1663 assert!(builder.is_ok());
1664 let builder = builder.unwrap().choice_atlantis("cooperate");
1665 assert!(builder.is_ok());
1666 let builder = builder.unwrap().choice_olympus("defect");
1667 assert!(builder.is_ok());
1668 let game_options = builder.unwrap().build();
1669
1670 assert_eq!(game_options.choice_atlantis(), "cooperate");
1671 assert_eq!(game_options.choice_olympus(), "defect");
1672 }
1673
1674 #[test]
1675 #[should_panic]
1676 fn test_build_randomized_seed_panic() {
1677 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1678 let builder = builder.seed(123456789);
1679 assert!(builder.is_err());
1680 builder.unwrap();
1681 }
1682
1683 #[test]
1684 #[should_panic]
1685 fn test_build_randomized_atlantis_atlantis_panic() {
1686 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1687 let builder = builder.atlantis_atlantis(NumberPair::new(1, 1));
1688 assert!(builder.is_err());
1689 builder.unwrap();
1690 }
1691
1692 #[test]
1693 #[should_panic]
1694 fn test_build_randomized_atlantis_olympus_panic() {
1695 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1696 let builder = builder.atlantis_olympus(NumberPair::new(1, 1));
1697 assert!(builder.is_err());
1698 builder.unwrap();
1699 }
1700
1701 #[test]
1702 #[should_panic]
1703 fn test_build_randomized_olympus_atlantis_panic() {
1704 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1705 let builder = builder.olympus_atlantis(NumberPair::new(1, 1));
1706 assert!(builder.is_err());
1707 builder.unwrap();
1708 }
1709
1710 #[test]
1711 #[should_panic]
1712 fn test_build_randomized_olympus_olympus_panic() {
1713 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Randomized);
1714 let builder = builder.olympus_olympus(NumberPair::new(1, 1));
1715 assert!(builder.is_err());
1716 builder.unwrap();
1717 }
1718
1719 #[test]
1720 #[should_panic]
1721 fn test_build_seeded_atlantis_atlantis_panic() {
1722 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1723 let builder = builder.atlantis_atlantis(NumberPair::new(1, 1));
1724 assert!(builder.is_err());
1725 builder.unwrap();
1726 }
1727
1728 #[test]
1729 #[should_panic]
1730 fn test_build_seeded_atlantis_olympus_panic() {
1731 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1732 let builder = builder.atlantis_olympus(NumberPair::new(1, 1));
1733 assert!(builder.is_err());
1734 builder.unwrap();
1735 }
1736
1737 #[test]
1738 #[should_panic]
1739 fn test_build_seeded_olympus_atlantis_panic() {
1740 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1741 let builder = builder.olympus_atlantis(NumberPair::new(1, 1));
1742 assert!(builder.is_err());
1743 builder.unwrap();
1744 }
1745
1746 #[test]
1747 #[should_panic]
1748 fn test_build_seeded_olympus_olympus_panic() {
1749 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Seeded);
1750 let builder = builder.olympus_olympus(NumberPair::new(1, 1));
1751 assert!(builder.is_err());
1752 builder.unwrap();
1753 }
1754
1755 #[test]
1756 #[should_panic]
1757 fn test_build_customized_seed_panic() {
1758 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized);
1759 let builder = builder.seed(123456789);
1760 assert!(builder.is_err());
1761 builder.unwrap();
1762 }
1763
1764 #[test]
1765 #[should_panic]
1766 fn test_build_customized_min_value_panic() {
1767 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized);
1768 let builder = builder.min_value(1);
1769 assert!(builder.is_err());
1770 builder.unwrap();
1771 }
1772
1773 #[test]
1774 #[should_panic]
1775 fn test_build_customized_max_value_panic() {
1776 let builder = GameOptionsBuilder::new(GameOptionsBuilderTypes::Customized);
1777 let builder = builder.max_value(10);
1778 assert!(builder.is_err());
1779 builder.unwrap();
1780 }
1781}