aboutsummaryrefslogtreecommitdiff
path: root/motus/js/initialize.ml
blob: 82f1288cb3b0e1c7ebd51689bd87374a4657af71 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
open StdLabels
open Note
open Motus_lib
open Brr

type t =
  { length : int
  ; content : (int * Jstr.t, Jv.Error.t) result
  ; sender : (int * Jstr.t * Validity.t) E.send
  ; proposition : State.proposition
  }

(** Pick the next word from the dictionnary, and return it as a proposition. 

    If the word is empty (no word) return [None], else return a proposition
    which can be edited by the user. 

    The rule list is used to identify the letter already fixed by the previous
    results. *)
let get_proposition : Wordlist.t -> Criteria.t list -> State.proposition option
    =
 fun analysis rules ->
  let word =
    Wordlist.extract_freq analysis |> Wordlist.pick_next_word analysis |> fst
  in
  match String.equal String.empty word with
  | true -> None
  | false ->
      let i = ref 0 in
      let proposition =
        word
        |> String.to_seq
        |> Seq.map (fun c ->
               let wellplaced =
                 List.exists rules ~f:(function
                     | Motus_lib.Criteria.Contain (_, Some i') when !i = i' ->
                         true
                     | _ -> false )
               in
               incr i;
               let validity =
                 match wellplaced with
                 | true -> Validity.Wellplaced
                 | _ -> Validity.Missing
               in

               Some (Jstr.of_char c, validity) )
        |> List.of_seq
      in
      Some proposition


let process { sender; length; content; proposition } state =
  match content with
  | Ok (200, value) ->
      let rules =
        Criteria.Lenght length :: State.get_current_rules proposition
      in
      let words = Jstr.cuts ~sep:(Jstr.v "\n") value in
      let analysis =
        List.fold_left
          ~f:(fun a w ->
            let upper = Jstr.uppercased w in
            Wordlist.add_word rules a (Jstr.to_string upper) )
          ~init:(Wordlist.empty_data ())
          words
      in
      let current_prop = get_proposition analysis rules
      and fields = FieldList.make length sender in
      ( match current_prop with
      | None -> state
      | Some prop ->
          FieldList.set_with_props prop fields rules;

          State.
            { analysis
            ; rules
            ; length
            ; current_prop = prop
            ; propositions = []
            ; fields
            } )
  | _ ->
      Console.(log [ Jstr.v "No words found" ]);
      state