## gflags CMake configuration file

# library version information
set (@PACKAGE_PREFIX@_VERSION_STRING "@PACKAGE_VERSION@")
set (@PACKAGE_PREFIX@_VERSION_MAJOR  @PACKAGE_VERSION_MAJOR@)
set (@PACKAGE_PREFIX@_VERSION_MINOR  @PACKAGE_VERSION_MINOR@)
set (@PACKAGE_PREFIX@_VERSION_PATCH  @PACKAGE_VERSION_PATCH@)

# import targets
if (NOT DEFINED @PACKAGE_PREFIX@_USE_TARGET_NAMESPACE)
  set (@PACKAGE_PREFIX@_USE_TARGET_NAMESPACE FALSE)
endif ()
if (@PACKAGE_PREFIX@_USE_TARGET_NAMESPACE)
  include ("${CMAKE_CURRENT_LIST_DIR}/@EXPORT_NAME@.cmake")
  set (@PACKAGE_PREFIX@_TARGET_NAMESPACE @PACKAGE_NAME@)
else ()
  include ("${CMAKE_CURRENT_LIST_DIR}/@PACKAGE_NAME@-nonamespace-targets.cmake")
  set (@PACKAGE_PREFIX@_TARGET_NAMESPACE)
endif ()
if (@PACKAGE_PREFIX@_TARGET_NAMESPACE)
  set (@PACKAGE_PREFIX@_TARGET_PREFIX ${@PACKAGE_PREFIX@_TARGET_NAMESPACE}::)
else ()
  set (@PACKAGE_PREFIX@_TARGET_PREFIX)
endif ()

# installation prefix
get_filename_component (CMAKE_CURRENT_LIST_DIR "${CMAKE_CURRENT_LIST_FILE}" PATH)
get_filename_component (_INSTALL_PREFIX "${CMAKE_CURRENT_LIST_DIR}/@INSTALL_PREFIX_REL2CONFIG_DIR@" ABSOLUTE)

# include directory
#
# Newer versions of CMake set the INTERFACE_INCLUDE_DIRECTORIES property
# of the imported targets. It is hence not necessary to add this path
# manually to the include search path for targets which link to gflags.
set (@PACKAGE_PREFIX@_INCLUDE_DIR "${_INSTALL_PREFIX}/@INCLUDE_INSTALL_DIR@")

if (@PACKAGE_NAME@_FIND_COMPONENTS)
  foreach (@PACKAGE_NAME@_FIND_COMPONENT IN LISTS @PACKAGE_NAME@_FIND_COMPONENTS)
    if (@PACKAGE_NAME@_FIND_REQUIRED_${@PACKAGE_NAME@_FIND_COMPONENT} AND NOT TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_${@PACKAGE_NAME@_FIND_COMPONENT})
      message (FATAL_ERROR "Package @PACKAGE_NAME@ was installed without required component ${@PACKAGE_PREFIX@_TARGET_PREFIX}${@PACKAGE_NAME@_FIND_COMPONENT}!")
    endif ()
  endforeach ()
  list (GET @PACKAGE_NAME@_FIND_COMPONENTS 0 @PACKAGE_NAME@_FIND_COMPONENT)
else ()
  set (@PACKAGE_NAME@_FIND_COMPONENT)
endif ()

# default settings of @PACKAGE_PREFIX@_SHARED and @PACKAGE_PREFIX@_NOTHREADS
#
# It is recommended to use either one of the following find_package commands
# instead of setting the @PACKAGE_PREFIX@_(SHARED|NOTHREADS) variables:
# - find_package(@PACKAGE_NAME@ REQUIRED)
# - find_package(@PACKAGE_NAME@ COMPONENTS nothreads_static)
# - find_package(@PACKAGE_NAME@ COMPONENTS nothreads_shared)
# - find_package(@PACKAGE_NAME@ COMPONENTS static)
# - find_package(@PACKAGE_NAME@ COMPONENTS shared)
if (NOT DEFINED @PACKAGE_PREFIX@_SHARED)
  if (DEFINED @PACKAGE_NAME@_SHARED)
    set (@PACKAGE_PREFIX@_SHARED ${@PACKAGE_NAME@_SHARED})
  elseif (@PACKAGE_NAME@_FIND_COMPONENT)
    if (@PACKAGE_NAME@_FIND_COMPONENT MATCHES "shared")
      set (@PACKAGE_PREFIX@_SHARED TRUE)
    else ()
      set (@PACKAGE_PREFIX@_SHARED FALSE)
    endif ()
  elseif (TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_shared OR TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_nothreads_shared)
    set (@PACKAGE_PREFIX@_SHARED TRUE)
  else ()
    set (@PACKAGE_PREFIX@_SHARED FALSE)
  endif ()
endif ()
if (NOT DEFINED @PACKAGE_PREFIX@_NOTHREADS)
  if (DEFINED @PACKAGE_NAME@_NOTHREADS)
    set (@PACKAGE_PREFIX@_NOTHREADS ${@PACKAGE_NAME@_NOTHREADS})
  elseif (@PACKAGE_NAME@_FIND_COMPONENT)
    if (@PACKAGE_NAME@_FIND_COMPONENT MATCHES "nothreads")
      set (@PACKAGE_PREFIX@_NOTHREADS TRUE)
    else ()
      set (@PACKAGE_PREFIX@_NOTHREADS FALSE)
    endif ()
  elseif (TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_static OR TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_shared)
    set (@PACKAGE_PREFIX@_NOTHREADS FALSE)
  else ()
    set (@PACKAGE_PREFIX@_NOTHREADS TRUE)
  endif ()
endif ()

# choose imported library target
if (NOT @PACKAGE_PREFIX@_TARGET)
  if (@PACKAGE_NAME@_TARGET)
    set (@PACKAGE_PREFIX@_TARGET ${@PACKAGE_NAME@_TARGET})
  elseif (@PACKAGE_PREFIX@_SHARED)
    if (@PACKAGE_PREFIX@_NOTHREADS)
      set (@PACKAGE_PREFIX@_TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_nothreads_shared)
    else ()
      set (@PACKAGE_PREFIX@_TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_shared)
    endif ()
  else ()
    if (@PACKAGE_PREFIX@_NOTHREADS)
      set (@PACKAGE_PREFIX@_TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_nothreads_static)
    else ()
      set (@PACKAGE_PREFIX@_TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@_static)
    endif ()
  endif ()
endif ()
if (NOT TARGET ${@PACKAGE_PREFIX@_TARGET})
  message (FATAL_ERROR "Your @PACKAGE_NAME@ installation does not contain a ${@PACKAGE_PREFIX@_TARGET} library target!"
                       " Try a different combination of @PACKAGE_PREFIX@_SHARED and @PACKAGE_PREFIX@_NOTHREADS.")
endif ()

# add more convenient "${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@" import target
if (NOT TARGET ${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@)
  if (@PACKAGE_PREFIX@_SHARED)
    add_library (${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@ SHARED IMPORTED)
  else ()
    add_library (${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@ STATIC IMPORTED)
  endif ()
  # copy INTERFACE_* properties
  foreach (_@PACKAGE_PREFIX@_PROPERTY_NAME IN ITEMS
    COMPILE_DEFINITIONS
    COMPILE_FEATURES
    COMPILE_OPTIONS
    INCLUDE_DIRECTORIES
    LINK_LIBRARIES
    POSITION_INDEPENDENT_CODE
  )
    get_target_property (_@PACKAGE_PREFIX@_PROPERTY_VALUE ${@PACKAGE_PREFIX@_TARGET} INTERFACE_${_@PACKAGE_PREFIX@_PROPERTY_NAME})
    if (_@PACKAGE_PREFIX@_PROPERTY_VALUE)
      set_target_properties(${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@ PROPERTIES
        INTERFACE_${_@PACKAGE_PREFIX@_PROPERTY_NAME} "${_@PACKAGE_PREFIX@_PROPERTY_VALUE}"
      )
    endif ()
  endforeach ()
  # copy IMPORTED_*_<CONFIG> properties
  get_target_property (_@PACKAGE_PREFIX@_CONFIGURATIONS ${@PACKAGE_PREFIX@_TARGET} IMPORTED_CONFIGURATIONS)
  set_target_properties (${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@ PROPERTIES IMPORTED_CONFIGURATIONS "${_@PACKAGE_PREFIX@_CONFIGURATIONS}")
  foreach (_@PACKAGE_PREFIX@_PROPERTY_NAME IN ITEMS
    IMPLIB
    LOCATION
    LINK_DEPENDENT_LIBRARIES
    LINK_INTERFACE_LIBRARIES
    LINK_INTERFACE_LANGUAGES
    LINK_INTERFACE_MULTIPLICITY
    NO_SONAME
    SONAME
  )
    foreach (_@PACKAGE_PREFIX@_CONFIG IN LISTS _@PACKAGE_PREFIX@_CONFIGURATIONS)
      get_target_property (_@PACKAGE_PREFIX@_PROPERTY_VALUE ${@PACKAGE_PREFIX@_TARGET} IMPORTED_${_@PACKAGE_PREFIX@_PROPERTY_NAME}_${_@PACKAGE_PREFIX@_CONFIG})
      if (_@PACKAGE_PREFIX@_PROPERTY_VALUE)
        set_target_properties(${@PACKAGE_PREFIX@_TARGET_PREFIX}@PACKAGE_NAME@ PROPERTIES
          IMPORTED_${_@PACKAGE_PREFIX@_PROPERTY_NAME}_${_@PACKAGE_PREFIX@_CONFIG} "${_@PACKAGE_PREFIX@_PROPERTY_VALUE}"
        )
      endif ()
    endforeach ()
  endforeach ()
  unset (_@PACKAGE_PREFIX@_CONFIGURATIONS)
  unset (_@PACKAGE_PREFIX@_CONFIG)
  unset (_@PACKAGE_PREFIX@_PROPERTY_NAME)
  unset (_@PACKAGE_PREFIX@_PROPERTY_VALUE)
endif ()

# alias for default import target to be compatible with older CMake package configurations
set (@PACKAGE_PREFIX@_LIBRARIES "${@PACKAGE_PREFIX@_TARGET}")

# set @PACKAGE_NAME@_* variables for backwards compatibility
if (NOT "^@PACKAGE_NAME@$" STREQUAL "^@PACKAGE_PREFIX@$")
  foreach (_@PACKAGE_PREFIX@_VARIABLE IN ITEMS
    VERSION_STRING
    VERSION_MAJOR
    VERSION_MINOR
    VERSION_PATCH
    INCLUDE_DIR
    LIBRARIES
    TARGET
  )
    set (@PACKAGE_NAME@_${_@PACKAGE_PREFIX@_VARIABLE} "${@PACKAGE_PREFIX@_${_@PACKAGE_PREFIX@_VARIABLE}}")
  endforeach ()
  unset (_@PACKAGE_PREFIX@_VARIABLE)
endif ()

# unset private variables
unset (@PACKAGE_NAME@_FIND_COMPONENT)
unset (_INSTALL_PREFIX)
