You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

132 lines
3.9 KiB

7 years ago
  1. #!/usr/bin/python3
  2. import argparse
  3. from string import ascii_lowercase
  4. import cmd2
  5. import re
  6. import os
  7. from candidates import candidates, filter_possibilities
  8. from dictionary import DEFAULT, ALTERNATE
  9. from word_remove_dialog import RemoveWordsActivity
  10. LOWERCASE = set(ascii_lowercase)
  11. DICTS = {"default": DEFAULT, "alt": ALTERNATE}
  12. # argparsers
  13. dictionary_manage_parser = argparse.ArgumentParser()
  14. commands = dictionary_manage_parser.add_mutually_exclusive_group()
  15. commands.add_argument(
  16. "-l", "--list", action="store_true", help="List available dictionaries"
  17. )
  18. commands.add_argument("-s", "--switch", help="Dictionary to swap to")
  19. letter_set_manage = argparse.ArgumentParser()
  20. letter_set_manage.add_argument("letter", nargs="+")
  21. guessing = argparse.ArgumentParser()
  22. guessing.add_argument("pattern", help="Pattern to match")
  23. hide_exclude = argparse.ArgumentParser()
  24. commands = hide_exclude.add_mutually_exclusive_group()
  25. commands.add_argument(
  26. "-e",
  27. "--edit",
  28. help="Change which words will be hidden from view",
  29. action="store_true",
  30. )
  31. commands.add_argument(
  32. "-c", "--commit", help="Move excluded words to be hidden words", action="store_true"
  33. )
  34. commands.add_argument(
  35. "-s",
  36. "--show",
  37. help="Show which words are in the current exclude list",
  38. action="store_true",
  39. )
  40. class MainLoop(cmd2.Cmd):
  41. """Loop for wordscape commands
  42. """
  43. prompt = "<{}> $ "
  44. def __init__(self):
  45. self.dict = "default"
  46. self.excludes = set()
  47. self.hidden = set()
  48. self.init_letters(input("Enter letters: "))
  49. super().__init__()
  50. def init_letters(self, letters):
  51. if not isinstance(letters, str):
  52. letters = "".join(letters)
  53. letters = letters.lower()
  54. self.letters = [l for l in letters if l in LOWERCASE]
  55. self.prompt = MainLoop.prompt.format(", ".join(self.letters))
  56. self.candidates = candidates(self.letters, DICTS[self.dict], self.excludes)
  57. @cmd2.with_argparser(dictionary_manage_parser)
  58. def do_dict(self, args):
  59. """list/switch dict"""
  60. if args.list:
  61. print(
  62. "\n".join(
  63. (
  64. "{} {}".format("*" if key == self.dict else " ", key)
  65. for key in DICTS.keys()
  66. )
  67. )
  68. )
  69. else:
  70. DICTS[args.switch]
  71. self.dict = args.switch
  72. @cmd2.with_argparser(letter_set_manage)
  73. def do_change_letters(self, args):
  74. """Change the letters on the board"""
  75. self.init_letters(args.letter)
  76. @cmd2.with_argparser(guessing)
  77. def do_find(self, args):
  78. """Find words that match a pattern"""
  79. pattern = re.compile(args.pattern + "$")
  80. matching_words = filter_possibilities(self.candidates, pattern)
  81. app = RemoveWordsActivity(matching_words - self.hidden, self.excludes)
  82. if os.name == "nt":
  83. app.run(fork=False)
  84. else:
  85. app.run()
  86. was_canceled, new_exludes = app.get_results()
  87. if not was_canceled:
  88. self.excludes.update(new_exludes)
  89. @cmd2.with_argparser(hide_exclude)
  90. def do_hide(self, args):
  91. """Hide words that are in the exclude list"""
  92. if args.show:
  93. print("\n".join(sorted(self.excludes)))
  94. return
  95. if args.commit:
  96. self.hidden.update(self.excludes)
  97. self.excludes = set()
  98. return
  99. if args.edit:
  100. app = RemoveWordsActivity(self.excludes, self.hidden)
  101. if os.name == "nt":
  102. app.run(fork=False)
  103. else:
  104. app.run()
  105. was_canceled, results = app.get_results()
  106. if not was_canceled:
  107. result_set = set(results)
  108. self.excludes = self.hidden - result_set
  109. self.hidden = result_set
  110. return
  111. if __name__ == "__main__":
  112. MainLoop().cmdloop()