colorMap = <| 1 -> RGBColor[106/255, 170/255, 100/255], 0 -> RGBColor[201/255, 180/255, 80/255], -1 -> RGBColor[134/255, 136/255, 138/255] |>;
tag[word_, target_] := 
  With[{sc = Characters[word], tc = Characters[target]}, 
   With[{neq = Select[Range[5], sc[[#]] != tc[[#]] &]},
    Table[
     Which[sc[[i]] == tc[[i]], 1, 
      MemberQ[tc[[neq]], sc[[i]]] && 
       Length[Position[sc[[neq]][[;; Position[neq, i][[1, 1]]]], 
          sc[[i]]]] <= Length[Position[tc[[neq]], sc[[i]]]], 0, 
      True, -1], {i, 5}]]];
WordlePlot[ss_List, target_] := Column[WordlePlot[#, target] & /@ ss];
WordlePlot[s_String, target_] := 
  With[{sc = Characters[s], tc = Characters[target], colors = colorMap /@ tag[s, target]},
    Row[Table[
      Graphics[{colors[[i]], Rectangle[], White, 
        Text[Style[sc[[i]], FontSize -> 48, 
          FontFamily -> "Clear Sans", Bold, White], {.5, .5}]}], {i, 
       5}]]
   ];

WordlePlot[{"STARE", "CLEAN", "FADED", "ABBEY"}, "ABBEY"]

words = ToUpperCase /@ Select[WordList["KnownWords"], 
    StringLength[#] == 5 && AllTrue[Characters[#], x |-> MemberQ[CharacterRange["a", "z"], x]] &];
chardata = Association[Rule @@@ ReverseSortBy[Tally@Flatten@Characters@words, Last]];

BarChart[Labeled[#2, 
    Style[#1, FontSize -> 24, FontFamily -> "Clear Sans"], Before] & @@@
   Reverse@Take[Normal@chardata, 15], BarSpacing -> 0, 
 BarOrigin -> Left, Axes -> False, ImageSize -> 600]

score[word_] := Total[chardata /@ Union[Characters[word]]]
scores = {#, score[#]} & /@ words;

TableForm[
 Style[First[#] <> "    (" <> ToString[Last[#]] <> ")", 
    FontSize -> 24, FontFamily -> "Courier New"] & /@ 
  Take[ReverseSortBy[scores, Last], 15], 
 TableHeadings -> {Style[#, FontSize -> 24, 
      FontFamily -> "Courier New"] & /@ Range[15], {}}]

guessData[guesses_, target_] := AssociationMap[w |-> tag[w, target], guesses];
gd = guessData[{"STARE", "CLEAN"}, "ABBEY"]

candidates[guessData_, words_] := Select[words, candidate |-> AllTrue[Keys @ guessData, tag[#, candidate] == guessData[#] &]]
candidates[gd, words]

maxRemaining[start_, words_] := 
 Last@SortBy[Table[{tup, Length[candidates[<|start -> tup|>, words]]}, {tup, Tuples[{-1, 0, 1}, 5]}], Last]

Length[words]
maxRemaining["STARE", words]
maxRemaining["ORATE", words]

Length[candidates[<| "ORATE" -> {-1, -1, -1, -1, -1} |>, words]]

maxRemaining[start_, words_] := 
 Last@SortBy[Table[{tup, Length[candidates[<|start -> tup|>, words]]}, {tup, Tuples[{-1, 0}, 5]}], Last]

contestants = First /@ Take[ReverseSortBy[scores, Last], 30];
ranking[cs_, words_] := With[{data = SortBy[
   Table[With[{mr = maxRemaining[w, words]}, {WordlePlot[w, 
       First@candidates[<|w -> mr[[1]]|>, words]], 
      Style[mr[[2]], FontSize -> 36, 
       FontFamily -> "Clear Sans"]}], {w, cs}], Last]},
TableForm[data[[;;5]], TableSpacing -> {5, 10}, 
 TableHeadings -> {(Style["#" <> ToString@#, 24, 
       FontFamily -> "Clear Sans"] & /@ Range[5]), None}]
];

ranking[contestants, words]

nonOverlapping[w1_, w2_] := 
  Length[Intersection[Characters[w1], Characters[w2]]] == 0;
grayScore[w_, words_] := Length[Select[words, nonOverlapping[#, w] &]];
newContestants = SortBy[words, grayScore[#, words] &][[;; 30]];

newContestants[[;;5]]

ranking[newContestants, words]

raiseWords = candidates[<| "RAISE" -> {-1, -1, -1, -1, -1} |>, words];

raiseContestants = SortBy[raiseWords, grayScore[#, raiseWords] &][[;; 30]];

ranking[raiseContestants, raiseWords]

raiseHotlyWords = 
  candidates[<|"HOTLY" -> {-1, 0, -1, 0, -1}|>, raiseWords];

ranking[words_] := With[{data = SortBy[
         Table[
       With[{mr = 
          Last@SortBy[
            Table[{w2, 
              Length[candidates[<|w -> tag[w, w2]|>, words]]}, {w2, 
              words}], Last]}, {WordlePlot[w, 
                mr[[1]]], 
               Style[mr[[2]], FontSize -> 36, 
                 FontFamily -> "Clear Sans"]}], {w, words}], Last]},
   TableForm[data[[;; 4]], TableSpacing -> {5, 10}, 
     TableHeadings -> {(Style["#" <> ToString@#, 24, 
                 FontFamily -> "Clear Sans"] & /@ Range[5]), None}]
   ];

ranking[raiseHotlyWords]

raiseHotlyBlockWords = 
  candidates[<|"BLOCK" -> {1, 1, 1, -1, -1}|>, raiseHotlyWords];
ranking[raiseHotlyBlockWords]

WordlePlot[{"RAISE", "HOTLY", "BLOCK", "BLOOD", "BLOWN"}, "BLOWN"]