From 7aaca048ffc7666b0eccf3d8b7ba212bae3c9e13 Mon Sep 17 00:00:00 2001
From: admin <weikou2014>
Date: 星期三, 29 三月 2023 16:15:42 +0800
Subject: [PATCH] 看盘页面优化

---
 main.py |  353 ++++++++++++++++++++++++++++++++++++++++++----------------
 1 files changed, 252 insertions(+), 101 deletions(-)

diff --git a/main.py b/main.py
index 00c292f..d6c0a4d 100644
--- a/main.py
+++ b/main.py
@@ -1,4 +1,5 @@
 import json
+import os
 import socket
 import sys
 import time
@@ -22,6 +23,7 @@
 from matplotlib.widgets import Button
 
 import wx
+import wx.html
 from matplotlib.backends.backend_wxagg import FigureCanvasWxAgg as FigureCanvas
 from matplotlib.figure import Figure
 
@@ -46,6 +48,17 @@
     toastone = wx.MessageDialog(None, content, "鎻愮ず", wx.YES_DEFAULT | wx.ICON_INFORMATION)
     if toastone.ShowModal() == wx.ID_YES:  # 濡傛灉鐐瑰嚮浜嗘彁绀烘鐨勭‘瀹氭寜閽�
         click()
+        toastone.Destroy()
+
+
+def show_sure(content, callback):
+    toastone = wx.MessageDialog(None, content, "鎻愮ず", wx.YES_NO | wx.ICON_INFORMATION)
+    result = toastone.ShowModal()
+    if result == wx.ID_YES:  # 濡傛灉鐐瑰嚮浜嗘彁绀烘鐨勭‘瀹氭寜閽�
+        callback(True)
+        toastone.Destroy()
+    elif result == wx.ID_NO:
+        callback(False)
         toastone.Destroy()
 
 
@@ -289,28 +302,38 @@
     rect_ = setting.get_ths_auto_code_rect()
     img = win32_util.window_capture(hwnd, (0, rect_[0], rect_[1], rect_[0] + rect_[2]))
     code = ocr_util.recognize_code(opencv_util.clip_ths_code_area(img))
+    if code is None:
+        code = ocr_util.recognize_code(img)
     return code
 
 
 # 鎮诞妗�
 class FloatFrame(wx.Frame):
     def __init__(self, position):
-        wx.Frame.__init__(self, None, -1, "鎮诞鐩洏", style=wx.CAPTION ^ wx.STAY_ON_TOP,
+        wx.Frame.__init__(self, None, -1, "鎮诞鐩洏", style=wx.CAPTION ^ wx.MINIMIZE_BOX ^ wx.CLOSE_BOX ^ wx.STAY_ON_TOP,
                           size=(320, 195))
         self.SetBackgroundColour(wx.Colour(224, 224, 224))
         self.SetTransparent(230)
         if position:
             self.SetPosition(wx.Point(position[0], position[1]))
-        boxsier = wx.FlexGridSizer(5, 2, 2, 20)
-
+        boxsier = wx.FlexGridSizer(5, 2, 2, 5)
+        bs1 = wx.BoxSizer(wx.HORIZONTAL)
         self.btn_remove_black = wx.Button(self, label="绉婚櫎榛戝悕鍗�", size=(70, 30))
-        boxsier.Add(self.btn_remove_black, 0, wx.TOP, 5)
+        self.btn_close_buy = wx.Button(self, label="鍏抽棴浜ゆ槗", size=(70, 30))
+        self.btn_close_buy.SetForegroundColour("#FF3232")
+        bs1.Add(self.btn_remove_black)
+        bs1.Add(self.btn_close_buy)
+        boxsier.Add(bs1, 0, wx.TOP, 5)
 
         bs1 = wx.BoxSizer(wx.HORIZONTAL)
-
         self.btn_remove_white = wx.Button(self, label="绉婚櫎鐧藉悕鍗�", size=(70, 30))
+        self.btn_open_buy = wx.Button(self, label="寮�鍚氦鏄�", size=(70, 30), )
+        self.btn_open_buy.SetForegroundColour("#00e600")
+
+        bs1.Add(self.btn_open_buy, 0, wx.TOP, 5)
         bs1.Add(self.btn_remove_white, 0, wx.TOP, 5)
-        boxsier.Add(bs1, 0, wx.LEFT, 80)
+
+        boxsier.Add(bs1, 0, wx.LEFT, 0)
 
         label = wx.StaticText(self, label="浜ゆ槗鍒锋柊锛�")
         bs1 = wx.BoxSizer(wx.HORIZONTAL)
@@ -325,7 +348,7 @@
         self.btn_want_buy = wx.Button(self, label="鍔犲叆鎯充拱鍗�", size=(70, 25))
         bs1.Add(self.btn_want_buy)
 
-        boxsier.Add(bs1, 0, wx.LEFT, 35)
+        boxsier.Add(bs1, 0, wx.LEFT, 25)
 
         label = wx.StaticText(self, label="鍒嗙粍鍒锋柊锛�")
         bs1 = wx.BoxSizer(wx.HORIZONTAL)
@@ -335,7 +358,7 @@
         boxsier.Add(bs1)
 
         self.btn_want_buy_remove = wx.Button(self, label="绉婚櫎鎯充拱鍗�", size=(70, 25))
-        boxsier.Add(self.btn_want_buy_remove, 0, wx.LEFT, 80)
+        boxsier.Add(self.btn_want_buy_remove, 0, wx.LEFT, 70)
 
         self.edit_code = wx.TextCtrl(self, size=(80, -1))
         boxsier.Add(self.edit_code)
@@ -359,9 +382,12 @@
         bs1.Add(self.white_list, 0, wx.CENTER | wx.ALL, 0)
         bs1.Add(self.btn_white, 0, wx.LEFT, 2)
 
-        boxsier.Add(bs1, 0, wx.LEFT, 32)
+        boxsier.Add(bs1, 0, wx.LEFT, 22)
 
         # 缁戝畾
+        self.btn_open_buy.Bind(wx.EVT_BUTTON, self.__open_buy)
+        self.btn_close_buy.Bind(wx.EVT_BUTTON, self.__close_buy)
+
         self.btn_black.Bind(wx.EVT_BUTTON, self.add_black)
         self.btn_white.Bind(wx.EVT_BUTTON, self.add_white)
         self.btn_remove_black.Bind(wx.EVT_BUTTON, self.remove_from_black)
@@ -569,8 +595,177 @@
         client.close()
         return result.decode("gbk")
 
+    def __request_buy(self, is_open):
+        client = socket.socket()  # 鐢熸垚socket锛岃繛鎺erver
+        ip_port = ("192.168.3.252", 9001)  # server鍦板潃鍜岀鍙e彿锛堟渶濂芥槸10000浠ュ悗锛�
+        client.connect(ip_port)
+        data = {"type": 501, "data": {"open": is_open}}
+        client.send(json.dumps(data).encode("utf-8"))
+        # 璇诲彇鍐呭
+        result = client.recv(10240)
+        client.close()
+        return result.decode("gbk")
 
-class mainFrame(wx.Frame):
+    def __open_buy(self, event):
+        def open_buy(sure):
+            if sure:
+                try:
+                    result = self.__request_buy(True)
+                    msg = json.loads(result)["msg"]
+                    show_info(msg, None)
+                except Exception as e:
+                    show_warning(str(e), None)
+
+        show_sure("鏄惁寮�鍚氦鏄�", open_buy)
+
+    def __close_buy(self, event):
+        def close_buy(sure):
+            if sure:
+                try:
+                    result = self.__request_buy(False)
+                    msg = json.loads(result)["msg"]
+                    show_info(msg, None)
+                except Exception as e:
+                    show_warning(str(e), None)
+
+        show_sure("鏄惁鍏抽棴浜ゆ槗", close_buy)
+
+
+# 浠g爜鏁版嵁
+class CodeDataFrame(wx.Frame):
+    def __init__(self, set_codes_success_callback):
+        # style=wx.CAPTION |
+        wx.Frame.__init__(self, None, -1, "鏁版嵁",
+                          style=wx.CAPTION | wx.STAY_ON_TOP | wx.MINIMIZE_BOX | wx.MAXIMIZE_BOX | wx.CLOSE_BOX | wx.RESIZE_BORDER,
+                          size=(320, 195))
+        self.set_codes_success = set_codes_success_callback
+        self.SetBackgroundColour(wx.Colour(224, 224, 224))
+        # self.SetTransparent(230)
+        boxsier = wx.BoxSizer(wx.VERTICAL)
+        self.data_text = wx.html.HtmlWindow(self, size=wx.Size(self.Size[0], self.Size[
+            1]))
+        self.data_text.SetBackgroundColour(wx.Colour(224, 224, 224))
+        if "gtk2" in wx.PlatformInfo:
+            self.data_text.SetStandardFonts()
+        boxsier.Add(self.data_text)
+        self.latest_code = ''
+        self.SetSizer(boxsier)
+        window_info = setting.get_xgb_window_info()
+        if window_info:
+            self.SetPosition(wx.Point(window_info[0], window_info[1]))
+            self.Size = wx.Size(window_info[2], window_info[3])
+        self.Bind(wx.EVT_CLOSE, self.OnExit)
+        self.Bind(wx.EVT_SIZE, self.OnResize)
+        self.data_text.SetPage("")
+        self.__menu()
+
+    def set_data(self, code, data):
+        self.data_text.SetPage(data)
+
+    # 璁剧疆浠g爜
+    def set_code(self, code):
+        if self.latest_code == code:
+            return
+        self.latest_code = code
+        t1 = threading.Thread(target=lambda: self.__init_data(code))
+        t1.setDaemon(True)
+        t1.start()
+
+    def __init_data(self, code):
+        if code:
+            # 璇锋眰缃戠粶
+            result_data = self.__request(code)
+            if result_data:
+                result_json = json.loads(result_data)
+                if result_json['code'] == 0:
+                    code = result_json['data']['code']
+                    data = result_json['data']['data']
+                    wx.CallAfter(self.set_data, code, data)
+
+    def __request(self, code, type=71):
+        client = socket.socket()  # 鐢熸垚socket锛岃繛鎺erver
+        ip_port = ("192.168.3.252", 9001)  # server鍦板潃鍜岀鍙e彿锛堟渶濂芥槸10000浠ュ悗锛�
+        client.connect(ip_port)
+        data = {"type": type, "data": {"code": code}}
+        client.send(json.dumps(data).encode("utf-8"))
+        # 璇诲彇鍐呭
+        result = client.recv(102400)
+        client.close()
+        return result.decode("gbk")
+
+    def OnExit(self, e):
+        try:
+            setting.set_xgb_window_info((self.Position[0], self.Position[1], self.Size[0], self.Size[1]))
+        except Exception as e:
+            print("")
+        jueJinProcess.terminate()
+        sys.exit(0)
+
+    def OnResize(self, e):
+        print("鍙樺寲鍚庣殑灏哄", e.Size)
+        self.data_text.Size = e.Size
+
+    def __menu(self):
+        self.mainmenu = wx.MenuBar()
+        setting_ = wx.Menu()
+        # setting_.Append(104, '&閽変綇', '', kind=wx.ITEM_CHECK)
+        # setting_.Check(104, setting.is_stay_on_top())
+        setting_.AppendSeparator()
+        setting_.Append(101, '&鎺橀噾鍙傛暟閰嶇疆', 'Open a new document')
+        setting_.AppendSeparator()
+        setting_.Append(103, '&浠g爜绠$悊', 'Open a new document')
+        setting_.Append(102, '&涓嬭浇娑ㄥ仠浠g爜', 'Open a new document')
+
+        self.mainmenu.Append(setting_, '&璁剧疆')
+
+        auto_help = wx.Menu()
+        auto_help.Append(202, '&鍚岃姳椤鸿缃�', '')
+        self.mainmenu.Append(auto_help, '&鑷姩鍖�')
+        # 璁剧疆浜嬩欢
+        self.Bind(wx.EVT_MENU, self.__set_juejin_params, id=101)
+        self.Bind(wx.EVT_MENU, self.__download_codes, id=102)
+        self.Bind(wx.EVT_MENU, self.__manage_code, id=103)
+        self.Bind(wx.EVT_MENU, self.__manage_ths_pos, id=202)
+
+        self.SetMenuBar(self.mainmenu)
+
+    def __set_juejin_params(self, event):
+        ps = self.GetPosition()
+        size = self.GetSize()
+        JueJinSettingFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2)).Show()
+
+    def __download_codes(self, event):
+        try:
+            result = self.__request("", 72)
+            result = json.loads(result)
+            if result['code'] == 0:
+                codes_dict = result['data']
+                if codes_dict:
+                    for key in codes_dict:
+                        # 灏嗕唬鐮佷繚瀛樺埌妗岄潰
+                        path = f"C:\\Users\\Administrator\\Desktop\\娑ㄥ仠浠g爜{key}.txt"
+                        with open(path, mode='w') as f:
+                            for c in codes_dict[key]:
+                                f.write(c)
+                                f.write("\n")
+                    show_info("涓嬭浇鎴愬姛", None)
+            else:
+                show_warning(result['msg'], None)
+        except Exception as e:
+            show_warning(str(e), None)
+
+    def __manage_code(self, event):
+        ps = self.GetPosition()
+        size = self.GetSize()
+        CodesSettingFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2), self.set_codes_success).Show()
+
+    def __manage_ths_pos(self, event):
+        ps = self.GetPosition()
+        size = self.GetSize()
+        THSPositionSettingFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2)).Show()
+
+
+class MainFrame(wx.Frame):
     def __init__(self):
         '''鏋勯�犲嚱鏁�'''
         wx.Frame.__init__(self, None, -1, APP_TITLE, style=wx.DEFAULT_FRAME_STYLE,
@@ -579,7 +774,7 @@
         # 榛樿style鏄笅鍒楅」鐨勭粍鍚堬細wx.MINIMIZE_BOX | wx.MAXIMIZE_BOX | wx.RESIZE_BORDER | wx.SYSTEM_MENU | wx.CAPTION | wx.CLOSE_BOX | wx.CLIP_CHILDREN
         self.SetBackgroundColour(wx.Colour(0, 0, 0))
         self.Center()
-        self.__menu()
+
         # 浠ヤ笅浠g爜澶勭悊鍥炬爣
         # if hasattr(sys, "frozen") and getattr(sys, "frozen") == "windows_exe":
         #     exeName = win32api.GetModuleFileName(win32api.GetModuleHandle(None))
@@ -594,6 +789,7 @@
         self.scroll = None
         self.mark_lines = {}
         self.col = 1
+        self.ratio = 0.76
         self.__re_draw()
 
         self.timer = wx.Timer(self)  # 鍒涘缓瀹氭椂鍣�
@@ -638,7 +834,8 @@
             for p in self.panels:
                 p.Destroy()
         self.boxsier.Clear()
-        pannel_height = round((self.Size[0] - (self.col - 1) * space) / self.col * (450 / 800))
+
+        pannel_height = round((self.Size[0] - (self.col - 1) * space) / self.col * self.ratio)
 
         self.scroll.SetScrollbars(1, 1, 0, pannel_height * rows)
         self.scroll.SetScrollRate(0, pannel_height)
@@ -660,7 +857,10 @@
         #
         # 鍒濆鍖栨暟鎹�
         drawManager = DrawManager(axes_list, codes_name)
-        drawManager.init_code_datas()
+        t1 = threading.Thread(target=lambda: drawManager.init_code_datas())
+        # 鍚庡彴杩愯
+        t1.setDaemon(True)
+        t1.start()
 
     def __create_canvas(self, pannel, title, name, price, close_callback=None):
         def show_mouse_line(event):
@@ -695,9 +895,12 @@
             close_callback(title)
 
         width_dpi = self.Size[0] / (100 * self.col)
-        figure_score = Figure(figsize=(width_dpi, round(width_dpi * (4.5 / 7.8), 2)))
+        figure_score = Figure(figsize=(width_dpi, round(width_dpi * (self.ratio), 2)))
         # 璁剧疆澶栬竟璺�
-        figure_score.subplots_adjust(left=0.01, bottom=0.15, right=0.85)
+        right_padding_px = 85
+        right = round((self.Size[0] - right_padding_px) / self.Size[0], 4)
+        figure_score.subplots_adjust(left=0.01, bottom=0.15, top=0.92,
+                                     right=right)
         # 璁剧疆瀛椾綋棰滆壊
         plt.rcParams["text.color"] = "red"
         plt.rcParams["axes.labelcolor"] = "red"
@@ -774,7 +977,7 @@
                 yticks_labels.append("")
         # 鍔犵矖涓酱绾�
 
-        axes2.set_ylabel(u'娑ㄥ箙')
+        axes2.set_ylabel(u'')
         # 璁剧疆绾佃酱鐨勫�肩殑鑼冨洿
         axes2.set_ylim(0 - max_rate * (1), max_rate * (1))
         axes2.set_yticks(yticks2)
@@ -803,42 +1006,6 @@
         axes.spines['bottom'].set_visible(False)
         return (axes2, line, average_line)
 
-    def __set_juejin_params(self, event):
-        ps = self.GetPosition()
-        size = self.GetSize()
-        JueJinSettingFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2)).Show()
-
-    def __check_juejin(self, event):
-        frame = wx.Frame(None, -1, '鎺橀噾鍙傛暟璁剧疆', size=(400, 100))
-        frame.Center()
-        frame.Show()
-
-    def __manage_code(self, event):
-        ps = self.GetPosition()
-        size = self.GetSize()
-        CodesSettingFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2), self.set_codes_success).Show()
-
-    def __add_forbidden_codes(self, event):
-        ps = self.GetPosition()
-        size = self.GetSize()
-        FobiddenCodesFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2)).Show()
-
-    def __manage_ths_pos(self, event):
-        ps = self.GetPosition()
-        size = self.GetSize()
-        THSPositionSettingFrame((ps[0] + size[0] / 2, ps[1] + size[1] / 2)).Show()
-
-    def __ths_auto_click(self, event):
-        if event.Selection:
-            setting.set_ths_auto_click(1)
-        else:
-            setting.set_ths_auto_click(0)
-
-    def set_codes_success(self):
-        print("璁剧疆浠g爜鎴愬姛鍥炶皟")
-        p2.send("resub")
-        self.__re_draw()
-
     def __show_top(self, event):
         if event.Selection:
             setting.set_stay_on_top(1)
@@ -846,39 +1013,6 @@
         else:
             setting.set_stay_on_top(0)
             self.WindowStyle = wx.MINIMIZE_BOX | wx.MAXIMIZE_BOX | wx.RESIZE_BORDER | wx.SYSTEM_MENU | wx.CAPTION | wx.CLOSE_BOX | wx.CLIP_CHILDREN
-
-    def __menu(self):
-        self.mainmenu = wx.MenuBar()
-        setting_ = wx.Menu()
-        setting_.Append(105, '&娣诲姞绂佹浠g爜', '')
-        setting_.AppendSeparator()
-        setting_.Append(104, '&閽変綇', '', kind=wx.ITEM_CHECK)
-        setting_.Check(104, setting.is_stay_on_top())
-        setting_.AppendSeparator()
-        setting_.Append(101, '&鎺橀噾鍙傛暟閰嶇疆', 'Open a new document')
-        setting_.Append(102, '&鎺橀噾妫�娴�', 'Open a new document')
-        setting_.AppendSeparator()
-        setting_.Append(103, '&浠g爜绠$悊', 'Open a new document')
-
-        self.mainmenu.Append(setting_, '&璁剧疆')
-
-        auto_help = wx.Menu()
-        auto_help.Append(202, '&鍚岃姳椤鸿缃�', '')
-        auto_help.Append(201, '&鑷姩鐐瑰嚮', '', kind=wx.ITEM_CHECK)
-
-        auto_help.Check(201, setting.is_ths_auto_click())
-
-        self.mainmenu.Append(auto_help, '&鑷姩鍖�')
-        # 璁剧疆浜嬩欢
-        self.Bind(wx.EVT_MENU, self.__set_juejin_params, id=101)
-        self.Bind(wx.EVT_MENU, self.__check_juejin, id=102)
-        self.Bind(wx.EVT_MENU, self.__manage_code, id=103)
-        self.Bind(wx.EVT_MENU, self.__show_top, id=104)
-        self.Bind(wx.EVT_MENU, self.__add_forbidden_codes, id=105)
-        self.Bind(wx.EVT_MENU, self.__manage_ths_pos, id=202)
-        self.Bind(wx.EVT_MENU, self.__ths_auto_click, id=201)
-
-        self.SetMenuBar(self.mainmenu)
 
     def OnExit(self, e):
         try:
@@ -910,6 +1044,11 @@
         self.timer.StartOnce(1000)
         # 闄嶄綆閲嶇粯棰戠巼
         # self.__re_draw()
+
+    def set_codes_success(self):
+        print("璁剧疆浠g爜鎴愬姛鍥炶皟")
+        p2.send("resub")
+        self.__re_draw()
 
 
 # 缁樺浘绠$悊鍣�
@@ -968,7 +1107,8 @@
 
                 if old_datas:
                     code_datas[code].extend(old_datas)
-                    self.update(code, code_datas[code])
+                    # self.update(code, code_datas[code])
+                    wx.CallAfter(self.update, code, code_datas[code])
 
     # 鏇存柊鏁版嵁
     def __update_data(self, code, axes, datas, min_rate, max_rate):
@@ -1064,6 +1204,7 @@
         self.lines = {}
 
     def update(self, code, datas):
+        __start_time = time.time()
         # 鑾峰彇鍓嶉珮鍜屽墠浣�
         max_rate = None
         min_rate = None
@@ -1088,12 +1229,23 @@
 
         # 灞曠ず鏈�杩戠殑600涓�
         datas = datas[-450:]
+        # 淇閲忔暟鎹�
+        last_info = None
+        for i in range(1, len(datas)):
+            # 濡傛灉鍦�
+            if not last_info:
+                last_info = datas[i]
+            if int(datas[i]["created_at"][-2:]) - int(datas[i - 1]["created_at"][-2:]) < 0:
+                last_info = datas[i]
+            datas[i]['average_rate'] = last_info['average_rate']
+
         for i in range(0, len(self.codes_info)):
             if self.codes_info[i][0] == code:
                 try:
                     self.__update_data(code, self.axes_list[i], datas, min_rate, max_rate)
                 except Exception as e:
                     logging.exception(e)
+        print("缁樺浘鑺辫垂鏃堕棿:", time.time() - __start_time)
 
 
 class mainApp(wx.App):
@@ -1107,6 +1259,7 @@
                 if not code:
                     time.sleep(0.1)
                     continue
+                self.xgb.set_code(code)
                 # 1s鏇存柊涓�娆�
                 if round(time.time()) - last_time > 5:
                     codes = juejin_core.GPCodeManager().get_codes()
@@ -1116,14 +1269,17 @@
                         self.Frame.scrollTo(index)
                         break
             except Exception as e:
-                print(str(e))
+                # print(str(e))
+                pass
             time.sleep(0.005)
 
     def OnInit(self):
         self.SetAppName(APP_TITLE)
-        self.Frame = mainFrame()
-        # self.Frame = FloatFrame(None)
-        self.Frame.Show()
+        self.frame = MainFrame()
+        self.frame.Show()
+        # 浼犻�掍唬鐮佽缃垚鍔熺殑鍥炶皟
+        self.xgb = CodeDataFrame(self.frame.set_codes_success)
+        self.xgb.Show()
         t1 = threading.Thread(target=lambda: self.__refresh())
         # 鍚庡彴杩愯
         t1.setDaemon(True)
@@ -1208,17 +1364,12 @@
 
 
 if __name__ == "__main__1":
-    hwnd = ths_util.get_ths_main_content_hwnd()
-    if not hwnd:
-        raise Exception("鐪嬬洏椤甸潰鍙ユ焺鏈幏鍙栧埌")
-    # 鍙ユ焺鎴浘
-    rect = win32gui.GetWindowRect(hwnd)
-    w = 150
-    height = 45
-    top = 38
-    # img = win32_util.window_capture(hwnd, (rect[2] - rect[0] -100 , 25, rect[2] - rect[0], 55))
-    # img = win32_util.window_capture(hwnd, rect)
-    img = win32_util.window_capture(hwnd, (0, 0, (rect[2] - rect[0]) * 15 // 10, (rect[3] - rect[1]) * 15 // 10))
+    code = ocr_util.recognize_code("C:\\Users\\Administrator\\Desktop\\test.png.bmp")
+    print(code)
+
+# 鎵撳寘鍛戒护
+# cd D:\workspace\GP\trade_desk
+# D:\workspace\GP\trade_desk\dist\env\pk_env\Scripts\pyinstaller.exe main.spec
 
 if __name__ == "__main__":
     print(pow(3, 1))

--
Gitblit v1.8.0