customfunctions.py 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121
  1. import math
  2. import tkinter
  3. import tkinter.messagebox
  4. SCREEN = None # 设置屏幕
  5. func_input = None
  6. help_ = None
  7. button = None
  8. logger = None
  9. bg_color = "#FFFAFA" # 主颜色
  10. botton_color = "#FFFAFA" # 按钮颜色
  11. word_color = "#000000" # 文字颜色
  12. help_doc = """
  13. 请在第一个输入框输入你的函数方程,不需要输入f(x)=和y=,唯一变量是x(x为自变量)
  14. 圆周率-Pi,自然无理数-e
  15. 指数的表示符号:**,比如x**2表示x的二次方
  16. 对数的表示符号:log(a,b),其中a是真书,b是底数(没有lg和ln)
  17. 三角函数sin(),cos(),tan(),cot(),csc(),sec()
  18. 反三角函数arcsin(),arccos(),arctan()
  19. 双曲函数:sinh(),cosh(),tanh()
  20. 注意:三角函数必须带括号使用
  21. 不支持定义域选择,不支持分段函数
  22. """
  23. class CustomFuncLogger:
  24. def __init__(self):
  25. self.func = None
  26. def set(self, func):
  27. self.func = func
  28. def __call__(self, *args, **kwargs):
  29. return self.func
  30. class FunctionExpression:
  31. def __init__(self, func):
  32. self.func = func
  33. self.named_domain = {
  34. "x": 0,
  35. "Pi": math.pi,
  36. "e": math.e,
  37. "log": math.log,
  38. "sin": math.sin,
  39. "cos": math.cos,
  40. "tan": math.tan,
  41. "cot": lambda x: 1 / math.tan(x),
  42. "csc": lambda x: 1 / math.sin(x),
  43. "sec": lambda x: 1 / math.cos(x),
  44. "sinh": math.sinh,
  45. "cosh": math.cosh,
  46. "tanh": math.tanh,
  47. "asin": math.asin,
  48. "acos": math.acos,
  49. "atan": math.atan,
  50. }
  51. def __call__(self, x):
  52. self.named_domain["x"] = x
  53. return eval(self.func, self.named_domain)
  54. def custom():
  55. global help_doc, logger
  56. func_str = UIAPI.get_func_str_gui()
  57. if func_str:
  58. if UIAPI.askok_gui(f"是否确认生成自定义函数:\n{func_input.get()}\n(点击取消可撤销未执行的制造函数)"):
  59. logger.set(FunctionExpression(func_input.get()))
  60. else:
  61. logger.set(None)
  62. else:
  63. if UIAPI.askok_gui(f"点击确定撤销为执行的制造函数"):
  64. logger.set(None)
  65. class UIAPI:
  66. @staticmethod
  67. def get_help_gui():
  68. tkinter.messagebox.showinfo(title="帮助", message=help_doc)
  69. @staticmethod
  70. def get_func_str_gui():
  71. return func_input.get().replace(" ", "")
  72. @staticmethod
  73. def askok_gui(message):
  74. return tkinter.messagebox.askokcancel("提示", message)
  75. def make_func():
  76. global SCREEN, func_input, help_, button, logger
  77. SCREEN = tkinter.Toplevel(bg=bg_color)
  78. SCREEN.title("")
  79. SCREEN.resizable(width=False, height=False)
  80. SCREEN.geometry(f"+350+10")
  81. button = tkinter.Button(
  82. SCREEN,
  83. text="制造函数",
  84. command=custom,
  85. width=28,
  86. height=1,
  87. bg=bg_color,
  88. fg=word_color,
  89. )
  90. help_ = tkinter.Button(
  91. SCREEN,
  92. text="帮助",
  93. command=UIAPI.get_help_gui,
  94. width=28,
  95. height=1,
  96. bg=bg_color,
  97. fg=word_color,
  98. )
  99. func_input = tkinter.Entry(SCREEN)
  100. func_input.pack(fill=tkinter.BOTH)
  101. button.pack()
  102. help_.pack()
  103. logger = CustomFuncLogger()
  104. return logger