diff --git a/qutebrowser/config/configtypes.py b/qutebrowser/config/configtypes.py index 4773a1038..ae7fed04e 100644 --- a/qutebrowser/config/configtypes.py +++ b/qutebrowser/config/configtypes.py @@ -26,6 +26,7 @@ import codecs import os.path import sre_constants import itertools +import collections from PyQt5.QtCore import QUrl from PyQt5.QtGui import QColor, QFont @@ -1123,6 +1124,41 @@ class FuzzyUrl(BaseType): return urlutils.fuzzy_url(value, do_search=False) +PaddingValues = collections.namedtuple('PaddingValues', ['top', 'bottom', + 'left', 'right']) + + +class Padding(IntList): + + """Setting for paddings around elements.""" + + def validate(self, value): + self._basic_validation(value) + if not value: + return + try: + vals = self.transform(value) + except (ValueError, TypeError): + raise configexc.ValidationError(value, "must be a list of 1 or 4 " + "integers!") + if None in vals and not self.none_ok: + raise configexc.ValidationError(value, "items may not be empty!") + elems = self.transform(value) + if any(e is not None and e < 0 for e in elems): + raise configexc.ValidationError(value, "Values need to be " + "positive!") + + def transform(self, value): + elems = super().transform(value) + if elems is None: + return elems + if len(elems) == 1: + val = elems[0] + return PaddingValues(val, val, val, val) + else: + return PaddingValues(*elems) + + class Encoding(BaseType): """Setting for a python encoding.""" diff --git a/tests/config/test_configtypes.py b/tests/config/test_configtypes.py index 19491a0af..4219218b1 100644 --- a/tests/config/test_configtypes.py +++ b/tests/config/test_configtypes.py @@ -1549,6 +1549,55 @@ class TestFuzzyUrl: assert klass().transform(val) == expected +class TestPadding: + + """Test Padding.""" + + @pytest.fixture + def klass(self): + return configtypes.Padding + + @pytest.mark.parametrize('val', [ + '', + '0', + '5', + '1,,2,3', + '1,2,3,4', + '1, 2, 3, 4', + ]) + def test_validate_valid(self, klass, val): + klass(none_ok=True).validate(val) + + @pytest.mark.parametrize('val', [ + '', + '1,,2,3', + '0.5', + '-1', + '1,2', + '1,2,3', + '1,2,3,4,5', + '1,2,-1,3', + ]) + def test_validate_invalid(self, klass, val): + with pytest.raises(configexc.ValidationError): + klass().validate(val) + + @pytest.mark.parametrize('val, expected', [ + ('', None), + ('5', (5, 5, 5, 5)), + ('1,2,3,4', (1, 2, 3, 4)), + ]) + def test_transform(self, klass, val, expected): + """Test transforming of values.""" + transformed = klass().transform(val) + assert transformed == expected + if expected is not None: + assert transformed.top == expected[0] + assert transformed.bottom == expected[1] + assert transformed.left == expected[2] + assert transformed.right == expected[3] + + class TestAutoSearch: """Test AutoSearch."""