Skip to content

Commit

Permalink
- Version 0.7.9
Browse files Browse the repository at this point in the history
- implemented search function for config windows
- fixed history cycling
- updated docs
  • Loading branch information
s-n-g committed Jul 15, 2019
1 parent d3f1c9b commit d04bac3
Show file tree
Hide file tree
Showing 9 changed files with 85 additions and 47 deletions.
5 changes: 4 additions & 1 deletion Changelog
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
2019-07-09 s-n-g
2019-07-15 s-n-g
* Searching is now available on any window presenting a list of items
* Transparency indication presentation always reflects setting
* A locked session is indicated next to PyRadio version
* Adding "Top" link to html files
* Docs updated

2019-07-08 s-n-g

Expand Down
4 changes: 1 addition & 3 deletions README.html
Original file line number Diff line number Diff line change
Expand Up @@ -236,10 +236,8 @@ <h2 id="search-function">Search function <span style="padding-left: 10px;"><sup
<p>On any window presenting a list of items (stations, playlists, themes) a <strong>search function</strong> is available by pressing “<strong>/</strong>”.</p>
<p>The <em>Search Window</em> supports normal and extend editing and in session history.</p>
<p>One can always get help by pressing the “<strong>?</strong>” key.</p>
<p>The search will be case insensitive under <strong>python 3</strong>; it will be case sensitive under <strong>python 2</strong>.</p>
<p>After a search term has been successfully found, next occurrence can be obtained using the “<strong>n</strong>” key and previous occurrence can be obtained using the “<strong>N</strong>” key.</p>
<p>After a search term has been successfully found (search is case insensitive), next occurrence can be obtained using the “<strong>n</strong>” key and previous occurrence can be obtained using the “<strong>N</strong>” key.</p>
<p style="margin: 1.5em 4em 0 4em; text-indent: -2.5em;"><strong>Note:</strong> <strong>Python 2</strong> users are confined in typing ASCII characters only.</p>
<p style="margin: 1.5em 4em 0 4em; text-indent: -2.5em;"><strong>Note:</strong> Currently, the <strong>search function</strong> is available on the stations’ and playlists’ and themes’ window only.</p>
<h2 id="pyradio-themes">PyRadio Themes <span style="padding-left: 10px;"><sup style="font-size: 50%"><a href="#" title="Go to top of the page">Top</a></sup></style></h2>
<p><strong>PyRadio</strong> comes with 6 preconfigured (hard coded) themes:</p>
<ol type="1">
Expand Down
6 changes: 1 addition & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -338,14 +338,10 @@ The *Search Window* supports normal and extend editing and in session history.

One can always get help by pressing the "**?**" key.

The search will be case insensitive under **python 3**; it will be case sensitive under **python 2**.

After a search term has been successfully found, next occurrence can be obtained using the "**n**" key and previous occurrence can be obtained using the "**N**" key.
After a search term has been successfully found (search is case insensitive), next occurrence can be obtained using the "**n**" key and previous occurrence can be obtained using the "**N**" key.

**Note:** **Python 2** users are confined in typing ASCII characters only.

**Note:** Currently, the **search function** is available on the stations' and playlists' and themes' window only.

## PyRadio Themes

**PyRadio** comes with 6 preconfigured (hard coded) themes:
Expand Down
7 changes: 1 addition & 6 deletions pyradio.1
Original file line number Diff line number Diff line change
Expand Up @@ -350,16 +350,11 @@ The \fISearch Window\fR supports normal and extend editing and in session histor

One can always get help by pressing the "\fI?\fR" key.

The search will be case insensitive under \fBpython 3\fR; it will be case sensitive under \fBpython 2\fR.

After a search term has been successfully found, next occurrence can be obtained using the "\fIn\fR" key and previous occurrence can be obtained using the "\fIN\fR" key.
After a search term has been successfully found (search is case insensitive), next occurrence can be obtained using the "\fIn\fR" key and previous occurrence can be obtained using the "\fIN\fR" key.

.IP \fBNote\fR
\fBPython 2\fR users are confined in typing ASCII characters only.

.IP \fBNote\fR
Currently, the \fBsearch function\fR is available on the stations', playlists' and themes' window only.

.SH PYRADIO THEMES
.PP

Expand Down
2 changes: 1 addition & 1 deletion pyradio/__init__.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
" pyradio -- Console radio player. "

version_info = (0, 7, 8)
version_info = (0, 7, 9)

__version__ = version = '.'.join(map(str, version_info))
__project__ = __name__
Expand Down
20 changes: 13 additions & 7 deletions pyradio/edit.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@ class PyRadioSearch(SimpleCursesLineEdit):

def __init__(self, parent, begin_y, begin_x, **kwargs):
SimpleCursesLineEdit.__init__(self, parent, begin_y, begin_x,
key_up_function_handler=self._get_history_next,
key_down_function_handler=self._get_history_previous,
key_up_function_handler=self._get_history_previous,
key_down_function_handler=self._get_history_next,
**kwargs)
if version_info < (3, 0):
self._range_command='xrange'
Expand Down Expand Up @@ -64,13 +64,13 @@ def _get_history_previous(self):
def get_next(self, a_list, start=0, stop=None):
if self.string:
for n in eval(self._range_command)(start, len(a_list)):
if self.string.lower() in a_list[n][0].lower():
if self.string.lower() in self._get_string(a_list[n]):
if logger.isEnabledFor(logging.DEBUG):
logger.debug('forward search term "{0}" found at {1}'.format(self.string, n))
return n
""" if not found start from list top """
for n in eval(self._range_command)(0, start):
if self.string.lower() in a_list[n][0].lower():
if self.string.lower() in self._get_string(a_list[n]):
if logger.isEnabledFor(logging.DEBUG):
logger.debug('forward search term "{0}" found at {1}'.format(self.string, n))
return n
Expand All @@ -84,13 +84,13 @@ def get_next(self, a_list, start=0, stop=None):
def get_previous(self, a_list, start=0, stop=None):
if self.string:
for n in eval(self._range_command)(start, -1, -1):
if self.string.lower() in a_list[n][0].lower():
if self.string.lower() in self._get_string(a_list[n]):
if logger.isEnabledFor(logging.DEBUG):
logger.debug('backward search term "{0}" found at {1}'.format(self.string, n))
return n
""" if not found start from list end """
for n in eval(self._range_command)(len(a_list) - 1, start, -1):
if self.string.lower() in a_list[n][0].lower():
if self.string.lower() in self._get_string(a_list[n]):
if logger.isEnabledFor(logging.DEBUG):
logger.debug('backward search term "{0}" found at {1}'.format(self.string, n))
return n
Expand All @@ -106,4 +106,10 @@ def print_not_found(self):
self._edit_win.refresh()
sleep(.3)
self.refreshEditWindow()


def _get_string(self, item):
if isinstance(item, str):
return item.lower()
else:
return item[0].lower()

60 changes: 48 additions & 12 deletions pyradio/radio.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
# Ben Dowling - 2009 - 2010
# Kirill Klenov - 2012
# Peter Stevenson (2E0PGS) - 2018
# Spiros Georgaras - 2018
# Spiros Georgaras - 2018, 2019

import curses
import threading
Expand Down Expand Up @@ -77,6 +77,9 @@ class PyRadio(object):
ord(','), ord('+'), ord('-'),
ord('?'), ord('#'), curses.KEY_RESIZE)

""" Characters to be "ignored" by windows that support search"""
_chars_to_bypass_for_search = (ord('/'), ord('n'), ord('N'))

# Number of stations to change with the page up/down keys
pageChange = 5

Expand Down Expand Up @@ -208,6 +211,8 @@ def __init__(self, pyradio_config, play=False, req_player='', theme=''):
self.ws.NORMAL_MODE: self.ws.SEARCH_NORMAL_MODE,
self.ws.PLAYLIST_MODE: self.ws.SEARCH_PLAYLIST_MODE,
self.ws.THEME_MODE: self.ws.SEARCH_THEME_MODE,
self.ws.SELECT_PLAYLIST_MODE: self.ws.SEARCH_SELECT_PLAYLIST_MODE,
self.ws.SELECT_STATION_MODE: self.ws.SEARCH_SELECT_STATION_MODE,
}
# search modes opened from main windows
self.search_main_window_modes = (
Expand Down Expand Up @@ -507,9 +512,6 @@ def run(self):
lambda: self.stop_update_notification_thread))
self._update_notification_thread.start()

""" set up stations search """
self._give_me_a_search_class(self.ws.operation_mode)

#signal.signal(signal.SIGINT, self.ctrl_c_handler)
self.log.write('Selected player: {}'.format(self._format_player_string()), help_msg=True)
#self.log.write_right('Press ? for help')
Expand Down Expand Up @@ -558,6 +560,10 @@ def _give_me_a_search_class(self, operation_mode):
edit_color = curses.color_pair(5),
cursor_color = curses.color_pair(6))
self.search = self._search_classes[self._mode_to_search[operation_mode]]
if self.ws.previous_operation_mode == self.ws.CONFIG_MODE:
self.search.box_color = curses.color_pair(3)
else:
self.search.box_color = curses.color_pair(5)

def ctrl_c_handler(self, signum, frame):
self.ctrl_c_pressed = True
Expand Down Expand Up @@ -800,7 +806,6 @@ def _show_theme_selector(self, changed_from_config=False):
self.jumpnr = ''
self._random_requested = False
self._theme_selector = None
self._give_me_a_search_class(self.ws.THEME_MODE)
#if logger.isEnabledFor(logging.ERROR):
# logger.error('DE\n\nself._theme = {0}\nself._theme_name = {1}\nself._cnf.theme = {2}\n\n'.format(self._theme, self._theme_name, self._cnf.theme))
self._theme_selector = PyRadioThemeSelector(self.bodyWin, self._cnf, self._theme,
Expand Down Expand Up @@ -1068,7 +1073,7 @@ def _show_search_help(self):
^U |Clear line.
DEL|,|^D |Delete character.
Backspace|,|^H |Backspace (delete previous character).
Up|,|^N| / |Down|,|^P |Get previous / next history item.
Up|,|^P| / |Down|,|^N |Get previous / next history item.
Enter| / |Esc |Perform / cancel search.
|Managing player volume does not work in search mode.
Expand Down Expand Up @@ -1108,6 +1113,7 @@ def _show_config_playlist_help(self):
g| / |<n>G |Jump to first or n-th / last playlist.
Enter|,|Space|,
Right|,|l |Select default playlist.
/| / |n| / |N |Search, go to next / previous result.
r |Revert to saved value.
Esc|,|q|,|Left|,|h |Canel.
%_Player Keys_
Expand All @@ -1122,6 +1128,7 @@ def _show_config_station_help(self):
M |Jump to the middle of the list.
Enter|,|Space|,
Right|,|l |Select default station.
/| / |n| / |N |Search, go to next / previous result.
r |Revert to saved value.
Esc|,|q|,|Left|,|h |Canel.
%_Player Keys_
Expand Down Expand Up @@ -1372,7 +1379,6 @@ def _print_update_notification(self):
is_message=True)
self._update_version = ''


def _align_stations_and_refresh(self, cur_mode):
need_to_scan_playlist = False
""" refresh reference """
Expand Down Expand Up @@ -1482,7 +1488,6 @@ def _open_playlist(self):
self._show_help(txt, self.ws.NORMAL_MODE, caption=' ', prompt=' ', is_message=True)
self.selections[self.ws.operation_mode] = [self.selection, self.startPos, self.playing, self._cnf.stations]
self.ws.window_mode = self.ws.PLAYLIST_MODE
self._give_me_a_search_class(self.ws.PLAYLIST_MODE)
self.selection, self.startPos, self.playing, self.stations = self.selections[self.ws.operation_mode]
self.number_of_items, self.playing = self.readPlaylists()
self.stations = self._cnf.playlists
Expand Down Expand Up @@ -1768,13 +1773,21 @@ def _apply_main_windows(ret):
_apply_main_windows(ret)
elif self.ws.operation_mode == self.ws.THEME_MODE:
self._theme_selector.set_theme(self._theme_selector._themes[ret])
elif self.ws.operation_mode == self.ws.SELECT_PLAYLIST_MODE:
self._playlist_select_win.setPlaylistById(ret, adjust=True)
elif self.ws.operation_mode == self.ws.SELECT_STATION_MODE:
self._station_select_win.setPlaylistById(ret, adjust=True)
self.refreshBody()

else:
if self.ws.operation_mode in self.search_main_window_modes:
_apply_main_windows(ret)
elif self.ws.previous_operation_mode == self.ws.THEME_MODE:
self._theme_selector.set_theme(self._theme_selector._themes[ret])
elif self.ws.previous_operation_mode == self.ws.SELECT_PLAYLIST_MODE:
self._playlist_select_win.setPlaylistById(ret, adjust=True)
elif self.ws.previous_operation_mode == self.ws.SELECT_STATION_MODE:
self._station_select_win.setPlaylistById(ret, adjust=True)
self.ws.close_window()
self.refreshBody()

Expand Down Expand Up @@ -1992,7 +2005,8 @@ def keypress(self, char):
return

elif self.ws.operation_mode == self.ws.SELECT_PLAYLIST_MODE:
if char not in self._chars_to_bypass:
if char not in self._chars_to_bypass and \
char not in self._chars_to_bypass_for_search:
ret, ret_playlist = self._playlist_select_win.keypress(char)
if ret >= 0:
if ret == 0:
Expand All @@ -2008,7 +2022,8 @@ def keypress(self, char):
return

elif self.ws.operation_mode == self.ws.SELECT_STATION_MODE:
if char not in self._chars_to_bypass:
if char not in self._chars_to_bypass and \
char not in self._chars_to_bypass_for_search:
ret, ret_station = self._station_select_win.keypress(char)
if ret >= 0:
if ret == 0:
Expand Down Expand Up @@ -2043,7 +2058,8 @@ def keypress(self, char):

elif self.ws.operation_mode == self.ws.THEME_MODE:
if char not in self._chars_to_bypass and \
char not in (ord('T'), ord('/'), ord('n'), ord('N'), ):
char not in self._chars_to_bypass_for_search and \
char not in (ord('T'),):
theme_id, save_theme = self._theme_selector.keypress(char)

#if self._cnf.theme_not_supported:
Expand Down Expand Up @@ -2114,6 +2130,7 @@ def keypress(self, char):
self.jumpnr = ''
self._random_requested = False
#self.search.string = '부'
self._give_me_a_search_class(self.ws.operation_mode)
self.search.show(self.bodyWin)
self.ws.operation_mode = self._search_modes[self.ws.operation_mode]
return
Expand All @@ -2133,6 +2150,13 @@ def keypress(self, char):
elif self.ws.operation_mode == self.ws.THEME_MODE:
self._search_list = self._theme_selector._themes
sel = self._theme_selector.selection + 1
elif self.ws.operation_mode == self.ws.SELECT_PLAYLIST_MODE:
self._search_list = self._playlist_select_win._items
sel = self._playlist_select_win._selected_playlist_id + 1
elif self.ws.operation_mode == self.ws.SELECT_STATION_MODE:
self._search_list = self._station_select_win._items
sel = self._station_select_win._selected_playlist_id + 1

if self.search.string:
if sel == len(self._search_list):
sel = 0
Expand All @@ -2157,6 +2181,13 @@ def keypress(self, char):
elif self.ws.operation_mode == self.ws.THEME_MODE:
self._search_list = self._theme_selector._themes
sel = self._theme_selector.selection - 1
elif self.ws.operation_mode == self.ws.SELECT_PLAYLIST_MODE:
self._search_list = self._playlist_select_win._items
sel = self._playlist_select_win._selected_playlist_id - 1
elif self.ws.operation_mode == self.ws.SELECT_STATION_MODE:
self._search_list = self._station_select_win._items
sel = self._station_select_win._selected_playlist_id - 1

if self.search.string:
if sel < 0:
sel = len(self._search_list) - 1
Expand All @@ -2178,12 +2209,17 @@ def keypress(self, char):
elif self.ws.previous_operation_mode == self.ws.THEME_MODE:
self._search_list = self._theme_selector._themes
sel = self._theme_selector.selection + 1
elif self.ws.previous_operation_mode == self.ws.SELECT_PLAYLIST_MODE:
self._search_list = self._playlist_select_win._items
sel = self._playlist_select_win._selected_playlist_id + 1
elif self.ws.previous_operation_mode == self.ws.SELECT_STATION_MODE:
self._search_list = self._station_select_win._items
sel = self._station_select_win._selected_playlist_id + 1

# perform search
if sel == len(self._search_list):
sel = 0
ret = self.search.get_next(self._search_list, sel)
logger.error('DE ret = {}'.format(ret))
if ret is None:
if self.search.string:
self.search.print_not_found()
Expand Down
8 changes: 4 additions & 4 deletions pyradio/simple_curses_widgets.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ class SimpleCursesLineEdit(object):
focused = True
_focused = True

_max_width = 0

log = None
_log_file = ''
Expand Down Expand Up @@ -242,6 +243,7 @@ def keypress(self, win, char):
""" ESCAPE """
self._string = ''
self._curs_pos = 0
self._input_history.reset_index()
return -1
else:
if self.log is not None:
Expand Down Expand Up @@ -491,11 +493,9 @@ def return_history(self, direction):
if self._history:
self._active_history_index += direction
if self._active_history_index <= -1:
self._active_history_index = -1
return ''
self._active_history_index = len(self._history) - 1
elif self._active_history_index >= len(self._history):
self._active_history_index = len(self._history)
return ''
self._active_history_index = 0
ret = self._history[self._active_history_index]
return ret
return ''
Expand Down
20 changes: 12 additions & 8 deletions pyradio/window_stack.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,16 @@ class Window_Stack_Constants(object):
SEARCH_NORMAL_MODE = 2
SEARCH_PLAYLIST_MODE = 3
SEARCH_THEME_MODE = 4
CONFIG_MODE = 5
SELECT_PLAYER_MODE = 6
SELECT_ENCODING_MODE = 7
SELECT_PLAYLIST_MODE = 8
SELECT_STATION_MODE = 9
SELECT_STATION_ENCODING_MODE = 10
NEW_THEME_MODE = 11
EDIT_THEME_MODE = 12
SEARCH_SELECT_PLAYLIST_MODE = 5
SEARCH_SELECT_STATION_MODE = 6
CONFIG_MODE = 7
SELECT_PLAYER_MODE = 8
SELECT_ENCODING_MODE = 9
SELECT_PLAYLIST_MODE = 10
SELECT_STATION_MODE = 11
SELECT_STATION_ENCODING_MODE = 12
NEW_THEME_MODE = 13
EDIT_THEME_MODE = 14
REMOVE_STATION_MODE = 50
SAVE_PLAYLIST_MODE = 51
ASK_TO_SAVE_PLAYLIST_WHEN_OPENING_PLAYLIST_MODE = 52
Expand Down Expand Up @@ -64,6 +66,8 @@ class Window_Stack_Constants(object):
SEARCH_NORMAL_MODE: 'SEARCH_NORMAL_MODE',
SEARCH_PLAYLIST_MODE: 'SEARCH_PLAYLIST_MODE',
SEARCH_THEME_MODE: 'SEARCH_THEME_MODE',
SEARCH_SELECT_PLAYLIST_MODE: 'SEARCH_SELECT_PLAYLIST_MODE',
SEARCH_SELECT_STATION_MODE: 'SEARCH_SELECT_STATION_MODE',
CONFIG_MODE: 'CONFIG_MODE',
SELECT_PLAYER_MODE: 'SELECT_PLAYER_MODE',
SELECT_ENCODING_MODE: 'SELECT_ENCODING_MODE',
Expand Down

0 comments on commit d04bac3

Please sign in to comment.