Updated answer
As a follow up question, can we apply a different strategy for distinguishing the words? For example, adding a frame instead of coloring them.
Answering the follow up question does bring better looking and easier to read results:
aResFr =
findwords[str, CommonWordQ,
<|Horizontal -> (Framed[Style[#, Blue, Bold],
Background -> Yellow] &),
Vertical -> (Framed[Style[#, Red], Background -> LightBlue] &),
Diagonal -> (Framed[Style[#, Purple, Bold],
Background -> GrayLevel[0.9]] &)|>];
Grid[#, Dividers -> All] & /@ aResFr

Grid[CombineHighlights[aResFr], Dividers -> All]

The update definitions below are based on the definitions of the first answer with some relatively small code refactoring. The function signatures have to be "relaxed" to take "highlighter function" as an argument.
Definitions
(*Declare the minimum length of a word*)
minWordLength = 3;
ClearAll[substrings];
substrings[str_String, len_ : minWordLength] :=
Block[{r = StringLength[str]},
Join @@ Table[StringTake[str, {i, j}], {i, r + 1}, {j, i + len - 1, r}]
];
ClearAll[wordsFinder];
wordsFinder[str_String, dictWordFunc_ : DictionaryWordQ,
highlighterFunc_ : (Style[#, Red] &)] :=
Block[{pos, res},
pos = Union @@ (Range @@ (Flatten[#, 1] &)@StringPosition[str, #] & /@
Select[substrings[str], dictWordFunc[#, IgnoreCase -> True] &]);
MapIndexed[If[MemberQ[pos, First@#2], highlighterFunc[#], #] &,
Characters@str]
];
ClearAll[highlightsDiag];
highlightsDiag[str_String, dictWordFunc_ : DictionaryWordQ,
highlighterFunc_ : (Style[#, Red] &)] :=
Block[{matChars, n, matInds, res},
matChars = Partition[Characters@str, Sqrt[StringLength[str]]];
n = Length[matChars];
matInds = Table[{i, j}, {i, n}, {j, n}];
res = Table[
AssociationThread[Diagonal[matInds, i],
wordsFinder[StringJoin @@ Diagonal[matChars, i], dictWordFunc,
highlighterFunc]], {i, -n + 1, n - 1}];
Normal[SparseArray[Normal[Join @@ res]]]
];
ClearAll[highlights];
highlights[str_String, dir_, dictWordFunc_ : DictionaryWordQ,
highlighterFunc_ : (Style[#, Red] &)] :=
Block[{matChars, n, matInds, res},
matChars = Partition[Characters@str, Sqrt[StringLength[str]]];
If[TrueQ[dir === Vertical],
matChars = Transpose[matChars]
];
n = Length[matChars];
matInds = Table[{i, j}, {i, n}, {j, n}];
res = Table[
AssociationThread[matInds[[i]],
wordsFinder[StringJoin @@ matChars[[i]], dictWordFunc,
highlighterFunc]], {i, n}];
res = Normal[SparseArray[Normal[Join @@ res]]];
If[TrueQ[dir === Vertical],
Transpose[res],
(ELSE)
res
]
] /; MemberQ[{Vertical, Horizontal}, dir];
ClearAll[findwords];
findwords[table_, dictWordFunc_ : DictionaryWordQ,
highlighterFunc_ : (Style[#, Red] &), opts : OptionsPattern[]] :=
Block[{str},
str = If[MatrixQ[table], StringJoin @@ Flatten[table], table];
str = ToUpperCase[str];
<|
"Horizontal" ->
highlights[str, Horizontal, dictWordFunc,
If[AssociationQ[highlighterFunc], highlighterFunc[Horizontal],
highlighterFunc]],
"Vertical" ->
highlights[str, Vertical, dictWordFunc,
If[AssociationQ[highlighterFunc], highlighterFunc[Vertical],
highlighterFunc]],
"Diagonal" ->
highlightsDiag[str, dictWordFunc,
If[AssociationQ[highlighterFunc], highlighterFunc[Diagonal],
highlighterFunc]]
|>
] /; (SquareMatrixQ[table] || StringQ[table]);
Clear[CombineHighlights];
CombineHighlights[aTbls_Association] :=
Map[If[VectorQ[#, StringQ], First[#], Last@Select[#, Not@*StringQ]] &,
Transpose[Values[aTbls], {3, 1, 2}], {2}];
Clear[CommonWordQ];
aCommonWords =
AssociationThread[ToLowerCase@Union[RandomWord["CommonWords", 10^6]],
True];
CommonWordQ[w_String, opts : OptionsPattern[]] :=
Lookup[aCommonWords, ToLowerCase@w, False];
First answer
Here are brief descriptions of my way of answering OP's questions:
We can define CommonWordQ function based on RandomWord["CommonWords"].
One way to do it is to refactor OP's code:
Diagonal words highlights are similar to the horizontal and vertical words highlights finding, but using Diagonal instead of Part.
Note, that:
I tried to reuse OP's code, as much as possible.
I combine the tables into one, but the results are hard to read.
Further refactoring can put other Style element, not just color.
The refactored functions take as arguments: string, is-it-a-word function, and color (or an association of colors).
Definitions
(*Declare the minimum length of a word*)
minWordLength = 3;
ClearAll[substrings];
substrings[str_String, len_ : minWordLength] :=
Block[{r = StringLength[str]},
Join @@
Table[StringTake[str, {i, j}], {i, r + 1}, {j, i + len - 1, r}]
];
ClearAll[wordsFinder];
wordsFinder[str_String, dictWordFunc_ : DictionaryWordQ, color_ : Red] :=
Block[{pos, res},
pos =
Union @@ (Range @@ (Flatten[#, 1] &)@StringPosition[str, #] & /@
Select[substrings[str],
dictWordFunc[#, IgnoreCase -> True] &]);
MapIndexed[If[MemberQ[pos, First@#2], Style[#, color], #] &,
Characters@str]
] /; ColorQ[color];
ClearAll[highlightsDiag];
highlightsDiag[str_String, dictWordFunc_ : DictionaryWordQ, color_ : Red] :=
Block[{matChars, n, matInds, res},
matChars = Partition[Characters@str, Sqrt[StringLength[str]]];
n = Length[matChars];
matInds = Table[{i, j}, {i, n}, {j, n}];
res =
Table[AssociationThread[Diagonal[matInds, i],
wordsFinder[StringJoin @@ Diagonal[matChars, i], dictWordFunc,
color]], {i, -n + 1, n - 1}];
Normal[SparseArray[Normal[Join @@ res]]]
] /; ColorQ[color];
ClearAll[highlights];
highlights[str_String, dir_, dictWordFunc_ : DictionaryWordQ, color_ : Red] :=
Block[{matChars, n, matInds, res},
matChars = Partition[Characters@str, Sqrt[StringLength[str]]];
If[TrueQ[dir === Vertical],
matChars = Transpose[matChars]
];
n = Length[matChars];
matInds = Table[{i, j}, {i, n}, {j, n}];
res =
Table[AssociationThread[matInds[[i]],
wordsFinder[StringJoin @@ matChars[[i]], dictWordFunc,
color]], {i, n}];
res = Normal[SparseArray[Normal[Join @@ res]]];
If[TrueQ[dir === Vertical],
Transpose[res],
(ELSE)
res
]
] /; MemberQ[{Vertical, Horizontal}, dir] && ColorQ[color];
ClearAll[findwords];
findwords[table_, dictWordFunc_ : DictionaryWordQ, color_ : Red, opts : OptionsPattern[]] :=
Block[{str},
str = If[MatrixQ[table], StringJoin @@ Flatten[table], table];
str = ToUpperCase[str];
<|
"Horizontal" ->
highlights[str, Horizontal, dictWordFunc,
If[ColorQ[color], color, color[1]]],
"Vertical" ->
highlights[str, Vertical, dictWordFunc,
If[ColorQ[color], color, color[2]]],
"Diagonals" ->
highlightsDiag[str, dictWordFunc,
If[ColorQ[color], color, color[3]]]
|>
] /; (SquareMatrixQ[table] || StringQ[table]);
Clear[CombineHighlights];
CombineHighlights[aTbls_Association] :=
Map[If[VectorQ[#, StringQ], First[#],
Last@Select[#, Head[#] === Style &]] &,
Transpose[Values[aTbls], {3, 1, 2}], {2}];
Clear[CommonWordQ];
aCommonWords = AssociationThread[ToLowerCase@Union[RandomWord["CommonWords", 10^6]], True];
CommonWordQ[w_String, opts : OptionsPattern[]] := Lookup[aCommonWords, ToLowerCase@w, False];
Tables for dictionary words
str = StringJoin@RandomChoice[CharacterRange["a", "z"], 256];
Grid[#, Dividers -> All] & /@ findwords[str, DictionaryWordQ, Red]

Tables for common words
Grid[#, Dividers -> All] & /@ findwords[str, CommonWordQ, Red]

Combining the tables
Combining the tables does not look that good (in my opinion):
aRes3 = findwords[str, CommonWordQ, <|1 -> Red, 2 -> Blue, 3 -> Green|>];
Grid[CombineHighlights[aRes3], Dividers -> All]

Diagonal[]? – J. M.'s missing motivation Jan 02 '21 at 18:50CommonWordQas in Anton’s answer. – C. E. Jan 03 '21 at 08:26CommonWordQdoes. Anyway, the point is that the word search part is solved in that question already. Columns, rows, diagonals, reversed words, all that is implemented there. If it can be shown that performance is a problem then it would make a great new question to take one of the solutions and ask how it can be made more efficient for all of the English language. But as it stands this question has a very big overlap with that other question, enough that I would call it a duplicate question. – C. E. Jan 03 '21 at 09:41CommonWordQdoes not do that – polfosol Jan 03 '21 at 10:08