30
30
from imdb import IMDb
31
31
from unidecode import unidecode
32
32
33
- from common import Manager , Provider , MOVIES_GROUP , PROVIDERS_PATH , SERIES_GROUP , TV_GROUP ,\
33
+ from common import Manager , Provider , Channel , MOVIES_GROUP , PROVIDERS_PATH , SERIES_GROUP , TV_GROUP ,\
34
34
async_function , idle_function
35
35
36
36
@@ -127,6 +127,7 @@ def __init__(self, application):
127
127
self .icon_theme = Gtk .IconTheme .get_default ()
128
128
self .manager = Manager (self .settings )
129
129
self .providers = []
130
+ self .favorite_data = []
130
131
self .active_provider = None
131
132
self .active_group = None
132
133
self .active_serie = None
@@ -140,6 +141,8 @@ def __init__(self, application):
140
141
self .mpv = None
141
142
self .ia = IMDb ()
142
143
144
+ self .page_is_loading = False # used to ignore signals while we set widget states
145
+
143
146
self .video_properties = {}
144
147
self .audio_properties = {}
145
148
@@ -262,6 +265,7 @@ def __init__(self, application):
262
265
"audio_properties_label" ,
263
266
"layout_properties_box" ,
264
267
"layout_properties_label" ,
268
+ "favorite_button" ,
265
269
]
266
270
267
271
for name in widget_names :
@@ -293,6 +297,7 @@ def __init__(self, application):
293
297
self .tv_button .connect ("clicked" , self .show_groups , TV_GROUP )
294
298
self .movies_button .connect ("clicked" , self .show_groups , MOVIES_GROUP )
295
299
self .series_button .connect ("clicked" , self .show_groups , SERIES_GROUP )
300
+ self .favorites_button .connect ("clicked" , self .show_favorites )
296
301
self .providers_button .connect ("clicked" , self .open_providers )
297
302
self .preferences_button .connect ("clicked" , self .open_preferences )
298
303
self .go_back_button .connect ("clicked" , self .on_go_back_button )
@@ -317,6 +322,8 @@ def __init__(self, application):
317
322
318
323
self .channels_listbox .connect ("row-activated" , self .on_channel_activated )
319
324
325
+ self .favorite_button .connect ("toggled" , self .on_favorite_button_toggled )
326
+
320
327
# Settings widgets
321
328
self .bind_setting_widget ("user-agent" , self .useragent_entry )
322
329
self .bind_setting_widget ("http-referer" , self .referer_entry )
@@ -329,7 +336,7 @@ def __init__(self, application):
329
336
if os .path .exists (os .path .expanduser ("~/.cache/hypnotix/yt-dlp/yt-dlp" )):
330
337
self .ytdlp_local_version_label .set_text (subprocess .getoutput ("~/.cache/hypnotix/yt-dlp/yt-dlp --version" ))
331
338
self .ytdlp_update_button .connect ("clicked" , self .update_ytdlp )
332
-
339
+
333
340
# Dark mode manager
334
341
# keep a reference to it (otherwise it gets randomly garbage collected)
335
342
self .dark_mode_manager = XApp .DarkModeManager .new (prefer_dark_mode = True )
@@ -507,6 +514,15 @@ def on_category_button_clicked(self, widget, group):
507
514
else :
508
515
self .show_vod (self .active_provider .series )
509
516
517
+ def show_favorites (self , widget ):
518
+ channels = []
519
+ for line in self .favorite_data :
520
+ info , url = line .split (":::" )
521
+ channel = Channel (None , info )
522
+ channel .url = url
523
+ channels .append (channel )
524
+ self .show_channels (channels )
525
+
510
526
def show_channels (self , channels ):
511
527
self .navigate_to ("channels_page" )
512
528
if self .content_type == TV_GROUP :
@@ -835,6 +851,19 @@ def open_keyboard_shortcuts(self, widget):
835
851
window .set_title (_ ("Hypnotix" ))
836
852
window .show ()
837
853
854
+ def on_favorite_button_toggled (self , widget ):
855
+ if self .page_is_loading :
856
+ return
857
+ name = self .active_channel .name
858
+ data = f"{ self .active_channel .info } :::{ self .active_channel .url } "
859
+ if widget .get_active () and data not in self .favorite_data :
860
+ print (f"Adding { name } to favorites" )
861
+ self .favorite_data .append (data )
862
+ elif widget .get_active () == False and data in self .favorite_data :
863
+ print (f"Removing { name } from favorites" )
864
+ self .favorite_data .remove (data )
865
+ self .manager .save_favorites (self .favorite_data )
866
+
838
867
def on_channel_activated (self , box , widget ):
839
868
self .active_channel = widget .channel
840
869
self .play_async (self .active_channel )
@@ -881,6 +910,16 @@ def before_play(self, channel):
881
910
self .label_channel_name .set_text (channel .name )
882
911
self .label_channel_url .set_text (channel .url )
883
912
913
+ self .page_is_loading = True
914
+ data = f"{ channel .info } :::{ channel .url } "
915
+ if data in self .favorite_data :
916
+ self .favorite_button .set_active (True )
917
+ self .favorite_button .set_tooltip_text (_ ("Remove from favorites" ))
918
+ else :
919
+ self .favorite_button .set_active (False )
920
+ self .favorite_button .set_tooltip_text (_ ("Add to favorites" ))
921
+ self .page_is_loading = False
922
+
884
923
@idle_function
885
924
def after_play (self , channel ):
886
925
self .mpv_stack .set_visible_child_name ("player_page" )
@@ -1456,6 +1495,7 @@ def on_key_press_event(self, widget, event):
1456
1495
1457
1496
@async_function
1458
1497
def reload (self , page = None , refresh = False ):
1498
+ self .favorite_data = self .manager .load_favorites ()
1459
1499
self .status (_ ("Loading providers..." ))
1460
1500
self .providers = []
1461
1501
for provider_info in self .settings .get_strv ("providers" ):
0 commit comments