Skip to content

Commit

Permalink
Introduce NULL QVariant to PyQt5
Browse files Browse the repository at this point in the history
  • Loading branch information
m-kuhn committed May 13, 2016
1 parent f48d043 commit 89b7a4a
Show file tree
Hide file tree
Showing 8 changed files with 281 additions and 110 deletions.
199 changes: 99 additions & 100 deletions cmake/SIPMacros.cmake
Expand Up @@ -40,105 +40,104 @@ SET(SIP_TAGS)
SET(SIP_CONCAT_PARTS 8)
SET(SIP_DISABLE_FEATURES)
SET(SIP_EXTRA_OPTIONS)

MACRO(ADD_SIP_PYTHON_MODULE MODULE_NAME MODULE_SIP)

SET(EXTRA_LINK_LIBRARIES ${ARGN})

STRING(REPLACE "." "/" _x ${MODULE_NAME})
GET_FILENAME_COMPONENT(_parent_module_path ${_x} PATH)
GET_FILENAME_COMPONENT(_child_module_name ${_x} NAME)

GET_FILENAME_COMPONENT(_module_path ${MODULE_SIP} PATH)
GET_FILENAME_COMPONENT(_abs_module_sip ${MODULE_SIP} ABSOLUTE)

# We give this target a long logical target name.
# (This is to avoid having the library name clash with any already
# install library names. If that happens then cmake dependency
# tracking get confused.)
STRING(REPLACE "." "_" _logical_name ${MODULE_NAME})
SET(_logical_name "python_module_${_logical_name}")

FILE(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/${_module_path}) # Output goes in this dir.

SET(_sip_includes)
FOREACH (_inc ${SIP_INCLUDES})
GET_FILENAME_COMPONENT(_abs_inc ${_inc} ABSOLUTE)
LIST(APPEND _sip_includes -I ${_abs_inc})
ENDFOREACH (_inc )

SET(_sip_tags)
FOREACH (_tag ${SIP_TAGS})
LIST(APPEND _sip_tags -t ${_tag})
ENDFOREACH (_tag)

SET(_sip_x)
FOREACH (_x ${SIP_DISABLE_FEATURES})
LIST(APPEND _sip_x -x ${_x})
ENDFOREACH (_x ${SIP_DISABLE_FEATURES})

SET(_message "-DMESSAGE=Generating CPP code for module ${MODULE_NAME}")
SET(_sip_output_files)
FOREACH(CONCAT_NUM RANGE 0 ${SIP_CONCAT_PARTS} )
IF( ${CONCAT_NUM} LESS ${SIP_CONCAT_PARTS} )
SET(_sip_output_files ${_sip_output_files} ${CMAKE_CURRENT_BINARY_DIR}/${_module_path}/sip${_child_module_name}part${CONCAT_NUM}.cpp )
ENDIF( ${CONCAT_NUM} LESS ${SIP_CONCAT_PARTS} )
ENDFOREACH(CONCAT_NUM RANGE 0 ${SIP_CONCAT_PARTS} )

# Suppress warnings
IF(PEDANTIC)
IF(MSVC)
# 4996 deprecation warnings (bindings re-export deprecated methods)
# 4701 potentially uninitialized variable used (sip generated code)
# 4702 unreachable code (sip generated code)
ADD_DEFINITIONS( /wd4996 /wd4701 /wd4702 )
ELSE(MSVC)
# disable all warnings
ADD_DEFINITIONS( -w -Wno-deprecated-declarations )
IF(NOT APPLE)
ADD_DEFINITIONS( -fpermissive )
ENDIF(NOT APPLE)
ENDIF(MSVC)
ENDIF(PEDANTIC)


SET(SIPCMD ${SIP_BINARY_PATH} ${_sip_tags} -w -e ${_sip_x} ${SIP_EXTRA_OPTIONS} -j ${SIP_CONCAT_PARTS} -c ${CMAKE_CURRENT_BINARY_DIR}/${_module_path} ${_sip_includes} ${_abs_module_sip})

ADD_CUSTOM_COMMAND(
OUTPUT ${_sip_output_files}
COMMAND ${CMAKE_COMMAND} -E echo ${message}
COMMAND ${CMAKE_COMMAND} -E touch ${_sip_output_files}
COMMAND ${SIPCMD}
DEPENDS ${_abs_module_sip} ${SIP_EXTRA_FILES_DEPEND}
)
# not sure if type MODULE could be uses anywhere, limit to cygwin for now
IF (CYGWIN OR APPLE)
ADD_LIBRARY(${_logical_name} MODULE ${_sip_output_files} )
ELSE (CYGWIN OR APPLE)
ADD_LIBRARY(${_logical_name} SHARED ${_sip_output_files} )
ENDIF (CYGWIN OR APPLE)
IF (NOT APPLE)
TARGET_LINK_LIBRARIES(${_logical_name} ${PYTHON_LIBRARY})
ENDIF (NOT APPLE)
TARGET_LINK_LIBRARIES(${_logical_name} ${EXTRA_LINK_LIBRARIES})
IF (APPLE)
SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES LINK_FLAGS "-undefined dynamic_lookup")
ENDIF (APPLE)
SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES PREFIX "" OUTPUT_NAME ${_child_module_name})

IF (WIN32)
SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES SUFFIX ".pyd")
ENDIF (WIN32)

IF(WIN32)
GET_TARGET_PROPERTY(_runtime_output ${_logical_name} RUNTIME_OUTPUT_DIRECTORY)
ADD_CUSTOM_COMMAND(TARGET ${_logical_name} POST_BUILD
COMMAND ${CMAKE_COMMAND} -E echo "Copying extension ${_child_module_name}"
COMMAND ${CMAKE_COMMAND} -E copy_if_different "$<TARGET_FILE:${_logical_name}>" "${_runtime_output}/${_child_module_name}.pyd"
DEPENDS ${_logical_name}
SET(SIP_EXTRA_OBJECTS)

MACRO(GENERATE_SIP_PYTHON_MODULE_CODE MODULE_NAME MODULE_SIP CPP_FILES)
STRING(REPLACE "." "/" _x ${MODULE_NAME})
GET_FILENAME_COMPONENT(_parent_module_path ${_x} PATH)
GET_FILENAME_COMPONENT(_child_module_name ${_x} NAME)

GET_FILENAME_COMPONENT(_module_path ${MODULE_SIP} PATH)
GET_FILENAME_COMPONENT(_abs_module_sip ${MODULE_SIP} ABSOLUTE)

FILE(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/${_module_path}) # Output goes in this dir.

SET(_sip_includes)
FOREACH (_inc ${SIP_INCLUDES})
GET_FILENAME_COMPONENT(_abs_inc ${_inc} ABSOLUTE)
LIST(APPEND _sip_includes -I ${_abs_inc})
ENDFOREACH (_inc )

SET(_sip_tags)
FOREACH (_tag ${SIP_TAGS})
LIST(APPEND _sip_tags -t ${_tag})
ENDFOREACH (_tag)

SET(_sip_x)
FOREACH (_x ${SIP_DISABLE_FEATURES})
LIST(APPEND _sip_x -x ${_x})
ENDFOREACH (_x ${SIP_DISABLE_FEATURES})

SET(_message "-DMESSAGE=Generating CPP code for module ${MODULE_NAME}")
SET(_sip_output_files)
FOREACH(CONCAT_NUM RANGE 0 ${SIP_CONCAT_PARTS} )
IF( ${CONCAT_NUM} LESS ${SIP_CONCAT_PARTS} )
SET(_sip_output_files ${_sip_output_files} ${CMAKE_CURRENT_BINARY_DIR}/${_module_path}/sip${_child_module_name}part${CONCAT_NUM}.cpp )
ENDIF( ${CONCAT_NUM} LESS ${SIP_CONCAT_PARTS} )
ENDFOREACH(CONCAT_NUM RANGE 0 ${SIP_CONCAT_PARTS} )

# Suppress warnings
IF(PEDANTIC)
IF(MSVC)
# 4996 deprecation warnings (bindings re-export deprecated methods)
# 4701 potentially uninitialized variable used (sip generated code)
# 4702 unreachable code (sip generated code)
ADD_DEFINITIONS( /wd4996 /wd4701 /wd4702 )
ELSE(MSVC)
# disable all warnings
ADD_DEFINITIONS( -w -Wno-deprecated-declarations )
IF(NOT APPLE)
ADD_DEFINITIONS( -fpermissive )
ENDIF(NOT APPLE)
ENDIF(MSVC)
ENDIF(PEDANTIC)

SET(SIPCMD ${SIP_BINARY_PATH} ${_sip_tags} -w -e ${_sip_x} ${SIP_EXTRA_OPTIONS} -j ${SIP_CONCAT_PARTS} -c ${CMAKE_CURRENT_BINARY_DIR}/${_module_path} ${_sip_includes} ${_abs_module_sip})

ADD_CUSTOM_COMMAND(
OUTPUT ${_sip_output_files}
COMMAND ${CMAKE_COMMAND} -E echo ${message}
COMMAND ${CMAKE_COMMAND} -E touch ${_sip_output_files}
COMMAND ${SIPCMD}
DEPENDS ${_abs_module_sip} ${SIP_EXTRA_FILES_DEPEND}
)

SET(CPP_FILES ${sip_output_files})
ENDMACRO(GENERATE_SIP_PYTHON_MODULE_CODE)

# Will compile and link the module
MACRO(BUILD_SIP_PYTHON_MODULE MODULE_NAME SIP_FILES EXTRA_OBJECTS)
SET(EXTRA_LINK_LIBRARIES ${ARGN})

# We give this target a long logical target name.
# (This is to avoid having the library name clash with any already
# install library names. If that happens then cmake dependency
# tracking get confused.)
STRING(REPLACE "." "_" _logical_name ${MODULE_NAME})
SET(_logical_name "python_module_${_logical_name}")

ADD_LIBRARY(${_logical_name} MODULE ${_sip_output_files} ${EXTRA_OBJECTS})
IF (NOT APPLE)
TARGET_LINK_LIBRARIES(${_logical_name} ${PYTHON_LIBRARY})
ENDIF (NOT APPLE)
TARGET_LINK_LIBRARIES(${_logical_name} ${EXTRA_LINK_LIBRARIES})
IF (APPLE)
SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES LINK_FLAGS "-undefined dynamic_lookup")
ENDIF (APPLE)
SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES PREFIX "" OUTPUT_NAME ${_child_module_name})

IF (WIN32)
SET_TARGET_PROPERTIES(${_logical_name} PROPERTIES SUFFIX ".pyd")
ENDIF (WIN32)

IF(WIN32)
GET_TARGET_PROPERTY(_runtime_output ${_logical_name} RUNTIME_OUTPUT_DIRECTORY)
ADD_CUSTOM_COMMAND(TARGET ${_logical_name} POST_BUILD
COMMAND ${CMAKE_COMMAND} -E echo "Copying extension ${_child_module_name}"
COMMAND ${CMAKE_COMMAND} -E copy_if_different "$<TARGET_FILE:${_logical_name}>" "${_runtime_output}/${_child_module_name}.pyd"
DEPENDS ${_logical_name}
)
ENDIF(WIN32)

INSTALL(TARGETS ${_logical_name} DESTINATION "${PYTHON_SITE_PACKAGES_DIR}/${_parent_module_path}")
ENDIF(WIN32)

ENDMACRO(ADD_SIP_PYTHON_MODULE)
INSTALL(TARGETS ${_logical_name} DESTINATION "${PYTHON_SITE_PACKAGES_DIR}/${_parent_module_path}")
ENDMACRO(BUILD_SIP_PYTHON_MODULE MODULE_NAME SIP_FILES EXTRA_OBJECTS)
23 changes: 16 additions & 7 deletions python/CMakeLists.txt
Expand Up @@ -70,6 +70,7 @@ ADD_SUBDIRECTORY(PyQt)
ADD_SUBDIRECTORY(pyplugin_installer)
ADD_SUBDIRECTORY(ext-libs)
ADD_SUBDIRECTORY(testing)
ADD_SUBDIRECTORY(sip_helpers)

IF(POLICY CMP0040)
CMAKE_POLICY (POP) # see PUSH above
Expand Down Expand Up @@ -113,6 +114,8 @@ INCLUDE_DIRECTORIES(
../src/gui/effects
../src/gui/layertree

sip_helpers

${CMAKE_BINARY_DIR} # qgsconfig.h, qgsversion.h
)

Expand Down Expand Up @@ -161,7 +164,9 @@ ENDIF(NOT PYQT4_VERSION_NUM LESS 264453)
FILE(GLOB_RECURSE sip_files_core core/*.sip)
SET(SIP_EXTRA_FILES_DEPEND ${sip_files_core})
SET(SIP_EXTRA_OPTIONS ${PYQT_SIP_FLAGS} -o -a ${CMAKE_BINARY_DIR}/python/qgis.core.api)
ADD_SIP_PYTHON_MODULE(qgis._core core/core.sip qgis_core)
GENERATE_SIP_PYTHON_MODULE_CODE(qgis._core core/core.sip cpp_files)
BUILD_SIP_PYTHON_MODULE(qgis._core core/core.sip ${cpp_files} $<TARGET_OBJECTS:qgis_sip_helpers> qgis_core)
SET(SIP_CORE_CPP_FILES ${cpp_files})

# additional gui includes
INCLUDE_DIRECTORIES(
Expand Down Expand Up @@ -189,7 +194,8 @@ IF(UNIX AND NOT SIP_VERSION_NUM LESS 265984)
ADD_DEFINITIONS(-Dprotected=public)
ENDIF(UNIX AND NOT SIP_VERSION_NUM LESS 265984)

ADD_SIP_PYTHON_MODULE(qgis._gui gui/gui.sip qgis_core qgis_gui)
GENERATE_SIP_PYTHON_MODULE_CODE(qgis._gui gui/gui.sip cpp_files)
BUILD_SIP_PYTHON_MODULE(qgis._gui gui/gui.sip ${cpp_files} "" qgis_core qgis_gui)

SET(PY_MODULES core gui analysis networkanalysis)

Expand All @@ -207,7 +213,8 @@ IF (WITH_SERVER AND WITH_SERVER_PLUGINS)
)
SET(SIP_EXTRA_FILES_DEPEND ${sip_files_core} ${sip_files_server})
SET(SIP_EXTRA_OPTIONS ${PYQT_SIP_FLAGS} -o -a ${CMAKE_BINARY_DIR}/python/qgis.server.api)
ADD_SIP_PYTHON_MODULE(qgis._server server/server.sip qgis_core qgis_server)
GENERATE_SIP_PYTHON_MODULE_CODE(qgis._server server/server.sip cpp_files)
BUILD_SIP_PYTHON_MODULE(qgis._server server/server.sip ${cpp_files} "" qgis_core qgis_server)
ENDIF (WITH_SERVER AND WITH_SERVER_PLUGINS)

# additional analysis includes
Expand All @@ -221,7 +228,7 @@ INCLUDE_DIRECTORIES(
${CMAKE_BINARY_DIR}/src/analysis/network
${CMAKE_BINARY_DIR}/src/analysis/raster
${CMAKE_BINARY_DIR}/src/analysis/interpolation
${CMAKE_BINARY_DIR}/src/analysis/openstreetmap
${CMAKE_BINARY_DIR}/src/analysis/openstreetmap
)

# analysis module
Expand All @@ -230,17 +237,19 @@ FILE(GLOB sip_files_analysis
analysis/raster/*.sip
analysis/vector/*.sip
analysis/interpolation/*.sip
analysis/openstreetmap/*.sip
analysis/openstreetmap/*.sip
)
SET(SIP_EXTRA_FILES_DEPEND ${sip_files_core} ${sip_files_analysis})
SET(SIP_EXTRA_OPTIONS ${PYQT_SIP_FLAGS} -o -a ${CMAKE_BINARY_DIR}/python/qgis.analysis.api)
ADD_SIP_PYTHON_MODULE(qgis._analysis analysis/analysis.sip qgis_core qgis_analysis)
GENERATE_SIP_PYTHON_MODULE_CODE(qgis._analysis analysis/analysis.sip cpp_files)
BUILD_SIP_PYTHON_MODULE(qgis._analysis analysis/analysis.sip ${cpp_files} "" qgis_core qgis_analysis)

# network-analysis module
FILE(GLOB_RECURSE sip_files_network_analysis analysis/network/*.sip)
SET(SIP_EXTRA_FILES_DEPEND ${sip_files_core} ${sip_files_network_analysis})
SET(SIP_EXTRA_OPTIONS ${PYQT_SIP_FLAGS} -o -a ${CMAKE_BINARY_DIR}/python/qgis.networkanalysis.api)
ADD_SIP_PYTHON_MODULE(qgis._networkanalysis analysis/network/networkanalysis.sip qgis_core qgis_networkanalysis)
GENERATE_SIP_PYTHON_MODULE_CODE(qgis._networkanalysis analysis/network/networkanalysis.sip cpp_files)
BUILD_SIP_PYTHON_MODULE(qgis._networkanalysis networkanalysis/networkanalysis.sip ${cpp_files} "" qgis_core qgis_networkanalysis)

SET(QGIS_PYTHON_DIR ${PYTHON_SITE_PACKAGES_DIR}/qgis)

Expand Down
47 changes: 45 additions & 2 deletions python/PyQt/PyQt5/QtCore.py
@@ -1,3 +1,46 @@
from PyQt5.QtCore import *
NULL = QVariant()
QPyNullVariant = QVariant()

from types import MethodType


def __nonzero__(self):
if self.isNull():
return False
else:
return super().__nonzero__()


def __repr__(self):
if self.isNull():
return 'NULL'
else:
return super().__repr__(self)


def __eq__(self, other):
if self.isNull():
return (isinstance(other, QVariant) and other.isNull())or other is None
else:
return super().__eq__(self, other)


def __ne__(self, other):
if self.isNull():
return not (isinstance(other, QVariant) and other.isNull()) and other is not None
else:
return super().__ne__(self, other)


def __hash__(self):
if self.isNull():
return 2178309
else:
return super.__hash__(self)

QVariant.__nonzero__ = __nonzero__
QVariant.__repr__ = __repr__
QVariant.__eq__ = __eq__
QVariant.__ne__ = __ne__
QVariant.__hash__ = __hash__

NULL = QVariant(QVariant.Int)
2 changes: 1 addition & 1 deletion python/core/__init__.py
Expand Up @@ -23,7 +23,7 @@
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'

from qgis.PyQt.QtCore import QCoreApplication, QPyNullVariant, NULL
from qgis.PyQt.QtCore import QCoreApplication, NULL

import inspect
import string
Expand Down
12 changes: 12 additions & 0 deletions python/core/conversions.sip
Expand Up @@ -1964,3 +1964,15 @@ template <TYPE>
%End
};
%End

%ModuleHeaderCode
#include "qgissiphelper.h"
%End

%PostInitialisationCode

// Import the Chimera helper registration functions.
void (*register_from_qvariant_convertor)(FromQVariantConvertorFn);
register_from_qvariant_convertor = (void (*)(FromQVariantConvertorFn))sipImportSymbol("pyqt5_register_from_qvariant_convertor");
register_from_qvariant_convertor(null_from_qvariant_convertor);
%End
39 changes: 39 additions & 0 deletions python/sip_helpers/CMakeLists.txt
@@ -0,0 +1,39 @@
SET (QGIS_SIP_HELPER_SRCS
qgissiphelper.cpp
)

SET (QGIS_SIP_HELPER_HDRS
qgissiphelper.h
)

INCLUDE_DIRECTORIES(SYSTEM
${PYTHON_INCLUDE_PATH}
${SIP_INCLUDE_DIR}
${Qt5Core_INCLUDE_DIRS}
${Qt5Xml_INCLUDE_DIRS}
${Qt5Gui_INCLUDE_DIRS}
${Qt5Widgets_INCLUDE_DIRS}
${Qt5PrintSupport_INCLUDE_DIRS}
)

INCLUDE_DIRECTORIES(
${CMAKE_CURRENT_BINARY_DIR}/../core
../../src/core
../../src/core/auth
../../src/core/pal
../../src/core/composer
../../src/core/diagram
../../src/core/effects
../../src/core/dxf
../../src/core/geometry
../../src/core/gps
../../src/core/layertree
../../src/core/raster
../../src/core/symbology-ng
.
)

ADD_CUSTOM_TARGET(generate_sip_core_cpp_files DEPENDS ${SIP_CORE_CPP_FILES})
ADD_LIBRARY(qgis_sip_helpers OBJECT ${QGIS_SIP_HELPER_SRCS} ${QGIS_SIP_HELPER_HDRS})
ADD_DEPENDENCIES(qgis_sip_helpers generate_sip_core_cpp_files)
SET_TARGET_PROPERTIES(qgis_sip_helpers PROPERTIES POSITION_INDEPENDENT_CODE TRUE)

0 comments on commit 89b7a4a

Please sign in to comment.