-
Notifications
You must be signed in to change notification settings - Fork 0
/
wedi.py
366 lines (329 loc) · 17.6 KB
/
wedi.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
try:
import tkinter as tk
from tkinter import messagebox
except ImportError:
import Tkinter as tk
import tkMessageBox as messagebox
import sys
import os
from run_gui import Run_gui
import webbrowser
from PIL import Image, ImageTk
from ToolTip import ToolTip
from settingsGUI import settings_GUI
import requests
import json
import subprocess
import util
class GUI:
def __init__(self, settings_filepath):
self.version = 1.2
self.run_gui_objects = []
self.settings_filepath = settings_filepath
try:
self.settings = util.open_json(settings_filepath)
except:
self.settings = self.default_settings()
self.format_dict = {"Best video quality":'best', "Worst video quality":'worst', "Only video (no audio)":'bestvideo'}
self.inv_format_dict = {v: k for k, v in self.format_dict.items()}
self.info_on = False
self.create_gui()
self.start_gui()
def start_gui(self):
self.root.mainloop()
def create_gui(self):
self.bg_color = '#e6e6ff'
self.green_color = '#4af441'
self.button_color = '#ffffe6'
font = ('calibri', 13)
menufont = ('calibri', 16, 'bold')
menufont1 = ('calibri', 16)
box_width = 40
self.root = tk.Tk()
self.root.configure(background=self.bg_color)
self.root.title("WeDi")
self.root.wm_protocol("WM_DELETE_WINDOW", self.on_close)
menu = tk.Menu(self.root)
self.root.config(menu=menu)
prefmenu = tk.Menu(menu, tearoff=0)
menu.add_cascade(label="Preferences", menu=prefmenu)
prefmenu.add_command(label="Settings", command=self.on_settings_menu)
helpmenu = tk.Menu(menu, tearoff=0)
menu.add_cascade(label="Help", menu=helpmenu)
helpmenu.add_command(label="Open download folder", command=self.on_open_download_folder)
helpmenu.add_command(label="Open Github page", command=self.on_open_github)
helpmenu.add_command(label="Open download page", command=self.on_open_download_page)
helpmenu.add_command(label="Check for updates", command=self.check_for_updates)
helpmenu.add_command(label="Disclaimer", command=self.on_disclaimer)
helpmenu.add_command(label="About", command=self.on_about)
self.docgray = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'docgray.png')))
self.docgreen = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'docgreen.png')))
self.imggray = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'imggray.png')))
self.imggreen = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'imggreen.png')))
self.audgray = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'audgray.png')))
self.audgreen = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'audgreen.png')))
self.devgray = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'devgray.png')))
self.devgreen = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'devgreen.png')))
self.vidgray = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'vidgray.png')))
self.vidgreen = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'vidgreen.png')))
self.buttonframe = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'buttonframe.png')))
self.titleimg = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'titleimg.png')))
self.pasteimg = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'pasteimg.png')))
self.delimg = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'delimg.png')))
self.buttonimg = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'button.png')))
self.infoOnImg = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'info_on.png')))
self.infoOffImg = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'info_off.png')))
self.imgicon = ImageTk.PhotoImage(Image.open(os.path.join('textures', 'icon.ico')))
#set the window icon
self.root.tk.call('wm', 'iconphoto', self.root._w, self.imgicon)
self.start_frame = tk.Frame(self.root, bg=self.bg_color)
self.start_frame2 = tk.Frame(self.root, bg=self.bg_color)
self.body_frame = tk.Frame(self.root, bg=self.bg_color)
self.end_frame = tk.Frame(self.root, bg=self.bg_color)
self.title = tk.Label(self.start_frame, image=self.titleimg, bg=self.bg_color, pady=35)
self.title.pack(side='top')
self.siteEntry = tk.Entry(self.start_frame, width=box_width+25, font=font)
self.siteEntry.pack(side='top')
try:
clipboard = self.root.clipboard_get()
except:
clipboard = ""
if len(clipboard) > 10 and clipboard[:4] == 'http':
self.siteEntry.insert(0, clipboard)
self.del_button = tk.Button(self.start_frame, image=self.delimg, bg=self.button_color, command=self.clear_site)
self.del_button.pack(side='right')
self.paste_button = tk.Button(self.start_frame, image=self.pasteimg, bg=self.button_color, command=self.paste_site)
self.paste_button.pack(side='right')
self.info_button = tk.Button(self.start_frame, image=self.infoOffImg, border=0, highlightthickness=0, bg=self.bg_color, activebackground=self.bg_color, command=self.on_info)
self.info_button.pack(side='left')
text = "Activate to show hover over help text"
self.info_toolTip = self.createToolTip(self.info_button, text)
tk.Label(self.start_frame2, text="Choose what you want to download", font=font, padx=20, pady=20, bg=self.bg_color).pack(side='top')
color = self.docgray
if self.settings['documents']['run']:
color = self.docgreen
self.doc_button = tk.Button(self.body_frame, image=color, border=0, highlightthickness=0, bg= self.bg_color, activebackground=self.bg_color, command=self.on_documents)
self.doc_button.grid(row=0, column=0, padx=20, pady=10)
color = self.imggray
if self.settings['images']['run']:
color = self.imggreen
self.img_button = tk.Button(self.body_frame, image=color, border=0, highlightthickness=0, bg= self.bg_color, activebackground=self.bg_color, command=self.on_images)
self.img_button.grid(row=0, column=1, padx=20, pady=10)
color = self.audgray
if self.settings['audios']['run']:
color = self.audgreen
self.aud_button = tk.Button(self.body_frame, image=color, border=0, highlightthickness=0, bg= self.bg_color, activebackground=self.bg_color, command=self.on_audios)
self.aud_button.grid(row=1, column=0, padx=20, pady=10)
color = self.devgray
if self.settings['dev']['run']:
color = self.devgreen
self.dev_button = tk.Button(self.body_frame, image=color, border=0, highlightthickness=0, bg= self.bg_color, activebackground=self.bg_color, command=self.on_analytics)
self.dev_button.grid(row=1, column=1, padx=20, pady=10)
color = self.vidgray
if self.settings['videos']['run']:
color = self.vidgreen
self.vid_button = tk.Button(self.body_frame, image=color, border=0, highlightthickness=0, bg= self.bg_color, activebackground=self.bg_color, command=self.on_videos)
self.vid_button.grid(row=2, column=0, padx=20, pady=10)
def set_format(value):
self.settings['videos']['format'] = self.format_dict[value]
formats = ["Best video quality", "Worst video quality", "Only video (no audio)"]
self.option = tk.StringVar()
self.option.set(self.inv_format_dict[self.settings['videos']['format']])
self.options = tk.OptionMenu(self.body_frame, self.option, *formats, command=set_format) # creates drop down menu
self.options.config(indicatoron=0,bg=self.bg_color, border=0, highlightthickness=0, image=self.buttonframe, compound=tk.CENTER, activebackground=self.bg_color, font=menufont)
self.options["menu"].config(bg=self.button_color, font=menufont1)
self.options.grid(row=2, column=1)
self.run_button = tk.Button(self.end_frame, text="Run", font=font, image=self.buttonimg, border=0, highlightthickness=0, bg=self.bg_color, activebackground=self.bg_color,compound=tk.CENTER, command=self.on_run)
self.run_button.pack(side='left', padx=50)
self.run_button2 = tk.Button(self.end_frame, text='Extensive run', font=font, image=self.buttonimg, border=0, highlightthickness=0, bg=self.bg_color, activebackground=self.bg_color,compound=tk.CENTER, command=self.on_extensive_run)
self.run_button2.pack(side='left', padx=50)
self.start_frame.pack(side="top")
self.start_frame2.pack(side="top")
self.body_frame.pack()
self.end_frame.pack(side="bottom", pady=25)
def clear_site(self):
self.siteEntry.delete(0, "end")
def paste_site(self):
self.siteEntry.delete(0, "end")
try:
clipboard = self.root.clipboard_get()
except:
clipboard = ""
if len(clipboard) > 10 and clipboard[:4] == 'http':
self.siteEntry.insert(0, clipboard)
def wait_for_all_child_windows(self):
if len(self.run_gui_objects) > 0:
run_gui_object = self.run_gui_objects[0]
run_gui_object.on_close()
if run_gui_object.finished_running:
del self.run_gui_objects[0]
self.root.after(10, self.wait_for_all_child_windows)
else:
self.root.destroy()
sys.exit(1)
def on_close(self):
for run_gui_object in self.run_gui_objects:
run_gui_object.on_close()
self.wait_for_all_child_windows()
def on_videos(self):
self.settings['videos']['run'] = not self.settings['videos']['run']
if self.settings['videos']['run']:
self.vid_button['image'] = self.vidgreen
else:
self.vid_button['image'] = self.vidgray
def on_documents(self):
self.settings['documents']['run'] = not self.settings['documents']['run']
if self.settings['documents']['run']:
self.doc_button['image'] = self.docgreen
else:
self.doc_button['image'] = self.docgray
def on_images(self):
self.settings['images']['run'] = not self.settings['images']['run']
if self.settings['images']['run']:
self.img_button['image'] = self.imggreen
else:
self.img_button['image'] = self.imggray
def on_audios(self):
self.settings['audios']['run'] = not self.settings['audios']['run']
if self.settings['audios']['run']:
self.aud_button['image'] = self.audgreen
else:
self.aud_button['image'] = self.audgray
def on_analytics(self):
self.settings['dev']['run'] = not self.settings['dev']['run']
if self.settings['dev']['run']:
self.dev_button['image'] = self.devgreen
else:
self.dev_button['image'] = self.devgray
def default_settings(self):
path = "..\\wedi_downloads"
extensive = False
img_types = ['jpg', 'jpeg', 'png', 'gif', 'svg']
doc_types = ['txt', 'py', 'java', 'php', 'pdf', 'md', 'gitignore', 'c']
vid_types = ['mp4', 'avi', 'mpeg', 'mpg', 'wmv', 'mov', 'flv',\
'swf', 'mkv', '3gp', 'webm', 'ogg']
aud_types = ['mp3', 'aac', 'wma', 'wav', 'm4a']
img_settings = {'run':False, 'img_types':img_types}
doc_settings = {'run':False, 'doc_types':doc_types}
vid_settings = {'run':True, 'vid_types':vid_types, 'format':'best'}
aud_settings = {'run':False, 'aud_types':aud_types}
dev_settings = {'run':True}
settings = {'path':path, 'extensive':extensive,'images':img_settings,\
'documents':doc_settings, 'videos':vid_settings,\
'audios':aud_settings, 'dev':dev_settings}
util.save_json(self.settings_filepath, settings)
return settings
def on_info(self):
if self.info_on:
self.info_button["image"] = self.infoOffImg
self.info_on = False
self.destroyToolTips()
else:
self.info_button["image"] = self.infoOnImg
self.info_on = True
self.createToolTips()
def createToolTip(self, widget, text):
toolTip = ToolTip(widget)
def enter(event):
toolTip.showtip(text)
def leave(event):
toolTip.hidetip()
widget.bind('<Enter>', enter)
widget.bind('<Leave>', leave)
return toolTip
def createToolTips(self):
self.toolTips = []
self.info_toolTip.hidetip()
text = "Deactivate to hide hover over help text"
self.info_toolTip = self.createToolTip(self.info_button, text)
self.toolTips.append(self.info_button)
text = "The url of the page you want to download from goes in here..."
self.createToolTip(self.siteEntry, text)
self.toolTips.append(self.siteEntry)
text = "Paste in url from clipboard"
self.createToolTip(self.paste_button, text)
self.toolTips.append(self.paste_button)
text = "Empty url entry field"
self.createToolTip(self.del_button, text)
self.toolTips.append(self.del_button)
text = "Creates files containing information about the supplied\nurl, the results of the run and some analytics data"
self.createToolTip(self.dev_button, text)
self.toolTips.append(self.dev_button)
text = "This option will also try to extract the audio from the videos found in the url\nPlease note that you need to have FFmpeg installed in your machine if you want\nthe downloaded audio file to be converted to mp3"
self.createToolTip(self.aud_button, text)
self.toolTips.append(self.aud_button)
text = "This option will also try to extract empeded video files found in the url\nPlease note that not all websites are supported"
self.createToolTip(self.vid_button, text)
self.toolTips.append(self.vid_button)
text = "This mode uses either Firefox or Chrome browsers\nin your machine to fetch the source code of the url"
self.createToolTip(self.run_button2, text)
self.toolTips.append(self.run_button2)
def destroyToolTips(self):
for w in self.toolTips:
w.unbind('<Enter>')
w.unbind('<Leave>')
self.info_toolTip.hidetip()
text = "Activate to show hover over help text"
self.info_toolTip = self.createToolTip(self.info_button, text)
def on_extensive_run(self):
self.on_run(extensive=True)
def on_settings_menu(self):
settings_GUI(self.settings_filepath, imgicon=self.imgicon)
def on_about(self):
msg = 'WeDi (Web Dissector) is a tool that makes it \
possible to download all contents of a page easily \
(images, documents, videos...etc)'
messagebox.showinfo(f'About WeDi v{self.version}', msg)
def on_disclaimer(self):
msg = "The user of WeDi is responsible to use WeDi only on \
web pages that allow their contents to be downloaded and stored locally."
messagebox.showinfo("Disclaimer", msg)
def on_open_download_folder(self):
downloadpath = util.open_json(self.settings_filepath)["path"]
_platform = sys.platform
if _platform == "linux" or _platform == "linux2": # linux
subprocess.Popen(["xdg-open", downloadpath])
elif _platform == "darwin": # MAC OS X
subprocess.Popen(["open", downloadpath])
elif _platform == "win32" or _platform == "win64": # Windows
os.startfile(downloadpath)
def on_open_github(self):
url = "https://github.com/ahmed91abbas/wedi"
webbrowser.open(url, new=0, autoraise=True)
def on_open_download_page(self):
url = "https://ahmed91abbas.github.io/wedi/"
webbrowser.open(url, new=0, autoraise=True)
def on_run(self, extensive=False):
current_settings = util.open_json(self.settings_filepath)
self.settings['extensive'] = extensive
site = self.siteEntry.get().rstrip()
if len(site) > 10 and site[:4] == 'http':
self.settings["path"] = current_settings["path"]
self.settings["documents"]["doc_types"] = current_settings["documents"]["doc_types"]
self.settings["images"]["img_types"] = current_settings["images"]["img_types"]
self.settings["audios"]["aud_types"] = current_settings["audios"]["aud_types"]
self.settings["videos"]["vid_types"] = current_settings["videos"]["vid_types"]
util.save_json(self.settings_filepath, self.settings)
run_gui_object = Run_gui(site, self.settings, imgicon=self.imgicon)
self.run_gui_objects.append(run_gui_object)
run_gui_object.start()
else:
print("Enter the webpage url!")
def check_for_updates(self):
url = "https://api.github.com/repos/ahmed91abbas/wedi/releases/latest"
response = requests.get(url)
if response.status_code == 200:
response = response.json()
version_tag = response["tag_name"]
online_version = float(version_tag[1:])
if online_version > self.version:
ans = messagebox.askyesno('Check for updates', f'Version {version_tag}'
f' is available. Current version is v{self.version}'\
f'\nDo you want to open the download page?')
if ans:
self.on_open_download_page()
else:
messagebox.showinfo("Check for updates", "Your version is up to date.")
if __name__ == '__main__':
settings_filepath = 'settings.json'
GUI(settings_filepath)