diff --git a/winpython/_vendor/qtpy/QtCore.py b/winpython/_vendor/qtpy/QtCore.py
index c1d81e8f..289fcac2 100644
--- a/winpython/_vendor/qtpy/QtCore.py
+++ b/winpython/_vendor/qtpy/QtCore.py
@@ -24,6 +24,10 @@
del pyqtSignal, pyqtSlot, pyqtProperty, QT_VERSION_STR
elif PYSIDE2:
from PySide2.QtCore import *
+ try: # may be limited to PySide-5.11a1 only
+ from PySide2.QtGui import QStringListModel
+ except:
+ pass
elif PYQT4:
from PyQt4.QtCore import *
# Those are things we inherited from Spyder that fix crazy crashes under
@@ -58,6 +62,7 @@ class QStandardPaths():
HomeLocation = _QDesktopServices.HomeLocation
DataLocation = _QDesktopServices.DataLocation
CacheLocation = _QDesktopServices.CacheLocation
+ writableLocation = _QDesktopServices.storageLocation
# Those are imported from `import *`
del pyqtSignal, pyqtSlot, pyqtProperty, QT_VERSION_STR, qInstallMsgHandler
@@ -88,6 +93,7 @@ class QStandardPaths():
HomeLocation = _QDesktopServices.HomeLocation
DataLocation = _QDesktopServices.DataLocation
CacheLocation = _QDesktopServices.CacheLocation
+ writableLocation = _QDesktopServices.storageLocation
import PySide.QtCore
__version__ = PySide.QtCore.__version__
diff --git a/winpython/_vendor/qtpy/QtGui.py b/winpython/_vendor/qtpy/QtGui.py
index 3dfaff07..071be132 100644
--- a/winpython/_vendor/qtpy/QtGui.py
+++ b/winpython/_vendor/qtpy/QtGui.py
@@ -12,6 +12,7 @@
exposed here. Therefore, you need to treat/use this package as if it were
the ``PyQt5.QtGui`` module.
"""
+import warnings
from . import PYQT5, PYQT4, PYSIDE, PYSIDE2, PythonQtError
@@ -75,10 +76,21 @@
from PyQt4.QtGui import QDesktopServices as _QDesktopServices
class QDesktopServices():
- openUrl = _QDesktopServices.openUrl
- setUrlHandler = _QDesktopServices.setUrlHandler
- unsetUrlHandler = _QDesktopServices.unsetUrlHandler
+ openUrl = _QDesktopServices.openUrl
+ setUrlHandler = _QDesktopServices.setUrlHandler
+ unsetUrlHandler = _QDesktopServices.unsetUrlHandler
+ def __getattr__(self, name):
+ attr = getattr(_QDesktopServices, name)
+
+ new_name = name
+ if name == 'storageLocation':
+ new_name = 'writableLocation'
+ warnings.warn(("Warning QDesktopServices.{} is deprecated in Qt5"
+ "we recommend you use QDesktopServices.{} instead").format(name, new_name),
+ DeprecationWarning)
+ return attr
+ QDesktopServices = QDesktopServices()
elif PYSIDE:
from PySide.QtGui import (QAbstractTextDocumentLayout, QActionEvent, QBitmap,
@@ -126,8 +138,20 @@ class QDesktopServices():
from PySide.QtGui import QDesktopServices as _QDesktopServices
class QDesktopServices():
- openUrl = _QDesktopServices.openUrl
- setUrlHandler = _QDesktopServices.setUrlHandler
- unsetUrlHandler = _QDesktopServices.unsetUrlHandler
+ openUrl = _QDesktopServices.openUrl
+ setUrlHandler = _QDesktopServices.setUrlHandler
+ unsetUrlHandler = _QDesktopServices.unsetUrlHandler
+
+ def __getattr__(self, name):
+ attr = getattr(_QDesktopServices, name)
+
+ new_name = name
+ if name == 'storageLocation':
+ new_name = 'writableLocation'
+ warnings.warn(("Warning QDesktopServices.{} is deprecated in Qt5"
+ "we recommend you use QDesktopServices.{} instead").format(name, new_name),
+ DeprecationWarning)
+ return attr
+ QDesktopServices = QDesktopServices()
else:
raise PythonQtError('No Qt bindings could be found')
diff --git a/winpython/_vendor/qtpy/QtHelp.py b/winpython/_vendor/qtpy/QtHelp.py
new file mode 100644
index 00000000..ca9d93dd
--- /dev/null
+++ b/winpython/_vendor/qtpy/QtHelp.py
@@ -0,0 +1,24 @@
+# -*- coding: utf-8 -*-
+#
+# Copyright © 2009- The Spyder Development Team
+#
+# Licensed under the terms of the MIT License
+# (see LICENSE.txt for details)
+
+"""QtHelp Wrapper."""
+
+import warnings
+
+from . import PYQT5
+from . import PYQT4
+from . import PYSIDE
+from . import PYSIDE2
+
+if PYQT5:
+ from PyQt5.QtHelp import *
+elif PYSIDE2:
+ from PySide2.QtHelp import *
+elif PYQT4:
+ from PyQt4.QtHelp import *
+elif PYSIDE:
+ from PySide.QtHelp import *
diff --git a/winpython/_vendor/qtpy/QtMultimedia.py b/winpython/_vendor/qtpy/QtMultimedia.py
index a20cc3bd..9015ece9 100644
--- a/winpython/_vendor/qtpy/QtMultimedia.py
+++ b/winpython/_vendor/qtpy/QtMultimedia.py
@@ -1,15 +1,14 @@
+import warnings
+
from . import PYQT5
from . import PYQT4
from . import PYSIDE
from . import PYSIDE2
-
if PYQT5:
from PyQt5.QtMultimedia import *
elif PYSIDE2:
- # Current wheels don't have this module
- # from PySide2.QtMultimedia import *
- pass
+ from PySide2.QtMultimedia import *
elif PYQT4:
from PyQt4.QtMultimedia import *
from PyQt4.QtGui import QSound
diff --git a/winpython/_vendor/qtpy/QtSql.py b/winpython/_vendor/qtpy/QtSql.py
new file mode 100644
index 00000000..98520bef
--- /dev/null
+++ b/winpython/_vendor/qtpy/QtSql.py
@@ -0,0 +1,24 @@
+# -*- coding: utf-8 -*-
+# -----------------------------------------------------------------------------
+# Copyright © 2009- The Spyder Development Team
+#
+# Licensed under the terms of the MIT License
+# (see LICENSE.txt for details)
+# -----------------------------------------------------------------------------
+"""Provides QtSql classes and functions."""
+
+# Local imports
+from . import PYQT5, PYSIDE2, PYQT4, PYSIDE, PythonQtError
+
+if PYQT5:
+ from PyQt5.QtSql import *
+elif PYSIDE2:
+ from PySide2.QtSql import *
+elif PYQT4:
+ from PyQt4.QtSql import *
+elif PYSIDE:
+ from PySide.QtSql import *
+else:
+ raise PythonQtError('No Qt bindings could be found')
+
+del PYQT4, PYQT5, PYSIDE, PYSIDE2
diff --git a/winpython/_vendor/qtpy/__init__.py b/winpython/_vendor/qtpy/__init__.py
index 1ade9a8c..54ad5486 100644
--- a/winpython/_vendor/qtpy/__init__.py
+++ b/winpython/_vendor/qtpy/__init__.py
@@ -10,12 +10,13 @@
**QtPy** is a shim over the various Python Qt bindings. It is used to write
Qt binding indenpendent libraries or applications.
-The shim will automatically select the first available API (PyQt5, PyQt4 and
-finally PySide).
+If one of the APIs has already been imported, then it will be used.
-You can force the use of one specific bindings (e.g. if your application is
-using one specific bindings and you need to use library that use QtPy) by
-setting up the ``QT_API`` environment variable.
+Otherwise, the shim will automatically select the first available API (PyQt5,
+PySide2, PyQt4 and finally PySide); in that case, you can force the use of one
+specific bindings (e.g. if your application is using one specific bindings and
+you need to use library that use QtPy) by setting up the ``QT_API`` environment
+variable.
PyQt5
=====
@@ -62,10 +63,23 @@
"""
import os
+import sys
+import warnings
# Version of QtPy
from ._version import __version__
+
+class PythonQtError(Exception):
+ """Error raise if no bindings could be selected"""
+ pass
+
+
+class PythonQtWarning(Warning):
+ """Warning if some features are not implemented in a binding."""
+ pass
+
+
# Qt API environment variable name
QT_API = 'QT_API'
@@ -86,7 +100,9 @@
# Setting a default value for QT_API
os.environ.setdefault(QT_API, 'pyqt5')
+
API = os.environ[QT_API].lower()
+initial_api = API
assert API in (PYQT5_API + PYQT4_API + PYSIDE_API + PYSIDE2_API)
is_old_pyqt = is_pyqt46 = False
@@ -94,15 +110,20 @@
PYQT4 = PYSIDE = PYSIDE2 = False
-class PythonQtError(Exception):
- """Error raise if no bindings could be selected"""
- pass
+if 'PyQt5' in sys.modules:
+ API = 'pyqt5'
+elif 'PySide2' in sys.modules:
+ API = 'pyside2'
+elif 'PyQt4' in sys.modules:
+ API = 'pyqt4'
+elif 'PySide' in sys.modules:
+ API = 'pyside'
if API in PYQT5_API:
try:
- from PyQt5.Qt import PYQT_VERSION_STR as PYQT_VERSION # analysis:ignore
- from PyQt5.Qt import QT_VERSION_STR as QT_VERSION # analysis:ignore
+ from PyQt5.QtCore import PYQT_VERSION_STR as PYQT_VERSION # analysis:ignore
+ from PyQt5.QtCore import QT_VERSION_STR as QT_VERSION # analysis:ignore
PYSIDE_VERSION = None
except ImportError:
API = os.environ['QT_API'] = 'pyside2'
@@ -129,7 +150,7 @@ class PythonQtError(Exception):
sip.setapi('QTextStream', 2)
sip.setapi('QTime', 2)
sip.setapi('QUrl', 2)
- except AttributeError:
+ except (AttributeError, ValueError):
# PyQt < v4.6
pass
from PyQt4.Qt import PYQT_VERSION_STR as PYQT_VERSION # analysis:ignore
@@ -153,12 +174,18 @@ class PythonQtError(Exception):
except ImportError:
raise PythonQtError('No Qt bindings could be found')
+# If a correct API name is passed to QT_API and it could not be found,
+# switches to another and informs through the warning
+if API != initial_api:
+ warnings.warn('Selected binding "{}" could not be found, '
+ 'using "{}"'.format(initial_api, API), RuntimeWarning)
+
API_NAME = {'pyqt5': 'PyQt5', 'pyqt': 'PyQt4', 'pyqt4': 'PyQt4',
'pyside': 'PySide', 'pyside2':'PySide2'}[API]
if PYQT4:
- import sip
- try:
- API_NAME += (" (API v{0})".format(sip.getapi('QString')))
- except AttributeError:
- pass
+ import sip
+ try:
+ API_NAME += (" (API v{0})".format(sip.getapi('QString')))
+ except AttributeError:
+ pass
diff --git a/winpython/_vendor/qtpy/_patch/qheaderview.py b/winpython/_vendor/qtpy/_patch/qheaderview.py
index 99cd20a7..b6baddbb 100644
--- a/winpython/_vendor/qtpy/_patch/qheaderview.py
+++ b/winpython/_vendor/qtpy/_patch/qheaderview.py
@@ -4,6 +4,7 @@
#
# Licensed under the terms of the MIT License
# (see LICENSE.txt for details)
+import warnings
def introduce_renamed_methods_qheaderview(QHeaderView):
@@ -15,8 +16,9 @@ def sectionsClickable(self):
return _isClickable(self)
QHeaderView.sectionsClickable = sectionsClickable
def isClickable(self):
- raise Exception('isClickable is only available in Qt4. Use '
- 'sectionsClickable instead.')
+ warnings.warn('isClickable is only available in Qt4. Use '
+ 'sectionsClickable instead.', stacklevel=2)
+ return _isClickable(self)
QHeaderView.isClickable = isClickable
@@ -28,8 +30,9 @@ def sectionsMovable(self):
return _isMovable(self)
QHeaderView.sectionsMovable = sectionsMovable
def isMovable(self):
- raise Exception('isMovable is only available in Qt4. Use '
- 'sectionsMovable instead.')
+ warnings.warn('isMovable is only available in Qt4. Use '
+ 'sectionsMovable instead.', stacklevel=2)
+ return _isMovable(self)
QHeaderView.isMovable = isMovable
@@ -41,8 +44,9 @@ def sectionResizeMode(self, logicalIndex):
return _resizeMode(self, logicalIndex)
QHeaderView.sectionResizeMode = sectionResizeMode
def resizeMode(self, logicalIndex):
- raise Exception('resizeMode is only available in Qt4. Use '
- 'sectionResizeMode instead.')
+ warnings.warn('resizeMode is only available in Qt4. Use '
+ 'sectionResizeMode instead.', stacklevel=2)
+ return _resizeMode(self, logicalIndex)
QHeaderView.resizeMode = resizeMode
_setClickable = QHeaderView.setClickable
@@ -53,8 +57,9 @@ def setSectionsClickable(self, clickable):
return _setClickable(self, clickable)
QHeaderView.setSectionsClickable = setSectionsClickable
def setClickable(self, clickable):
- raise Exception('setClickable is only available in Qt4. Use '
- 'setSectionsClickable instead.')
+ warnings.warn('setClickable is only available in Qt4. Use '
+ 'setSectionsClickable instead.', stacklevel=2)
+ return _setClickable(self, clickable)
QHeaderView.setClickable = setClickable
@@ -66,8 +71,9 @@ def setSectionsMovable(self, movable):
return _setMovable(self, movable)
QHeaderView.setSectionsMovable = setSectionsMovable
def setMovable(self, movable):
- raise Exception('setMovable is only available in Qt4. Use '
- 'setSectionsMovable instead.')
+ warnings.warn('setMovable is only available in Qt4. Use '
+ 'setSectionsMovable instead.', stacklevel=2)
+ return _setMovable(self, movable)
QHeaderView.setMovable = setMovable
@@ -80,8 +86,9 @@ def setSectionResizeMode(self, *args):
_setResizeMode(self, *args)
QHeaderView.setSectionResizeMode = setSectionResizeMode
def setResizeMode(self, *args):
- raise Exception('setResizeMode is only available in Qt4. Use '
- 'setSectionResizeMode instead.')
+ warnings.warn('setResizeMode is only available in Qt4. Use '
+ 'setSectionResizeMode instead.', stacklevel=2)
+ _setResizeMode(self, *args)
QHeaderView.setResizeMode = setResizeMode
diff --git a/winpython/_vendor/qtpy/_version.py b/winpython/_vendor/qtpy/_version.py
index 0465a17f..3e2a74ac 100644
--- a/winpython/_vendor/qtpy/_version.py
+++ b/winpython/_vendor/qtpy/_version.py
@@ -1,2 +1,2 @@
-version_info = (1, 3, 0)
+version_info = (1, 4, 2)
__version__ = '.'.join(map(str, version_info))
diff --git a/winpython/_vendor/qtpy/tests/test.ui b/winpython/_vendor/qtpy/tests/test.ui
deleted file mode 100644
index 8f0a67c0..00000000
--- a/winpython/_vendor/qtpy/tests/test.ui
+++ /dev/null
@@ -1,35 +0,0 @@
-
-
- Form
-
-
-
- 0
- 0
- 400
- 300
-
-
-
- Form
-
-
- -
-
-
-
-
-
- Ceci n'est pas un bouton
-
-
-
- -
-
-
-
-
-
-
-
-
-
diff --git a/winpython/_vendor/qtpy/tests/test_custom.ui b/winpython/_vendor/qtpy/tests/test_custom.ui
deleted file mode 100644
index f74b5c72..00000000
--- a/winpython/_vendor/qtpy/tests/test_custom.ui
+++ /dev/null
@@ -1,42 +0,0 @@
-
-
- Form
-
-
-
- 0
- 0
- 400
- 300
-
-
-
- Form
-
-
- -
-
-
-
-
-
- Ceci n'est pas un bouton
-
-
-
- -
-
-
-
-
-
-
-
-
- _QComboBoxSubclass
- QComboBox
-
-
-
-
-
-
diff --git a/winpython/_vendor/qtpy/tests/test_patch_qheaderview.py b/winpython/_vendor/qtpy/tests/test_patch_qheaderview.py
index 6c9e6ded..17037f34 100644
--- a/winpython/_vendor/qtpy/tests/test_patch_qheaderview.py
+++ b/winpython/_vendor/qtpy/tests/test_patch_qheaderview.py
@@ -82,17 +82,17 @@ class Model(QAbstractListModel):
# test that the old methods in Qt4 raise exceptions
if PYQT4 or PYSIDE:
- with pytest.raises(Exception):
+ with pytest.warns(UserWarning):
headerview.isClickable()
- with pytest.raises(Exception):
+ with pytest.warns(UserWarning):
headerview.isMovable()
- with pytest.raises(Exception):
+ with pytest.warns(UserWarning):
headerview.resizeMode(0)
- with pytest.raises(Exception):
+ with pytest.warns(UserWarning):
headerview.setClickable(True)
- with pytest.raises(Exception):
- headerview.setMovableClickable(True)
- with pytest.raises(Exception):
+ with pytest.warns(UserWarning):
+ headerview.setMovable(True)
+ with pytest.warns(UserWarning):
headerview.setResizeMode(0, QHeaderView.Interactive)
diff --git a/winpython/_vendor/qtpy/tests/test_qdesktopservice_split.py b/winpython/_vendor/qtpy/tests/test_qdesktopservice_split.py
index bf12927d..472f2df1 100644
--- a/winpython/_vendor/qtpy/tests/test_qdesktopservice_split.py
+++ b/winpython/_vendor/qtpy/tests/test_qdesktopservice_split.py
@@ -1,11 +1,12 @@
+"""Test QDesktopServices split in Qt5."""
+
from __future__ import absolute_import
import pytest
-from qtpy import PYSIDE2
+import warnings
+from qtpy import PYQT4, PYSIDE
-"""Test QDesktopServices split in Qt5."""
-@pytest.mark.skipif(PYSIDE2, reason="It fails on PySide2")
def test_qstandarpath():
"""Test the qtpy.QStandardPaths namespace"""
from qtpy.QtCore import QStandardPaths
@@ -16,13 +17,25 @@ def test_qstandarpath():
with pytest.raises(AttributeError) as excinfo:
QStandardPaths.setUrlHandler
-@pytest.mark.skipif(PYSIDE2, reason="It fails on PySide2")
+
def test_qdesktopservice():
"""Test the qtpy.QDesktopServices namespace"""
from qtpy.QtGui import QDesktopServices
assert QDesktopServices.setUrlHandler is not None
- # Attributes from QStandardPaths shouldn't be in QDesktopServices
- with pytest.raises(AttributeError) as excinfo:
- QDesktopServices.StandardLocation
\ No newline at end of file
+
+@pytest.mark.skipif(not (PYQT4 or PYSIDE), reason="Warning is only raised in old bindings")
+def test_qdesktopservice_qt4_pyside():
+ from qtpy.QtGui import QDesktopServices
+ # Attributes from QStandardPaths should raise a warning when imported
+ # from QDesktopServices
+ with warnings.catch_warnings(record=True) as w:
+ # Cause all warnings to always be triggered.
+ warnings.simplefilter("always")
+ # Try to import QtHelp.
+ QDesktopServices.StandardLocation
+
+ assert len(w) == 1
+ assert issubclass(w[-1].category, DeprecationWarning)
+ assert "deprecated" in str(w[-1].message)
diff --git a/winpython/_vendor/qtpy/tests/test_qthelp.py b/winpython/_vendor/qtpy/tests/test_qthelp.py
new file mode 100644
index 00000000..2b70ca75
--- /dev/null
+++ b/winpython/_vendor/qtpy/tests/test_qthelp.py
@@ -0,0 +1,22 @@
+"""Test for QtHelp namespace."""
+
+from __future__ import absolute_import
+
+import pytest
+
+
+def test_qthelp():
+ """Test the qtpy.QtHelp namespace."""
+ from qtpy import QtHelp
+
+ assert QtHelp.QHelpContentItem is not None
+ assert QtHelp.QHelpContentModel is not None
+ assert QtHelp.QHelpContentWidget is not None
+ assert QtHelp.QHelpEngine is not None
+ assert QtHelp.QHelpEngineCore is not None
+ assert QtHelp.QHelpIndexModel is not None
+ assert QtHelp.QHelpIndexWidget is not None
+ assert QtHelp.QHelpSearchEngine is not None
+ assert QtHelp.QHelpSearchQuery is not None
+ assert QtHelp.QHelpSearchQueryWidget is not None
+ assert QtHelp.QHelpSearchResultWidget is not None
diff --git a/winpython/_vendor/qtpy/tests/test_qtmultimedia.py b/winpython/_vendor/qtpy/tests/test_qtmultimedia.py
index 5561e77b..02b415ff 100644
--- a/winpython/_vendor/qtpy/tests/test_qtmultimedia.py
+++ b/winpython/_vendor/qtpy/tests/test_qtmultimedia.py
@@ -1,12 +1,12 @@
from __future__ import absolute_import
import pytest
-from qtpy import PYSIDE2, QtMultimedia
-@pytest.mark.skipif(PYSIDE2, reason="It fails on PySide2")
def test_qtmultimedia():
"""Test the qtpy.QtMultimedia namespace"""
+ from qtpy import QtMultimedia
+
assert QtMultimedia.QAbstractVideoBuffer is not None
assert QtMultimedia.QAudio is not None
assert QtMultimedia.QAudioDeviceInfo is not None
diff --git a/winpython/_vendor/qtpy/tests/test_qtsql.py b/winpython/_vendor/qtpy/tests/test_qtsql.py
new file mode 100644
index 00000000..1e7404ff
--- /dev/null
+++ b/winpython/_vendor/qtpy/tests/test_qtsql.py
@@ -0,0 +1,24 @@
+from __future__ import absolute_import
+
+import pytest
+from qtpy import QtSql
+
+def test_qtsql():
+ """Test the qtpy.QtSql namespace"""
+ assert QtSql.QSqlDatabase is not None
+ assert QtSql.QSqlDriverCreatorBase is not None
+ assert QtSql.QSqlDriver is not None
+ assert QtSql.QSqlError is not None
+ assert QtSql.QSqlField is not None
+ assert QtSql.QSqlIndex is not None
+ assert QtSql.QSqlQuery is not None
+ assert QtSql.QSqlRecord is not None
+ assert QtSql.QSqlResult is not None
+ assert QtSql.QSqlQueryModel is not None
+ assert QtSql.QSqlRelationalDelegate is not None
+ assert QtSql.QSqlRelation is not None
+ assert QtSql.QSqlRelationalTableModel is not None
+ assert QtSql.QSqlTableModel is not None
+
+ # Following modules are not (yet) part of any wrapper:
+ # QSqlDriverCreator, QSqlDriverPlugin
diff --git a/winpython/_vendor/qtpy/tests/test_qtsvg.py b/winpython/_vendor/qtpy/tests/test_qtsvg.py
index 51b743bb..74d8522e 100644
--- a/winpython/_vendor/qtpy/tests/test_qtsvg.py
+++ b/winpython/_vendor/qtpy/tests/test_qtsvg.py
@@ -1,9 +1,8 @@
from __future__ import absolute_import
import pytest
-from qtpy import PYSIDE2
-@pytest.mark.skipif(PYSIDE2, reason="It fails on PySide2")
+
def test_qtsvg():
"""Test the qtpy.QtSvg namespace"""
from qtpy import QtSvg
@@ -11,4 +10,4 @@ def test_qtsvg():
assert QtSvg.QGraphicsSvgItem is not None
assert QtSvg.QSvgGenerator is not None
assert QtSvg.QSvgRenderer is not None
- assert QtSvg.QSvgWidget is not None
\ No newline at end of file
+ assert QtSvg.QSvgWidget is not None
diff --git a/winpython/_vendor/vendor.txt b/winpython/_vendor/vendor.txt
index 5407b13c..86bb5250 100644
--- a/winpython/_vendor/vendor.txt
+++ b/winpython/_vendor/vendor.txt
@@ -1 +1 @@
-qtpy==1.3.0
\ No newline at end of file
+qtpy==1.4.2
\ No newline at end of file