Send patches - preferably formatted by git format-patch - to patches at archlinux32 dot org.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWerner Llácer <wllacer@gmail.com>2022-02-11 13:22:35 +0100
committerGitHub <noreply@github.com>2022-02-11 13:22:35 +0100
commit5990491292fb1a9b7dbd80af6109d9e71630a75c (patch)
treed13305f24464142cf8ce8c6896345a3078b446f9
parent18e033d2f0554fd568e4cf4cb0da7ecab7c5f202 (diff)
Some refinements to the Menu infraestructure (#962)
* Correct definition of btrfs standard layout * Solve issue #936 * make ask_for_a_timezone as synonym to ask_timezone * Some refining in GeneralMenu secret is now a general function * Revert "Some refining in GeneralMenu" This reverts commit e6e131cb19795e0ddc169e897ae4df57a1c7f9fb. * New version of the FlexibleMenu * Added new functionality to Selector * Created a GeneralMenu class * GlobalMenu is made a child of GeneralMenu * Some refining in GeneralMenu secret is now a general function * log is invoked in GeneralMenu directly * Materialize again _setup_selection_menu_options. Gives more room to play * Callbacks converted as methods Synch() (data area and menu) decoupled from enable() and made general before any run * Only_hd gets a new implementation of the menu flake8 corrections * New version of the FlexibleMenu * Added new functionality to Selector * Created a GeneralMenu class * GlobalMenu is made a child of GeneralMenu * changes from the rebase left dangling * Adapt to PR #874 * Adapted to nationalization framework (PR 893). String still NOT adapted * flake8 complains * Use of archinstall.output_config instead of local copy at swiss.py * Problems with the last merge * git complains * Menu admits now preset values and cursor positioning * Now GeneralMenu moves to the next entry after each selection * flake8 complains * Control of limits for cursor position at GeneralMenu * Make auto cursor positioning optional at GeneralMenu. True for GlobalMenu * Code cleanup after rebase, and flake8 complains
-rw-r--r--archinstall/lib/menu/menu.py46
-rw-r--r--archinstall/lib/menu/selection_menu.py20
-rw-r--r--examples/only_hd.py1
3 files changed, 59 insertions, 8 deletions
diff --git a/archinstall/lib/menu/menu.py b/archinstall/lib/menu/menu.py
index 1811482d..ac075b66 100644
--- a/archinstall/lib/menu/menu.py
+++ b/archinstall/lib/menu/menu.py
@@ -7,7 +7,7 @@ import sys
import logging
class Menu(TerminalMenu):
- def __init__(self, title, p_options, skip=True, multi=False, default_option=None, sort=True):
+ def __init__(self, title, p_options, skip=True, multi=False, default_option=None, sort=True, preset_values=None, cursor_index=None):
"""
Creates a new menu
@@ -29,6 +29,12 @@ class Menu(TerminalMenu):
:param sort: Indicate if the options should be sorted alphabetically before displaying
:type sort: bool
+
+ :param preset_values: Predefined value(s) of the menu. In a multi menu, it selects the options included therein. If the selection is simple, moves the cursor to the position of the value
+ :type preset_values: str or list
+
+ :param cursor_index: The position where the cursor will be located. If it is not in range (number of elements of the menu) it goes to the first position
+ :type cursor_index: int
"""
# we guarantee the inmutability of the options outside the class.
# an unknown number of iterables (.keys(),.values(),generator,...) can't be directly copied, in this case
@@ -61,6 +67,7 @@ class Menu(TerminalMenu):
self.skip = skip
self.default_option = default_option
self.multi = multi
+ self.preselection(preset_values,cursor_index)
menu_title = f'\n{title}\n\n'
@@ -86,7 +93,9 @@ class Menu(TerminalMenu):
cycle_cursor=True,
clear_screen=True,
multi_select=multi,
- show_search_hint=True
+ show_search_hint=True,
+ preselected_entries=self.preset_values,
+ cursor_index=self.cursor_index
)
def _show(self):
@@ -114,3 +123,36 @@ class Menu(TerminalMenu):
return self.run()
return ret
+
+ def set_cursor_pos(self,pos :int):
+ if pos and 0 < pos < len(self._menu_entries):
+ self._view.active_menu_index = pos
+ else:
+ self._view.active_menu_index = 0 # we define a default
+
+ def set_cursor_pos_entry(self,value :str):
+ pos = self._menu_entries.index(value)
+ self.set_cursor_pos(pos)
+
+ def preselection(self,preset_values :list = [],cursor_index :int = None):
+ def from_preset_to_cursor():
+ if preset_values:
+ if isinstance(preset_values,str):
+ self.cursor_index = self.menu_options.index(preset_values)
+ else: # should return an error, but this is smoother
+ self.cursor_index = self.menu_options.index(preset_values[0])
+
+ self.preset_values = preset_values
+ self.cursor_index = cursor_index
+ if preset_values and cursor_index is None:
+ from_preset_to_cursor()
+ if preset_values and not self.multi: # Not supported by the infraestructure
+ self.preset_values = None
+ from_preset_to_cursor()
+
+ if self.default_option and self.multi:
+ if isinstance(preset_values,str) and self.default_option == preset_values:
+ self.preset_values = f"{preset_values} (default)"
+ elif isinstance(preset_values,(list,tuple)) and self.default_option in preset_values:
+ idx = preset_values.index(self.default_option)
+ self.preset_values[idx] = f"{preset_values[idx]} (default)"
diff --git a/archinstall/lib/menu/selection_menu.py b/archinstall/lib/menu/selection_menu.py
index 0be2a7e8..afa713ba 100644
--- a/archinstall/lib/menu/selection_menu.py
+++ b/archinstall/lib/menu/selection_menu.py
@@ -1,6 +1,7 @@
from __future__ import annotations
import sys
import logging
+
from typing import Callable, Any, List, Iterator
from .menu import Menu
@@ -32,7 +33,6 @@ from ..user_interaction import select_profile
from ..user_interaction import select_archinstall_language
from ..translation import Translation
-
class Selector:
def __init__(
self,
@@ -165,19 +165,22 @@ class Selector:
if status and not self.is_enabled():
self.set_enabled(True)
-
class GeneralMenu:
- def __init__(self, data_store :dict = None):
+ def __init__(self, data_store :dict = None, auto_cursor=False):
"""
Create a new selection menu.
:param data_store: Area (Dict) where the resulting data will be held. At least an entry for each option. Default area is self._data_store (not preset in the call, due to circular references
:type data_store: Dict
+ :param auto_cursor: Boolean which determines if the cursor stays on the first item (false) or steps each invocation of a selection entry (true)
+ :type auto_cursor: bool
+
"""
self._translation = Translation.load_nationalization()
self.is_context_mgr = False
self._data_store = data_store if data_store is not None else {}
+ self.auto_cursor = auto_cursor
self._menu_options = {}
self._setup_selection_menu_options()
@@ -247,14 +250,18 @@ class GeneralMenu:
# we synch all the options just in case
for item in self.list_options():
self.synch(item)
+ cursor_pos = None
while True:
# Before continuing, set the preferred keyboard layout/language in the current terminal.
# This will just help the user with the next following questions.
self._set_kb_language()
enabled_menus = self._menus_to_enable()
menu_text = [m.text for m in enabled_menus.values()]
- selection = Menu('Set/Modify the below options', menu_text, sort=False).run()
- if selection:
+ selection = Menu('Set/Modify the below options', menu_text, sort=False, cursor_index=cursor_pos).run()
+ if selection and self.auto_cursor:
+ cursor_pos = menu_text.index(selection) + 1 # before the strip otherwise fails
+ if cursor_pos >= len(menu_text):
+ cursor_pos = len(menu_text) - 1
selection = selection.strip()
if selection:
# if this calls returns false, we exit the menu. We allow for an callback for special processing on realeasing control
@@ -294,6 +301,7 @@ class GeneralMenu:
result = None
if selector.func:
+ # TODO insert code to allow selector functions with preset value
result = selector.func()
self._menu_options[selector_name].set_current_selection(result)
self._data_store[selector_name] = result
@@ -399,7 +407,7 @@ class GeneralMenu:
class GlobalMenu(GeneralMenu):
def __init__(self,data_store):
- super().__init__(data_store=data_store)
+ super().__init__(data_store=data_store, auto_cursor=True)
def _setup_selection_menu_options(self):
self._menu_options['archinstall-language'] = \
diff --git a/examples/only_hd.py b/examples/only_hd.py
index c0364cd1..5d081b14 100644
--- a/examples/only_hd.py
+++ b/examples/only_hd.py
@@ -1,3 +1,4 @@
+
import logging
import os
import pathlib